]>
Commit | Line | Data |
---|---|---|
7c673cae FG |
1 | /////////1/////////2/////////3/////////4/////////5/////////6/////////7/////////8 |
2 | // extended_type_info_typeid.cpp: specific implementation of type info | |
3 | // that is based on typeid | |
4 | ||
5 | // (C) Copyright 2002 Robert Ramey - http://www.rrsd.com . | |
6 | // Use, modification and distribution is subject to the Boost Software | |
7 | // License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at | |
8 | // http://www.boost.org/LICENSE_1_0.txt) | |
9 | ||
10 | // See http://www.boost.org for updates, documentation, and revision history. | |
11 | ||
12 | #include <algorithm> | |
13 | #include <set> | |
14 | #include <boost/assert.hpp> | |
15 | #include <typeinfo> | |
16 | #include <cstddef> // NULL | |
17 | ||
18 | #include <boost/core/no_exceptions_support.hpp> | |
19 | ||
20 | // it marks our code with proper attributes as being exported when | |
21 | // we're compiling it while marking it import when just the headers | |
22 | // is being included. | |
23 | #define BOOST_SERIALIZATION_SOURCE | |
24 | #include <boost/serialization/config.hpp> | |
25 | #include <boost/serialization/singleton.hpp> | |
26 | #include <boost/serialization/extended_type_info_typeid.hpp> | |
27 | ||
28 | namespace boost { | |
29 | namespace serialization { | |
30 | namespace typeid_system { | |
31 | ||
32 | #define EXTENDED_TYPE_INFO_TYPE_KEY 1 | |
33 | ||
34 | struct type_compare | |
35 | { | |
36 | bool | |
37 | operator()( | |
38 | const extended_type_info_typeid_0 * lhs, | |
39 | const extended_type_info_typeid_0 * rhs | |
40 | ) const { | |
41 | return lhs->is_less_than(*rhs); | |
42 | } | |
43 | }; | |
44 | ||
45 | typedef std::multiset< | |
46 | const extended_type_info_typeid_0 *, | |
47 | type_compare | |
48 | > tkmap; | |
49 | ||
50 | BOOST_SERIALIZATION_DECL bool | |
51 | extended_type_info_typeid_0::is_less_than( | |
52 | const boost::serialization::extended_type_info & rhs | |
53 | ) const { | |
54 | // shortcut for common case | |
55 | if(this == & rhs) | |
56 | return false; | |
57 | return 0 != m_ti->before( | |
58 | *(static_cast<const extended_type_info_typeid_0 &>(rhs).m_ti) | |
59 | ); | |
60 | } | |
61 | ||
62 | BOOST_SERIALIZATION_DECL bool | |
63 | extended_type_info_typeid_0::is_equal( | |
64 | const boost::serialization::extended_type_info & rhs | |
65 | ) const { | |
66 | return | |
67 | // note: std::type_info == operator returns an int !!! | |
68 | // the following permits conversion to bool without a warning. | |
69 | ! ( | |
70 | * m_ti | |
71 | != *(static_cast<const extended_type_info_typeid_0 &>(rhs).m_ti) | |
72 | ) | |
73 | ; | |
74 | } | |
75 | ||
76 | BOOST_SERIALIZATION_DECL | |
77 | extended_type_info_typeid_0::extended_type_info_typeid_0( | |
78 | const char * key | |
79 | ) : | |
80 | extended_type_info(EXTENDED_TYPE_INFO_TYPE_KEY, key), | |
81 | m_ti(NULL) | |
82 | {} | |
83 | ||
84 | BOOST_SERIALIZATION_DECL | |
85 | extended_type_info_typeid_0::~extended_type_info_typeid_0() | |
86 | {} | |
87 | ||
88 | BOOST_SERIALIZATION_DECL void | |
89 | extended_type_info_typeid_0::type_register(const std::type_info & ti){ | |
90 | m_ti = & ti; | |
91 | singleton<tkmap>::get_mutable_instance().insert(this); | |
92 | } | |
93 | ||
94 | BOOST_SERIALIZATION_DECL void | |
95 | extended_type_info_typeid_0::type_unregister() | |
96 | { | |
97 | if(NULL != m_ti){ | |
b32b8144 | 98 | BOOST_ASSERT(! singleton<tkmap>::is_destroyed()); |
7c673cae FG |
99 | if(! singleton<tkmap>::is_destroyed()){ |
100 | tkmap & x = singleton<tkmap>::get_mutable_instance(); | |
b32b8144 FG |
101 | |
102 | // remove all entries in map which corresponds to this type | |
103 | // make sure that we don't use any invalidated iterators | |
104 | for(;;){ | |
105 | const tkmap::iterator & it = x.find(this); | |
106 | if(it == x.end()) | |
107 | break; | |
108 | x.erase(it); | |
109 | }; | |
7c673cae FG |
110 | } |
111 | } | |
112 | m_ti = NULL; | |
113 | } | |
114 | ||
115 | #ifdef BOOST_MSVC | |
116 | # pragma warning(push) | |
117 | # pragma warning(disable : 4511 4512) | |
118 | #endif | |
119 | ||
120 | // this derivation is used for creating search arguments | |
121 | class extended_type_info_typeid_arg : | |
122 | public extended_type_info_typeid_0 | |
123 | { | |
124 | virtual void * construct(unsigned int /*count*/, ...) const{ | |
125 | BOOST_ASSERT(false); | |
126 | return NULL; | |
127 | } | |
128 | virtual void destroy(void const * const /*p*/) const { | |
129 | BOOST_ASSERT(false); | |
130 | } | |
131 | public: | |
132 | extended_type_info_typeid_arg(const std::type_info & ti) : | |
133 | extended_type_info_typeid_0(NULL) | |
134 | { | |
135 | // note absense of self register and key as this is used only as | |
136 | // search argument given a type_info reference and is not to | |
137 | // be added to the map. | |
138 | m_ti = & ti; | |
139 | } | |
140 | ~extended_type_info_typeid_arg(){ | |
141 | m_ti = NULL; | |
142 | } | |
143 | }; | |
144 | ||
145 | #ifdef BOOST_MSVC | |
146 | # pragma warning(pop) | |
147 | #endif | |
148 | ||
149 | BOOST_SERIALIZATION_DECL const extended_type_info * | |
150 | extended_type_info_typeid_0::get_extended_type_info( | |
151 | const std::type_info & ti | |
152 | ) const { | |
153 | typeid_system::extended_type_info_typeid_arg etia(ti); | |
154 | const tkmap & t = singleton<tkmap>::get_const_instance(); | |
155 | const tkmap::const_iterator it = t.find(& etia); | |
156 | if(t.end() == it) | |
157 | return NULL; | |
158 | return *(it); | |
159 | } | |
160 | ||
161 | } // namespace detail | |
162 | } // namespace serialization | |
163 | } // namespace boost |