Subversion Repositories Kolibri OS

Rev

Blame | Last modification | View Log | RSS feed

  1. // RTTI support internals for -*- C++ -*-
  2. // Copyright (C) 1994-2013 Free Software Foundation, Inc.
  3.  
  4. // This file is part of GCC.
  5. //
  6. // GCC is free software; you can redistribute it and/or modify
  7. // it under the terms of the GNU General Public License as published by
  8. // the Free Software Foundation; either version 3, or (at your option)
  9. // any later version.
  10.  
  11. // GCC is distributed in the hope that it will be useful,
  12. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14. // GNU General Public License for more details.
  15.  
  16. // Under Section 7 of GPL version 3, you are granted additional
  17. // permissions described in the GCC Runtime Library Exception, version
  18. // 3.1, as published by the Free Software Foundation.
  19.  
  20. // You should have received a copy of the GNU General Public License and
  21. // a copy of the GCC Runtime Library Exception along with this program;
  22. // see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
  23. // <http://www.gnu.org/licenses/>.
  24.  
  25. #include "typeinfo"
  26. #include <cstddef>
  27.  
  28. // Class declarations shared between the typeinfo implementation files.
  29.  
  30. #include <cxxabi.h>
  31.  
  32. namespace __cxxabiv1 {
  33.  
  34. inline bool __pbase_type_info::
  35. __pointer_catch (const __pbase_type_info *thrown_type,
  36.                  void **thr_obj,
  37.                  unsigned outer) const
  38. {
  39.   return __pointee->__do_catch (thrown_type->__pointee, thr_obj, outer + 2);
  40. }
  41.  
  42. namespace {
  43.  
  44. using namespace std;
  45. using namespace abi;
  46.  
  47. // Initial part of a vtable, this structure is used with offsetof, so we don't
  48. // have to keep alignments consistent manually.
  49. struct vtable_prefix
  50. {
  51.   // Offset to most derived object.
  52.   ptrdiff_t whole_object;
  53.  
  54.   // Additional padding if necessary.
  55. #ifdef _GLIBCXX_VTABLE_PADDING
  56.   ptrdiff_t padding1;              
  57. #endif
  58.  
  59.   // Pointer to most derived type_info.
  60.   const __class_type_info *whole_type;  
  61.  
  62.   // Additional padding if necessary.
  63. #ifdef _GLIBCXX_VTABLE_PADDING
  64.   ptrdiff_t padding2;              
  65. #endif
  66.  
  67.   // What a class's vptr points to.
  68.   const void *origin;              
  69. };
  70.  
  71. template <typename T>
  72. inline const T *
  73. adjust_pointer (const void *base, ptrdiff_t offset)
  74. {
  75.   return reinterpret_cast <const T *>
  76.     (reinterpret_cast <const char *> (base) + offset);
  77. }
  78.  
  79. // ADDR is a pointer to an object.  Convert it to a pointer to a base,
  80. // using OFFSET. IS_VIRTUAL is true, if we are getting a virtual base.
  81. inline void const *
  82. convert_to_base (void const *addr, bool is_virtual, ptrdiff_t offset)
  83. {
  84.   if (is_virtual)
  85.     {
  86.       const void *vtable = *static_cast <const void *const *> (addr);
  87.      
  88.       offset = *adjust_pointer<ptrdiff_t> (vtable, offset);
  89.     }
  90.  
  91.   return adjust_pointer<void> (addr, offset);
  92. }
  93.  
  94. // some predicate functions for __class_type_info::__sub_kind
  95. inline bool contained_p (__class_type_info::__sub_kind access_path)
  96. {
  97.   return access_path >= __class_type_info::__contained_mask;
  98. }
  99. inline bool public_p (__class_type_info::__sub_kind access_path)
  100. {
  101.   return access_path & __class_type_info::__contained_public_mask;
  102. }
  103. inline bool virtual_p (__class_type_info::__sub_kind access_path)
  104. {
  105.   return (access_path & __class_type_info::__contained_virtual_mask);
  106. }
  107. inline bool contained_public_p (__class_type_info::__sub_kind access_path)
  108. {
  109.   return ((access_path & __class_type_info::__contained_public)
  110.           == __class_type_info::__contained_public);
  111. }
  112. inline bool contained_nonpublic_p (__class_type_info::__sub_kind access_path)
  113. {
  114.   return ((access_path & __class_type_info::__contained_public)
  115.           == __class_type_info::__contained_mask);
  116. }
  117. inline bool contained_nonvirtual_p (__class_type_info::__sub_kind access_path)
  118. {
  119.   return ((access_path & (__class_type_info::__contained_mask
  120.                           | __class_type_info::__contained_virtual_mask))
  121.           == __class_type_info::__contained_mask);
  122. }
  123.  
  124. static const __class_type_info *const nonvirtual_base_type =
  125.     static_cast <const __class_type_info *> (0) + 1;
  126.  
  127. } // namespace
  128.  
  129. // __upcast_result is used to hold information during traversal of a class
  130. // hierarchy when catch matching.
  131. struct __class_type_info::__upcast_result
  132. {
  133.   const void *dst_ptr;        // pointer to caught object
  134.   __sub_kind part2dst;        // path from current base to target
  135.   int src_details;            // hints about the source type hierarchy
  136.   const __class_type_info *base_type; // where we found the target,
  137.                               // if in vbase the __class_type_info of vbase
  138.                               // if a non-virtual base then 1
  139.                               // else NULL
  140.   __upcast_result (int d)
  141.     :dst_ptr (NULL), part2dst (__unknown), src_details (d), base_type (NULL)
  142.     {}
  143. };
  144.  
  145. // __dyncast_result is used to hold information during traversal of a class
  146. // hierarchy when dynamic casting.
  147. struct __class_type_info::__dyncast_result
  148. {
  149.   const void *dst_ptr;        // pointer to target object or NULL
  150.   __sub_kind whole2dst;       // path from most derived object to target
  151.   __sub_kind whole2src;       // path from most derived object to sub object
  152.   __sub_kind dst2src;         // path from target to sub object
  153.   int whole_details;          // details of the whole class hierarchy
  154.  
  155.   __dyncast_result (int details_ = __vmi_class_type_info::__flags_unknown_mask)
  156.     :dst_ptr (NULL), whole2dst (__unknown),
  157.      whole2src (__unknown), dst2src (__unknown),
  158.      whole_details (details_)
  159.     {}
  160.  
  161. protected:
  162.   __dyncast_result(const __dyncast_result&);
  163.  
  164.   __dyncast_result&
  165.   operator=(const __dyncast_result&);
  166. };
  167.  
  168. inline __class_type_info::__sub_kind __class_type_info::
  169. __find_public_src (ptrdiff_t src2dst,
  170.                    const void *obj_ptr,
  171.                    const __class_type_info *src_type,
  172.                    const void *src_ptr) const
  173. {
  174.   if (src2dst >= 0)
  175.     return adjust_pointer <void> (obj_ptr, src2dst) == src_ptr
  176.             ? __contained_public : __not_contained;
  177.   if (src2dst == -2)
  178.     return __not_contained;
  179.   return __do_find_public_src (src2dst, obj_ptr, src_type, src_ptr);
  180. }
  181.  
  182. }
  183.