1 | ////////////////////////////////////////////////////////////////////////////// |
2 | // |
3 | // (C) Copyright Ion Gaztanaga 2014-2014. 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/container for documentation. |
8 | // |
9 | ////////////////////////////////////////////////////////////////////////////// |
10 | |
11 | #ifndef BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_CALLABLE_WITH_HPP |
12 | #define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_CALLABLE_WITH_HPP |
13 | |
14 | #ifndef BOOST_CONFIG_HPP |
15 | # include <boost/config.hpp> |
16 | #endif |
17 | |
18 | //In case no decltype and no variadics, mark that we don't support 0 arg calls due to |
19 | //compiler ICE in GCC 3.4/4.0/4.1 and, wrong SFINAE for GCC 4.2/4.3/MSVC10/MSVC11 |
20 | #if defined(BOOST_NO_CXX11_DECLTYPE) && defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) |
21 | # if defined(BOOST_GCC) && (BOOST_GCC < 40400) |
22 | # define BOOST_INTRUSIVE_DETAIL_HAS_MEMBER_FUNCTION_CALLABLE_WITH_0_ARGS_UNSUPPORTED |
23 | # elif defined(BOOST_INTEL) && (BOOST_INTEL < 1200) |
24 | # define BOOST_INTRUSIVE_DETAIL_HAS_MEMBER_FUNCTION_CALLABLE_WITH_0_ARGS_UNSUPPORTED |
25 | # elif defined(BOOST_MSVC) && (BOOST_MSVC < 1800) |
26 | # define BOOST_INTRUSIVE_DETAIL_HAS_MEMBER_FUNCTION_CALLABLE_WITH_0_ARGS_UNSUPPORTED |
27 | # endif |
28 | #endif //#if defined(BOOST_NO_CXX11_DECLTYPE) && defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) |
29 | |
30 | #include <cstddef> |
31 | #include <boost/move/utility_core.hpp> |
32 | #include <boost/move/detail/fwd_macros.hpp> |
33 | |
34 | namespace boost_intrusive_hmfcw { |
35 | |
36 | typedef char yes_type; |
37 | struct no_type{ char dummy[2]; }; |
38 | |
39 | struct dont_care |
40 | { |
41 | dont_care(...); |
42 | }; |
43 | |
44 | #if defined(BOOST_NO_CXX11_DECLTYPE) |
45 | |
46 | #if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) |
47 | |
48 | template<class T> |
49 | struct make_dontcare |
50 | { |
51 | typedef dont_care type; |
52 | }; |
53 | |
54 | #endif |
55 | |
56 | struct private_type |
57 | { |
58 | static private_type p; |
59 | private_type const &operator,(int) const; |
60 | }; |
61 | |
62 | template<typename T> |
63 | no_type is_private_type(T const &); |
64 | yes_type is_private_type(private_type const &); |
65 | |
66 | #endif //#if defined(BOOST_NO_CXX11_DECLTYPE) |
67 | |
68 | #if defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) || defined(BOOST_NO_CXX11_DECLTYPE) |
69 | |
70 | template<typename T> struct remove_cv { typedef T type; }; |
71 | template<typename T> struct remove_cv<const T> { typedef T type; }; |
72 | template<typename T> struct remove_cv<const volatile T> { typedef T type; }; |
73 | template<typename T> struct remove_cv<volatile T> { typedef T type; }; |
74 | |
75 | #endif |
76 | |
77 | } //namespace boost_intrusive_hmfcw { |
78 | |
79 | #endif //BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_CALLABLE_WITH_HPP |
80 | |
81 | #ifndef BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME |
82 | #error "You MUST define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME before including this header!" |
83 | #endif |
84 | |
85 | #ifndef BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MIN |
86 | #error "You MUST define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MIN before including this header!" |
87 | #endif |
88 | |
89 | #ifndef BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MAX |
90 | #error "You MUST define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MAX before including this header!" |
91 | #endif |
92 | |
93 | #if BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MAX < BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MIN |
94 | #error "BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MAX value MUST be greater or equal than BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MIN!" |
95 | #endif |
96 | |
97 | #if BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MAX == 0 |
98 | #define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_COMMA_IF |
99 | #else |
100 | #define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_COMMA_IF , |
101 | #endif |
102 | |
103 | #ifndef BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_BEG |
104 | #error "BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_BEG not defined!" |
105 | #endif |
106 | |
107 | #ifndef BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_END |
108 | #error "BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_END not defined!" |
109 | #endif |
110 | |
111 | BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_BEG |
112 | |
113 | #if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) && !defined(BOOST_NO_CXX11_DECLTYPE) |
114 | //With decltype and variadic templaes, things are pretty easy |
115 | template<typename Fun, class ...Args> |
116 | struct BOOST_MOVE_CAT(has_member_function_callable_with_,BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME) |
117 | { |
118 | template<class U> |
119 | static decltype(boost::move_detail::declval<U>(). |
120 | BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME(::boost::move_detail::declval<Args>()...) |
121 | , boost_intrusive_hmfcw::yes_type()) Test(U* f); |
122 | template<class U> |
123 | static boost_intrusive_hmfcw::no_type Test(...); |
124 | static const bool value = sizeof(Test<Fun>((Fun*)0)) == sizeof(boost_intrusive_hmfcw::yes_type); |
125 | }; |
126 | |
127 | #else //defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) || defined(BOOST_NO_CXX11_DECLTYPE) |
128 | |
129 | ///////////////////////////////////////////////////////// |
130 | ///////////////////////////////////////////////////////// |
131 | // |
132 | // has_member_function_callable_with_impl_XXX |
133 | // declaration, special case and 0 arg specializaton |
134 | // |
135 | ///////////////////////////////////////////////////////// |
136 | |
137 | template <typename Type> |
138 | class BOOST_MOVE_CAT(has_member_function_named_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME) |
139 | { |
140 | struct BaseMixin |
141 | { |
142 | void BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME() |
143 | {} //Some compilers require the definition or linker errors happen |
144 | }; |
145 | |
146 | struct Base |
147 | : public boost_intrusive_hmfcw::remove_cv<Type>::type, public BaseMixin |
148 | { //Declare the unneeded default constructor as some old compilers wrongly require it with is_convertible |
149 | Base(){} |
150 | }; |
151 | template <typename T, T t> class Helper{}; |
152 | |
153 | template <typename U> |
154 | static boost_intrusive_hmfcw::no_type deduce |
155 | (U*, Helper<void (BaseMixin::*)(), &U::BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME>* = 0); |
156 | static boost_intrusive_hmfcw::yes_type deduce(...); |
157 | |
158 | public: |
159 | static const bool value = sizeof(boost_intrusive_hmfcw::yes_type) == sizeof(deduce((Base*)0)); |
160 | }; |
161 | |
162 | #if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) |
163 | ///////////////////////////////////////////////////////// |
164 | ///////////////////////////////////////////////////////// |
165 | // |
166 | // has_member_function_callable_with_impl_XXX for 1 to N arguments |
167 | // |
168 | ///////////////////////////////////////////////////////// |
169 | ///////////////////////////////////////////////////////// |
170 | |
171 | //defined(BOOST_NO_CXX11_DECLTYPE) must be true |
172 | template<class Fun> |
173 | struct FunWrapTmpl : Fun |
174 | { |
175 | using Fun::BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME; |
176 | FunWrapTmpl(); |
177 | template<class ...DontCares> |
178 | boost_intrusive_hmfcw::private_type BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME(DontCares...) const; |
179 | }; |
180 | |
181 | template<typename Fun, bool HasFunc, class ...Args> |
182 | struct BOOST_MOVE_CAT(has_member_function_callable_with_impl_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME); |
183 | |
184 | //No BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME member specialization |
185 | template<typename Fun, class ...Args> |
186 | struct BOOST_MOVE_CAT(has_member_function_callable_with_impl_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME) |
187 | <Fun, false, Args...> |
188 | { |
189 | static const bool value = false; |
190 | }; |
191 | |
192 | template<typename Fun, class ...Args> |
193 | struct BOOST_MOVE_CAT(has_member_function_callable_with_impl_,BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME)<Fun, true, Args...> |
194 | { |
195 | static bool const value = (sizeof(boost_intrusive_hmfcw::no_type) == sizeof(boost_intrusive_hmfcw::is_private_type |
196 | ( (::boost::move_detail::declval |
197 | < FunWrapTmpl<Fun> >(). |
198 | BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME(::boost::move_detail::declval<Args>()...), 0) ) |
199 | ) |
200 | ); |
201 | }; |
202 | |
203 | template<typename Fun, class ...Args> |
204 | struct BOOST_MOVE_CAT(has_member_function_callable_with_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME) |
205 | : public BOOST_MOVE_CAT(has_member_function_callable_with_impl_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME) |
206 | <Fun |
207 | , BOOST_MOVE_CAT(has_member_function_named_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME)<Fun>::value |
208 | , Args...> |
209 | {}; |
210 | #else //defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) |
211 | |
212 | ///////////////////////////////////////////////////////// |
213 | ///////////////////////////////////////////////////////// |
214 | // |
215 | // has_member_function_callable_with_impl_XXX specializations |
216 | // |
217 | ///////////////////////////////////////////////////////// |
218 | |
219 | template<typename Fun, bool HasFunc BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_COMMA_IF BOOST_MOVE_CAT(BOOST_MOVE_CLASSDFLT,BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MAX)> |
220 | struct BOOST_MOVE_CAT(has_member_function_callable_with_impl_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME); |
221 | |
222 | //No BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME member specialization |
223 | template<typename Fun BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_COMMA_IF BOOST_MOVE_CAT(BOOST_MOVE_CLASS,BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MAX)> |
224 | struct BOOST_MOVE_CAT(has_member_function_callable_with_impl_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME) |
225 | <Fun, false BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_COMMA_IF BOOST_MOVE_CAT(BOOST_MOVE_TARG,BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MAX)> |
226 | { |
227 | static const bool value = false; |
228 | }; |
229 | |
230 | #if BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MIN == 0 |
231 | //0 arg specialization when BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME is present |
232 | #if !defined(BOOST_NO_CXX11_DECLTYPE) |
233 | |
234 | template<typename Fun> |
235 | struct BOOST_MOVE_CAT(has_member_function_callable_with_impl_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME)<Fun, true> |
236 | { |
237 | template<class U> |
238 | static decltype(boost::move_detail::declval<U>().BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME() |
239 | , boost_intrusive_hmfcw::yes_type()) Test(U* f); |
240 | |
241 | template<class U> |
242 | static boost_intrusive_hmfcw::no_type Test(...); |
243 | static const bool value = sizeof(Test<Fun>((Fun*)0)) == sizeof(boost_intrusive_hmfcw::yes_type); |
244 | }; |
245 | |
246 | #else //defined(BOOST_NO_CXX11_DECLTYPE) |
247 | |
248 | #if !defined(BOOST_INTRUSIVE_DETAIL_HAS_MEMBER_FUNCTION_CALLABLE_WITH_0_ARGS_UNSUPPORTED) |
249 | |
250 | template<class F, std::size_t N = sizeof(boost::move_detail::declval<F>().BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME(), 0)> |
251 | struct BOOST_MOVE_CAT(zeroarg_checker_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME) |
252 | { boost_intrusive_hmfcw::yes_type dummy[N ? 1 : 2]; }; |
253 | |
254 | template<typename Fun> |
255 | struct BOOST_MOVE_CAT(has_member_function_callable_with_impl_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME)<Fun, true> |
256 | { |
257 | template<class U> static BOOST_MOVE_CAT(zeroarg_checker_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME)<U> |
258 | Test(BOOST_MOVE_CAT(zeroarg_checker_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME)<U>*); |
259 | template<class U> static boost_intrusive_hmfcw::no_type Test(...); |
260 | static const bool value = sizeof(Test< Fun >(0)) == sizeof(boost_intrusive_hmfcw::yes_type); |
261 | }; |
262 | |
263 | #else //defined(BOOST_INTRUSIVE_DETAIL_HAS_MEMBER_FUNCTION_CALLABLE_WITH_0_ARGS_UNSUPPORTED) |
264 | |
265 | template<typename Fun> |
266 | struct BOOST_MOVE_CAT(has_member_function_callable_with_impl_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME)<Fun, true> |
267 | { //Some compilers gives ICE when instantiating the 0 arg version so it is not supported. |
268 | static const bool value = true; |
269 | }; |
270 | |
271 | #endif//!defined(BOOST_INTRUSIVE_DETAIL_HAS_MEMBER_FUNCTION_CALLABLE_WITH_0_ARGS_UNSUPPORTED) |
272 | #endif //!defined(BOOST_NO_CXX11_DECLTYPE) |
273 | #endif //#if BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MIN == 0 |
274 | |
275 | #if BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MAX > 0 |
276 | //1 to N arg specialization when BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME is present |
277 | //Declare some unneeded default constructor as some old compilers wrongly require it with is_convertible |
278 | #if defined(BOOST_NO_CXX11_DECLTYPE) |
279 | #define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_ITERATION(N)\ |
280 | \ |
281 | template<class Fun>\ |
282 | struct BOOST_MOVE_CAT(FunWrap##N, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME)\ |
283 | : Fun\ |
284 | {\ |
285 | using Fun::BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME;\ |
286 | BOOST_MOVE_CAT(FunWrap##N, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME)();\ |
287 | boost_intrusive_hmfcw::private_type BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME\ |
288 | (BOOST_MOVE_REPEAT##N(boost_intrusive_hmfcw::dont_care)) const;\ |
289 | };\ |
290 | \ |
291 | template<typename Fun, BOOST_MOVE_CLASS##N>\ |
292 | struct BOOST_MOVE_CAT(has_member_function_callable_with_impl_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME)<Fun, true, BOOST_MOVE_TARG##N>\ |
293 | {\ |
294 | static bool const value = (sizeof(boost_intrusive_hmfcw::no_type) == sizeof(boost_intrusive_hmfcw::is_private_type\ |
295 | ( (::boost::move_detail::declval\ |
296 | < BOOST_MOVE_CAT(FunWrap##N, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME)<Fun> >().\ |
297 | BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME(BOOST_MOVE_DECLVAL##N), 0) )\ |
298 | )\ |
299 | );\ |
300 | };\ |
301 | // |
302 | #else |
303 | #define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_ITERATION(N)\ |
304 | template<typename Fun, BOOST_MOVE_CLASS##N>\ |
305 | struct BOOST_MOVE_CAT(has_member_function_callable_with_impl_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME)\ |
306 | <Fun, true, BOOST_MOVE_TARG##N>\ |
307 | {\ |
308 | template<class U>\ |
309 | static decltype(boost::move_detail::declval<U>().\ |
310 | BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME(BOOST_MOVE_DECLVAL##N)\ |
311 | , boost_intrusive_hmfcw::yes_type()) Test(U* f);\ |
312 | template<class U>\ |
313 | static boost_intrusive_hmfcw::no_type Test(...);\ |
314 | static const bool value = sizeof(Test<Fun>((Fun*)0)) == sizeof(boost_intrusive_hmfcw::yes_type);\ |
315 | };\ |
316 | // |
317 | #endif |
318 | //////////////////////////////////// |
319 | // Build and invoke BOOST_MOVE_ITERATE_NTOM macrofunction, note that N has to be at least 1 |
320 | //////////////////////////////////// |
321 | #if BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MIN == 0 |
322 | #define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_ITERATE_MIN 1 |
323 | #else |
324 | #define BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_ITERATE_MIN BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MIN |
325 | #endif |
326 | BOOST_MOVE_CAT |
327 | (BOOST_MOVE_CAT(BOOST_MOVE_CAT(BOOST_MOVE_ITERATE_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_ITERATE_MIN), TO) |
328 | ,BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MAX) |
329 | (BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_ITERATION) |
330 | #undef BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_ITERATION |
331 | #undef BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_ITERATE_MIN |
332 | //////////////////////////////////// |
333 | // End of BOOST_MOVE_ITERATE_NTOM |
334 | //////////////////////////////////// |
335 | #endif //BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MAX > 0 |
336 | |
337 | ///////////////////////////////////////////////////////// |
338 | ///////////////////////////////////////////////////////// |
339 | // |
340 | // has_member_function_callable_with_FUNC |
341 | // |
342 | ///////////////////////////////////////////////////////// |
343 | ///////////////////////////////////////////////////////// |
344 | |
345 | //Otherwise use the preprocessor |
346 | template<typename Fun BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_COMMA_IF BOOST_MOVE_CAT(BOOST_MOVE_CLASSDFLT,BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MAX)> |
347 | struct BOOST_MOVE_CAT(has_member_function_callable_with_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME) |
348 | : public BOOST_MOVE_CAT(has_member_function_callable_with_impl_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME) |
349 | <Fun |
350 | , BOOST_MOVE_CAT(has_member_function_named_, BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME)<Fun>::value |
351 | BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_COMMA_IF BOOST_MOVE_CAT(BOOST_MOVE_TARG,BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MAX)> |
352 | {}; |
353 | #endif //defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) |
354 | #endif |
355 | |
356 | BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_END |
357 | |
358 | //Undef local macros |
359 | #undef BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_COMMA_IF |
360 | |
361 | //Undef user defined macros |
362 | #undef BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_FUNCNAME |
363 | #undef BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MIN |
364 | #undef BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_MAX |
365 | #undef BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_BEG |
366 | #undef BOOST_INTRUSIVE_HAS_MEMBER_FUNCTION_CALLABLE_WITH_NS_END |
367 | |