1 | ///////////////////////////////////////////////////////////////////////////// |
2 | // |
3 | // (C) Copyright Joaquin M Lopez Munoz 2006-2013 |
4 | // (C) Copyright Ion Gaztanaga 2014-2014 |
5 | // |
6 | // Distributed under the Boost Software License, Version 1.0. |
7 | // (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/libs/intrusive for documentation. |
11 | // |
12 | ///////////////////////////////////////////////////////////////////////////// |
13 | |
14 | #ifndef BOOST_INTRUSIVE_DETAIL_EBO_HOLDER_HPP |
15 | #define BOOST_INTRUSIVE_DETAIL_EBO_HOLDER_HPP |
16 | |
17 | #ifndef BOOST_CONFIG_HPP |
18 | # include <boost/config.hpp> |
19 | #endif |
20 | |
21 | #if defined(BOOST_HAS_PRAGMA_ONCE) |
22 | # pragma once |
23 | #endif |
24 | |
25 | namespace boost { |
26 | namespace intrusive { |
27 | namespace detail { |
28 | |
29 | #if defined(BOOST_MSVC) || defined(__BORLANDC_) |
30 | #define BOOST_INTRUSIVE_TT_DECL __cdecl |
31 | #else |
32 | #define BOOST_INTRUSIVE_TT_DECL |
33 | #endif |
34 | |
35 | #if defined(_MSC_EXTENSIONS) && !defined(__BORLAND__) && !defined(_WIN64) && !defined(_M_ARM) && !defined(UNDER_CE) |
36 | #define BOOST_INTRUSIVE_TT_TEST_MSC_FUNC_SIGS |
37 | #endif |
38 | |
39 | template <typename T> |
40 | struct is_unary_or_binary_function_impl |
41 | { static const bool value = false; }; |
42 | |
43 | // see boost ticket #4094 |
44 | // avoid duplicate definitions of is_unary_or_binary_function_impl |
45 | #ifndef BOOST_INTRUSIVE_TT_TEST_MSC_FUNC_SIGS |
46 | |
47 | template <typename R> |
48 | struct is_unary_or_binary_function_impl<R (*)()> |
49 | { static const bool value = true; }; |
50 | |
51 | template <typename R> |
52 | struct is_unary_or_binary_function_impl<R (*)(...)> |
53 | { static const bool value = true; }; |
54 | |
55 | #else // BOOST_INTRUSIVE_TT_TEST_MSC_FUNC_SIGS |
56 | |
57 | template <typename R> |
58 | struct is_unary_or_binary_function_impl<R (__stdcall*)()> |
59 | { static const bool value = true; }; |
60 | |
61 | #ifndef _MANAGED |
62 | |
63 | template <typename R> |
64 | struct is_unary_or_binary_function_impl<R (__fastcall*)()> |
65 | { static const bool value = true; }; |
66 | |
67 | #endif |
68 | |
69 | template <typename R> |
70 | struct is_unary_or_binary_function_impl<R (__cdecl*)()> |
71 | { static const bool value = true; }; |
72 | |
73 | template <typename R> |
74 | struct is_unary_or_binary_function_impl<R (__cdecl*)(...)> |
75 | { static const bool value = true; }; |
76 | |
77 | #endif |
78 | |
79 | // see boost ticket #4094 |
80 | // avoid duplicate definitions of is_unary_or_binary_function_impl |
81 | #ifndef BOOST_INTRUSIVE_TT_TEST_MSC_FUNC_SIGS |
82 | |
83 | template <typename R, class T0> |
84 | struct is_unary_or_binary_function_impl<R (*)(T0)> |
85 | { static const bool value = true; }; |
86 | |
87 | template <typename R, class T0> |
88 | struct is_unary_or_binary_function_impl<R (*)(T0...)> |
89 | { static const bool value = true; }; |
90 | |
91 | #else // BOOST_INTRUSIVE_TT_TEST_MSC_FUNC_SIGS |
92 | |
93 | template <typename R, class T0> |
94 | struct is_unary_or_binary_function_impl<R (__stdcall*)(T0)> |
95 | { static const bool value = true; }; |
96 | |
97 | #ifndef _MANAGED |
98 | |
99 | template <typename R, class T0> |
100 | struct is_unary_or_binary_function_impl<R (__fastcall*)(T0)> |
101 | { static const bool value = true; }; |
102 | |
103 | #endif |
104 | |
105 | template <typename R, class T0> |
106 | struct is_unary_or_binary_function_impl<R (__cdecl*)(T0)> |
107 | { static const bool value = true; }; |
108 | |
109 | template <typename R, class T0> |
110 | struct is_unary_or_binary_function_impl<R (__cdecl*)(T0...)> |
111 | { static const bool value = true; }; |
112 | |
113 | #endif |
114 | |
115 | // see boost ticket #4094 |
116 | // avoid duplicate definitions of is_unary_or_binary_function_impl |
117 | #ifndef BOOST_INTRUSIVE_TT_TEST_MSC_FUNC_SIGS |
118 | |
119 | template <typename R, class T0, class T1> |
120 | struct is_unary_or_binary_function_impl<R (*)(T0, T1)> |
121 | { static const bool value = true; }; |
122 | |
123 | template <typename R, class T0, class T1> |
124 | struct is_unary_or_binary_function_impl<R (*)(T0, T1...)> |
125 | { static const bool value = true; }; |
126 | |
127 | #else // BOOST_INTRUSIVE_TT_TEST_MSC_FUNC_SIGS |
128 | |
129 | template <typename R, class T0, class T1> |
130 | struct is_unary_or_binary_function_impl<R (__stdcall*)(T0, T1)> |
131 | { static const bool value = true; }; |
132 | |
133 | #ifndef _MANAGED |
134 | |
135 | template <typename R, class T0, class T1> |
136 | struct is_unary_or_binary_function_impl<R (__fastcall*)(T0, T1)> |
137 | { static const bool value = true; }; |
138 | |
139 | #endif |
140 | |
141 | template <typename R, class T0, class T1> |
142 | struct is_unary_or_binary_function_impl<R (__cdecl*)(T0, T1)> |
143 | { static const bool value = true; }; |
144 | |
145 | template <typename R, class T0, class T1> |
146 | struct is_unary_or_binary_function_impl<R (__cdecl*)(T0, T1...)> |
147 | { static const bool value = true; }; |
148 | #endif |
149 | |
150 | template <typename T> |
151 | struct is_unary_or_binary_function_impl<T&> |
152 | { static const bool value = false; }; |
153 | |
154 | template<typename T> |
155 | struct is_unary_or_binary_function : is_unary_or_binary_function_impl<T> |
156 | {}; |
157 | |
158 | template<typename T, bool IsEmpty = true> |
159 | class ebo_functor_holder_impl |
160 | { |
161 | public: |
162 | ebo_functor_holder_impl() |
163 | {} |
164 | ebo_functor_holder_impl(const T& t) |
165 | : t_(t) |
166 | {} |
167 | template<class Arg1, class Arg2> |
168 | ebo_functor_holder_impl(const Arg1& arg1, const Arg2& arg2) |
169 | : t_(arg1, arg2) |
170 | {} |
171 | |
172 | T& get(){return t_;} |
173 | const T& get()const{return t_;} |
174 | |
175 | private: |
176 | T t_; |
177 | }; |
178 | |
179 | template<typename T> |
180 | class ebo_functor_holder_impl<T, false> |
181 | : public T |
182 | { |
183 | public: |
184 | ebo_functor_holder_impl() |
185 | {} |
186 | explicit ebo_functor_holder_impl(const T& t) |
187 | : T(t) |
188 | {} |
189 | template<class Arg1, class Arg2> |
190 | ebo_functor_holder_impl(const Arg1& arg1, const Arg2& arg2) |
191 | : T(arg1, arg2) |
192 | {} |
193 | |
194 | T& get(){return *this;} |
195 | const T& get()const{return *this;} |
196 | }; |
197 | |
198 | template<typename T> |
199 | class ebo_functor_holder |
200 | : public ebo_functor_holder_impl<T, is_unary_or_binary_function<T>::value> |
201 | { |
202 | private: |
203 | typedef ebo_functor_holder_impl<T, is_unary_or_binary_function<T>::value> super; |
204 | |
205 | public: |
206 | ebo_functor_holder(){} |
207 | explicit ebo_functor_holder(const T& t) |
208 | : super(t) |
209 | {} |
210 | |
211 | template<class Arg1, class Arg2> |
212 | ebo_functor_holder(const Arg1& arg1, const Arg2& arg2) |
213 | : super(arg1, arg2) |
214 | {} |
215 | |
216 | ebo_functor_holder& operator=(const ebo_functor_holder& x) |
217 | { |
218 | this->get()=x.get(); |
219 | return *this; |
220 | } |
221 | }; |
222 | |
223 | |
224 | } //namespace detail { |
225 | } //namespace intrusive { |
226 | } //namespace boost { |
227 | |
228 | #endif //#ifndef BOOST_INTRUSIVE_DETAIL_EBO_HOLDER_HPP |
229 | |