Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

187 lines
4.5 KiB

  1. /***
  2. *stdexcpt.cpp - defines C++ standard exception classes
  3. *
  4. * Copyright (c) 1994-2001, Microsoft Corporation. All rights reserved.
  5. *
  6. *Purpose:
  7. * Implementation of C++ standard exception classes which must live in
  8. * the main CRT, not the C++ CRT, because they are referenced by RTTI
  9. * support in the main CRT.
  10. *
  11. * exception
  12. * bad_cast
  13. * bad_typeid
  14. * __non_rtti_object
  15. *
  16. *Revision History:
  17. * 04-27-94 BES Module created.
  18. * 10-17-94 BWT Disable code for PPC.
  19. * 02-15-95 JWM Minor cleanups related to Olympus bug 3716
  20. * 07-02-95 JWM Now generally ANSI-compliant; excess baggage removed.
  21. * 06-01-99 PML __exString disappeared as of 5/3/99 Plauger STL drop.
  22. * 11-09-99 PML Use malloc, not new, to avoid recursion (vs7#16826).
  23. * 09-07-00 PML Get rid of /lib:libcp directive in obj (vs7#159463)
  24. * 03-21-01 PML Move bad_cast, bad_typeid, __non_rtti_object function
  25. * defs out of typeinfo.h so _STATIC_CPPLIB will work.
  26. *
  27. *******************************************************************************/
  28. #define _USE_ANSI_CPP /* Don't emit /lib:libcp directive */
  29. #include <stdlib.h>
  30. #include <string.h>
  31. #include <eh.h>
  32. #include <stdexcpt.h>
  33. #include <typeinfo.h>
  34. ////////////////////////////////////////////////////////////////////////////////
  35. //
  36. // Implementation of class "exception"
  37. //
  38. //
  39. // Default constructor - initialize to blank
  40. //
  41. exception::exception ()
  42. {
  43. _m_what = NULL;
  44. _m_doFree = 0;
  45. }
  46. //
  47. // Standard constructor: initialize with copy of string
  48. //
  49. exception::exception ( const char * const & what )
  50. {
  51. _m_what = static_cast< char * >( malloc( strlen( what ) + 1 ) );
  52. if ( _m_what != NULL )
  53. strcpy( (char*)_m_what, what );
  54. _m_doFree = 1;
  55. }
  56. //
  57. // Copy constructor
  58. //
  59. exception::exception ( const exception & that )
  60. {
  61. _m_doFree = that._m_doFree;
  62. if (_m_doFree)
  63. {
  64. _m_what = static_cast< char * >( malloc( strlen( that._m_what ) + 1 ) );
  65. if (_m_what != NULL)
  66. strcpy( (char*)_m_what, that._m_what );
  67. }
  68. else
  69. _m_what = that._m_what;
  70. }
  71. //
  72. // Assignment operator: destruct, then copy-construct
  73. //
  74. exception& exception::operator=( const exception& that )
  75. {
  76. if (this != &that)
  77. {
  78. this->exception::~exception();
  79. this->exception::exception(that);
  80. }
  81. return *this;
  82. }
  83. //
  84. // Destructor: free the storage used by the message string if it was
  85. // dynamicly allocated
  86. //
  87. exception::~exception()
  88. {
  89. if (_m_doFree)
  90. free( const_cast< char * >( _m_what ) );
  91. }
  92. //
  93. // exception::what
  94. // Returns the message string of the exception.
  95. // Default implementation of this method returns the stored string if there
  96. // is one, otherwise returns a standard string.
  97. //
  98. const char * exception::what() const
  99. {
  100. if ( _m_what != NULL )
  101. return _m_what;
  102. else
  103. return "Unknown exception";
  104. }
  105. ////////////////////////////////////////////////////////////////////////////////
  106. //
  107. // Implementation of class "bad_cast"
  108. //
  109. bad_cast::bad_cast(const char * _Message)
  110. : exception(_Message)
  111. {
  112. }
  113. bad_cast::bad_cast(const bad_cast & that)
  114. : exception(that)
  115. {
  116. }
  117. bad_cast::~bad_cast()
  118. {
  119. }
  120. #ifdef CRTDLL
  121. //
  122. // This is a dummy constructor. Previously, the only bad_cast ctor was
  123. // bad_cast(const char * const &). To provide backwards compatibility
  124. // for std::bad_cast, we want the main ctor to be bad_cast(const char *)
  125. // instead. Since you can't have both bad_cast(const char * const &) and
  126. // bad_cast(const char *), we define this bad_cast(const char * const *),
  127. // which will have the exact same codegen as bad_cast(const char * const &),
  128. // and alias the old form with a .def entry.
  129. //
  130. bad_cast::bad_cast(const char * const * _PMessage)
  131. : exception(*_PMessage)
  132. {
  133. }
  134. #endif
  135. ////////////////////////////////////////////////////////////////////////////////
  136. //
  137. // Implementation of class "bad_typeid"
  138. //
  139. bad_typeid::bad_typeid(const char * _Message)
  140. : exception(_Message)
  141. {
  142. }
  143. bad_typeid::bad_typeid(const bad_typeid & that)
  144. : exception(that)
  145. {
  146. }
  147. bad_typeid::~bad_typeid()
  148. {
  149. }
  150. ////////////////////////////////////////////////////////////////////////////////
  151. //
  152. // Implementation of class "__non_rtti_object"
  153. //
  154. __non_rtti_object::__non_rtti_object(const char * _Message)
  155. : bad_typeid(_Message)
  156. {
  157. }
  158. __non_rtti_object::__non_rtti_object(const __non_rtti_object & that)
  159. : bad_typeid(that)
  160. {
  161. }
  162. __non_rtti_object::~__non_rtti_object()
  163. {
  164. }