]> git.proxmox.com Git - ceph.git/blob - ceph/src/boost/boost/interprocess/detail/named_proxy.hpp
update sources to v12.2.3
[ceph.git] / ceph / src / boost / boost / interprocess / detail / named_proxy.hpp
1 //////////////////////////////////////////////////////////////////////////////
2 //
3 // (C) Copyright Ion Gaztanaga 2005-2012. Distributed under the Boost
4 // Software License, Version 1.0. (See accompanying file
5 // LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
6 //
7 // See http://www.boost.org/libs/interprocess for documentation.
8 //
9 //////////////////////////////////////////////////////////////////////////////
10
11 #ifndef BOOST_INTERPROCESS_NAMED_PROXY_HPP
12 #define BOOST_INTERPROCESS_NAMED_PROXY_HPP
13
14 #ifndef BOOST_CONFIG_HPP
15 # include <boost/config.hpp>
16 #endif
17 #
18 #if defined(BOOST_HAS_PRAGMA_ONCE)
19 # pragma once
20 #endif
21
22 #include <boost/interprocess/detail/config_begin.hpp>
23 #include <boost/interprocess/detail/workaround.hpp>
24
25 // interprocess/detail
26 #include <boost/interprocess/detail/in_place_interface.hpp>
27 #include <boost/interprocess/detail/mpl.hpp>
28 #include <boost/move/utility_core.hpp>
29 #ifndef BOOST_INTERPROCESS_PERFECT_FORWARDING
30 #include <boost/move/detail/fwd_macros.hpp>
31 #else
32 #include <boost/move/utility_core.hpp>
33 #include <boost/interprocess/detail/variadic_templates_tools.hpp>
34 #endif //#ifdef BOOST_INTERPROCESS_PERFECT_FORWARDING
35 #include <boost/container/detail/placement_new.hpp>
36
37 #include <cstddef>
38
39 //!\file
40 //!Describes a proxy class that implements named allocation syntax.
41
42 namespace boost {
43 namespace interprocess {
44 namespace ipcdetail {
45
46 #ifdef BOOST_INTERPROCESS_PERFECT_FORWARDING
47
48 template<class T, bool is_iterator, class ...Args>
49 struct CtorArgN : public placement_destroy<T>
50 {
51 typedef bool_<is_iterator> IsIterator;
52 typedef CtorArgN<T, is_iterator, Args...> self_t;
53 typedef typename build_number_seq<sizeof...(Args)>::type index_tuple_t;
54
55 self_t& operator++()
56 {
57 this->do_increment(IsIterator(), index_tuple_t());
58 return *this;
59 }
60
61 self_t operator++(int) { return ++*this; *this; }
62
63 CtorArgN(Args && ...args)
64 : args_(args...)
65 {}
66
67 virtual void construct_n(void *mem
68 , std::size_t num
69 , std::size_t &constructed)
70 {
71 T* memory = static_cast<T*>(mem);
72 for(constructed = 0; constructed < num; ++constructed){
73 this->construct(memory++, IsIterator(), index_tuple_t());
74 this->do_increment(IsIterator(), index_tuple_t());
75 }
76 }
77
78 private:
79 template<std::size_t ...IdxPack>
80 void construct(void *mem, true_, const index_tuple<IdxPack...>&)
81 { ::new((void*)mem, boost_container_new_t())T(*boost::forward<Args>(get<IdxPack>(args_))...); }
82
83 template<std::size_t ...IdxPack>
84 void construct(void *mem, false_, const index_tuple<IdxPack...>&)
85 { ::new((void*)mem, boost_container_new_t())T(boost::forward<Args>(get<IdxPack>(args_))...); }
86
87 template<std::size_t ...IdxPack>
88 void do_increment(true_, const index_tuple<IdxPack...>&)
89 {
90 this->expansion_helper(++get<IdxPack>(args_)...);
91 }
92
93 template<class ...ExpansionArgs>
94 void expansion_helper(ExpansionArgs &&...)
95 {}
96
97 template<std::size_t ...IdxPack>
98 void do_increment(false_, const index_tuple<IdxPack...>&)
99 {}
100
101 tuple<Args&...> args_;
102 };
103
104 //!Describes a proxy class that implements named
105 //!allocation syntax.
106 template
107 < class SegmentManager //segment manager to construct the object
108 , class T //type of object to build
109 , bool is_iterator //passing parameters are normal object or iterators?
110 >
111 class named_proxy
112 {
113 typedef typename SegmentManager::char_type char_type;
114 const char_type * mp_name;
115 SegmentManager * mp_mngr;
116 mutable std::size_t m_num;
117 const bool m_find;
118 const bool m_dothrow;
119
120 public:
121 named_proxy(SegmentManager *mngr, const char_type *name, bool find, bool dothrow)
122 : mp_name(name), mp_mngr(mngr), m_num(1)
123 , m_find(find), m_dothrow(dothrow)
124 {}
125
126 template<class ...Args>
127 T *operator()(Args &&...args) const
128 {
129 CtorArgN<T, is_iterator, Args...> &&ctor_obj = CtorArgN<T, is_iterator, Args...>
130 (boost::forward<Args>(args)...);
131 return mp_mngr->template
132 generic_construct<T>(mp_name, m_num, m_find, m_dothrow, ctor_obj);
133 }
134
135 //This operator allows --> named_new("Name")[3]; <-- syntax
136 const named_proxy &operator[](std::size_t num) const
137 { m_num *= num; return *this; }
138 };
139
140 #else //#ifdef BOOST_INTERPROCESS_PERFECT_FORWARDING
141
142 ////////////////////////////////////////////////////////////////
143 // What the macro should generate (n == 2):
144 //
145 // template<class T, bool is_iterator, class P1, class P2>
146 // struct Ctor2Arg
147 // : public placement_destroy<T>
148 // {
149 // typedef bool_<is_iterator> IsIterator;
150 // typedef Ctor2Arg self_t;
151 //
152 // void do_increment(false_)
153 // { ++m_p1; ++m_p2; }
154 //
155 // void do_increment(true_){}
156 //
157 // self_t& operator++()
158 // {
159 // this->do_increment(IsIterator());
160 // return *this;
161 // }
162 //
163 // self_t operator++(int) { return ++*this; *this; }
164 //
165 // Ctor2Arg(const P1 &p1, const P2 &p2)
166 // : p1((P1 &)p_1), p2((P2 &)p_2) {}
167 //
168 // void construct(void *mem)
169 // { new((void*)object)T(m_p1, m_p2); }
170 //
171 // virtual void construct_n(void *mem
172 // , std::size_t num
173 // , std::size_t &constructed)
174 // {
175 // T* memory = static_cast<T*>(mem);
176 // for(constructed = 0; constructed < num; ++constructed){
177 // this->construct(memory++, IsIterator());
178 // this->do_increment(IsIterator());
179 // }
180 // }
181 //
182 // private:
183 // void construct(void *mem, true_)
184 // { new((void*)mem)T(*m_p1, *m_p2); }
185 //
186 // void construct(void *mem, false_)
187 // { new((void*)mem)T(m_p1, m_p2); }
188 //
189 // P1 &m_p1; P2 &m_p2;
190 // };
191 ////////////////////////////////////////////////////////////////
192
193 #define BOOST_INTERPROCESS_NAMED_PROXY_CTORARGN(N)\
194 \
195 template<class T BOOST_MOVE_I##N BOOST_MOVE_CLASS##N > \
196 struct CtorArg##N : placement_destroy<T>\
197 {\
198 typedef CtorArg##N self_t;\
199 \
200 CtorArg##N ( BOOST_MOVE_UREF##N )\
201 BOOST_MOVE_COLON##N BOOST_MOVE_FWD_INIT##N{}\
202 \
203 virtual void construct_n(void *mem, std::size_t num, std::size_t &constructed)\
204 {\
205 T* memory = static_cast<T*>(mem);\
206 for(constructed = 0; constructed < num; ++constructed){\
207 ::new((void*)memory++) T ( BOOST_MOVE_MFWD##N );\
208 }\
209 }\
210 \
211 private:\
212 BOOST_MOVE_MREF##N\
213 };\
214 //!
215 BOOST_MOVE_ITERATE_0TO9(BOOST_INTERPROCESS_NAMED_PROXY_CTORARGN)
216 #undef BOOST_INTERPROCESS_NAMED_PROXY_CTORARGN
217
218 #define BOOST_INTERPROCESS_NAMED_PROXY_CTORITN(N)\
219 \
220 template<class T BOOST_MOVE_I##N BOOST_MOVE_CLASS##N > \
221 struct CtorIt##N : public placement_destroy<T>\
222 {\
223 typedef CtorIt##N self_t;\
224 \
225 self_t& operator++()\
226 { BOOST_MOVE_MINC##N; return *this; }\
227 \
228 self_t operator++(int) { return ++*this; *this; }\
229 \
230 CtorIt##N ( BOOST_MOVE_VAL##N )\
231 BOOST_MOVE_COLON##N BOOST_MOVE_VAL_INIT##N{}\
232 \
233 virtual void construct_n(void *mem, std::size_t num, std::size_t &constructed)\
234 {\
235 T* memory = static_cast<T*>(mem);\
236 for(constructed = 0; constructed < num; ++constructed){\
237 ::new((void*)memory++) T( BOOST_MOVE_MITFWD##N );\
238 ++(*this);\
239 }\
240 }\
241 \
242 private:\
243 BOOST_MOVE_MEMB##N\
244 };\
245 //!
246 BOOST_MOVE_ITERATE_0TO9(BOOST_INTERPROCESS_NAMED_PROXY_CTORITN)
247 #undef BOOST_INTERPROCESS_NAMED_PROXY_CTORITN
248
249 //!Describes a proxy class that implements named
250 //!allocation syntax.
251 template
252 < class SegmentManager //segment manager to construct the object
253 , class T //type of object to build
254 , bool is_iterator //passing parameters are normal object or iterators?
255 >
256 class named_proxy
257 {
258 typedef typename SegmentManager::char_type char_type;
259 const char_type * mp_name;
260 SegmentManager * mp_mngr;
261 mutable std::size_t m_num;
262 const bool m_find;
263 const bool m_dothrow;
264
265 public:
266 named_proxy(SegmentManager *mngr, const char_type *name, bool find, bool dothrow)
267 : mp_name(name), mp_mngr(mngr), m_num(1)
268 , m_find(find), m_dothrow(dothrow)
269 {}
270
271 #define BOOST_INTERPROCESS_NAMED_PROXY_CALL_OPERATOR(N)\
272 \
273 BOOST_MOVE_TMPL_LT##N BOOST_MOVE_CLASS##N BOOST_MOVE_GT##N \
274 T *operator()( BOOST_MOVE_UREF##N ) const\
275 {\
276 typedef typename if_c<is_iterator \
277 , CtorIt##N<T BOOST_MOVE_I##N BOOST_MOVE_TARG##N> \
278 , CtorArg##N<T BOOST_MOVE_I##N BOOST_MOVE_TARG##N> \
279 >::type ctor_obj_t;\
280 ctor_obj_t ctor_obj = ctor_obj_t( BOOST_MOVE_FWD##N );\
281 return mp_mngr->template generic_construct<T>(mp_name, m_num, m_find, m_dothrow, ctor_obj);\
282 }\
283 //
284 BOOST_MOVE_ITERATE_0TO9(BOOST_INTERPROCESS_NAMED_PROXY_CALL_OPERATOR)
285 #undef BOOST_INTERPROCESS_NAMED_PROXY_CALL_OPERATOR
286
287 ////////////////////////////////////////////////////////////////////////
288 // What the macro should generate (n == 2)
289 ////////////////////////////////////////////////////////////////////////
290 //
291 // template <class P1, class P2>
292 // T *operator()(P1 &p1, P2 &p2) const
293 // {
294 // typedef CtorArg2
295 // <T, is_iterator, P1, P2>
296 // ctor_obj_t;
297 // ctor_obj_t ctor_obj(p1, p2);
298 //
299 // return mp_mngr->template generic_construct<T>
300 // (mp_name, m_num, m_find, m_dothrow, ctor_obj);
301 // }
302 //
303 //////////////////////////////////////////////////////////////////////////
304
305 //This operator allows --> named_new("Name")[3]; <-- syntax
306 const named_proxy &operator[](std::size_t num) const
307 { m_num *= num; return *this; }
308 };
309
310 #endif //#ifdef BOOST_INTERPROCESS_PERFECT_FORWARDING
311
312 }}} //namespace boost { namespace interprocess { namespace ipcdetail {
313
314 #include <boost/interprocess/detail/config_end.hpp>
315
316 #endif //#ifndef BOOST_INTERPROCESS_NAMED_PROXY_HPP