1 // Copyright Daniel Wallin 2006.
2 // Copyright Cromwell D. Enage 2017.
3 // Distributed under the Boost Software License, Version 1.0.
4 // (See accompanying file LICENSE_1_0.txt or copy at
5 // http://www.boost.org/LICENSE_1_0.txt)
6 
7 #ifndef BOOST_PARAMETER_AUX_PREPROCESSOR_IMPL_FORWARDING_OVERLOADS_HPP
8 #define BOOST_PARAMETER_AUX_PREPROCESSOR_IMPL_FORWARDING_OVERLOADS_HPP
9 
10 #include <boost/parameter/config.hpp>
11 
12 #if defined(BOOST_PARAMETER_HAS_PERFECT_FORWARDING)
13 
14 #include <boost/preprocessor/cat.hpp>
15 
16 // Expands to a forwarding parameter for a constructor or forwarding function.
17 #define BOOST_PARAMETER_FUNCTION_ARG_TYPE_Z(z, n, type_prefix)               \
18     BOOST_PP_CAT(type_prefix, n)&&
19 /**/
20 
21 #include <utility>
22 
23 // Expands to an argument passed from a forwarding function to the front-end
24 // implementation function, or from a constructor to its delegate.
25 #define BOOST_PARAMETER_FUNCTION_FORWARD_PARAM_Z(z, n, type_prefix)          \
26     ::std::forward<BOOST_PP_CAT(type_prefix, n)>(BOOST_PP_CAT(a, n))
27 /**/
28 
29 #include <boost/parameter/aux_/preprocessor/impl/parenthesized_type.hpp>
30 #include <boost/preprocessor/tuple/elem.hpp>
31 
32 // Expands to the default constructor, whose job is to pass an empty back to
33 // the delegate constructor of the base class.
34 #define BOOST_PARAMETER_CONSTRUCTOR_OVERLOAD_0_Z(z, n, data)                 \
35     inline BOOST_PP_TUPLE_ELEM(2, 0, data)()                                 \
36       : BOOST_PARAMETER_PARENTHESIZED_TYPE(BOOST_PP_TUPLE_ELEM(2, 1, data))( \
37             BOOST_PP_CAT(constructor_parameters, __LINE__)()()               \
38         )                                                                    \
39     {                                                                        \
40     }
41 /**/
42 
43 #include <boost/parameter/aux_/pp_impl/argument_pack.hpp>
44 #include <boost/parameter/aux_/preprocessor/impl/function_name.hpp>
45 #include <boost/preprocessor/control/expr_if.hpp>
46 
47 // Expands to a 0-arity forwarding function, whose job is to pass an empty
48 // pack to the front-end implementation function.
49 #define BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOAD_0_Z(z, n, data)            \
50     BOOST_PARAMETER_MEMBER_FUNCTION_STATIC(BOOST_PP_TUPLE_ELEM(4, 1, data))  \
51     inline BOOST_PARAMETER_FUNCTION_RESULT_NAME(                             \
52         BOOST_PP_TUPLE_ELEM(4, 1, data)                                      \
53       , BOOST_PP_TUPLE_ELEM(4, 3, data)                                      \
54     )<                                                                       \
55         ::boost::parameter::aux::argument_pack<                              \
56             BOOST_PARAMETER_FUNCTION_SPECIFICATION_NAME(                     \
57                 BOOST_PP_TUPLE_ELEM(4, 1, data)                              \
58               , BOOST_PP_TUPLE_ELEM(4, 3, data)                              \
59             )                                                                \
60         >::type                                                              \
61     >::type                                                                  \
62     BOOST_PARAMETER_MEMBER_FUNCTION_NAME(BOOST_PP_TUPLE_ELEM(3, 0, data))()  \
63     BOOST_PP_EXPR_IF(BOOST_PP_TUPLE_ELEM(4, 3, data), const)                 \
64     {                                                                        \
65         return BOOST_PP_EXPR_IF(BOOST_PP_TUPLE_ELEM(4, 2, data), this->)     \
66         BOOST_PARAMETER_FUNCTION_IMPL_NAME(                                  \
67             BOOST_PP_TUPLE_ELEM(4, 1, data)                                  \
68           , BOOST_PP_TUPLE_ELEM(4, 3, data)                                  \
69         )(                                                                   \
70             BOOST_PARAMETER_FUNCTION_SPECIFICATION_NAME(                     \
71                 BOOST_PP_TUPLE_ELEM(4, 1, data)                              \
72               , BOOST_PP_TUPLE_ELEM(4, 3, data)                              \
73             )()()                                                            \
74         );                                                                   \
75     }
76 /**/
77 
78 #include <boost/parameter/aux_/preprocessor/impl/function_forward_match.hpp>
79 #include <boost/preprocessor/repetition/enum.hpp>
80 #include <boost/preprocessor/repetition/enum_params.hpp>
81 #include <boost/preprocessor/repetition/enum_binary_params.hpp>
82 
83 // Expands to a forwarding function, whose job is to consolidate its arguments
84 // into a pack for the front-end implementation function to take in.
85 #define BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOAD_1_Z(z, n, data)            \
86     template <BOOST_PP_ENUM_PARAMS_Z(z, n, typename ParameterArgumentType)>  \
87     BOOST_PARAMETER_MEMBER_FUNCTION_STATIC(BOOST_PP_TUPLE_ELEM(4, 1, data))  \
88     inline typename BOOST_PARAMETER_FUNCTION_RESULT_NAME(                    \
89         BOOST_PP_TUPLE_ELEM(4, 1, data)                                      \
90       , BOOST_PP_TUPLE_ELEM(4, 3, data)                                      \
91     )<                                                                       \
92         typename ::boost::parameter::aux::argument_pack<                     \
93             BOOST_PARAMETER_FUNCTION_SPECIFICATION_NAME(                     \
94                 BOOST_PP_TUPLE_ELEM(4, 1, data)                              \
95               , BOOST_PP_TUPLE_ELEM(4, 3, data)                              \
96             )                                                                \
97           , BOOST_PP_CAT(BOOST_PP_ENUM_, z)(                                 \
98                 n                                                            \
99               , BOOST_PARAMETER_FUNCTION_ARG_TYPE_Z                          \
100               , ParameterArgumentType                                        \
101             )                                                                \
102         >::type                                                              \
103     >::type                                                                  \
104     BOOST_PARAMETER_MEMBER_FUNCTION_NAME(BOOST_PP_TUPLE_ELEM(4, 0, data))(   \
105         BOOST_PP_ENUM_BINARY_PARAMS_Z(z, n, ParameterArgumentType, && a)     \
106         BOOST_PARAMETER_FUNCTION_FORWARD_MATCH_Z(                            \
107             z                                                                \
108           , BOOST_PARAMETER_FUNCTION_SPECIFICATION_NAME(                     \
109                 BOOST_PP_TUPLE_ELEM(4, 1, data)                              \
110               , BOOST_PP_TUPLE_ELEM(4, 3, data)                              \
111             )                                                                \
112           , n                                                                \
113           , ParameterArgumentType                                            \
114         )                                                                    \
115     ) BOOST_PP_EXPR_IF(BOOST_PP_TUPLE_ELEM(4, 3, data), const)               \
116     {                                                                        \
117         return BOOST_PP_EXPR_IF(BOOST_PP_TUPLE_ELEM(4, 2, data), this->)     \
118         BOOST_PARAMETER_FUNCTION_IMPL_NAME(                                  \
119             BOOST_PP_TUPLE_ELEM(4, 1, data)                                  \
120           , BOOST_PP_TUPLE_ELEM(4, 3, data)                                  \
121         )(                                                                   \
122             BOOST_PARAMETER_FUNCTION_SPECIFICATION_NAME(                     \
123                 BOOST_PP_TUPLE_ELEM(4, 1, data)                              \
124               , BOOST_PP_TUPLE_ELEM(4, 3, data)                              \
125             )()(                                                             \
126                 BOOST_PP_CAT(BOOST_PP_ENUM_, z)(                             \
127                     n                                                        \
128                   , BOOST_PARAMETER_FUNCTION_FORWARD_PARAM_Z                 \
129                   , ParameterArgumentType                                    \
130                 )                                                            \
131             )                                                                \
132         );                                                                   \
133     }
134 /**/
135 
136 #include <boost/preprocessor/comparison/equal.hpp>
137 
138 // Expands to a constructor whose job is to consolidate its arguments into a
139 // pack for the delegate constructor of the base class to take in.
140 #define BOOST_PARAMETER_CONSTRUCTOR_OVERLOAD_1_Z(z, n, data)                 \
141     template <BOOST_PP_ENUM_PARAMS_Z(z, n, typename ParameterArgumentType)>  \
142     BOOST_PP_EXPR_IF(BOOST_PP_EQUAL(n, 1), explicit)                         \
143     inline BOOST_PP_TUPLE_ELEM(2, 0, data)(                                  \
144         BOOST_PP_ENUM_BINARY_PARAMS_Z(z, n, ParameterArgumentType, && a)     \
145         BOOST_PARAMETER_FUNCTION_FORWARD_MATCH_Z(                            \
146             z                                                                \
147           , BOOST_PP_CAT(constructor_parameters, __LINE__)                   \
148           , n                                                                \
149           , ParameterArgumentType                                            \
150         )                                                                    \
151     ) : BOOST_PARAMETER_PARENTHESIZED_TYPE(BOOST_PP_TUPLE_ELEM(2, 1, data))( \
152             BOOST_PP_CAT(constructor_parameters, __LINE__)()(                \
153                 BOOST_PP_CAT(BOOST_PP_ENUM_, z)(                             \
154                     n                                                        \
155                   , BOOST_PARAMETER_FUNCTION_FORWARD_PARAM_Z                 \
156                   , ParameterArgumentType                                    \
157                 )                                                            \
158             )                                                                \
159         )                                                                    \
160     {                                                                        \
161     }
162 /**/
163 
164 #include <boost/preprocessor/control/if.hpp>
165 
166 #define BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOAD_Z(z, n, data)              \
167     BOOST_PP_IF(                                                             \
168         n                                                                    \
169       , BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOAD_1_Z                        \
170       , BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOAD_0_Z                        \
171     )(z, n, data)
172 /**/
173 
174 #define BOOST_PARAMETER_CONSTRUCTOR_OVERLOAD_Z(z, n, data)                   \
175     BOOST_PP_IF(                                                             \
176         n                                                                    \
177       , BOOST_PARAMETER_CONSTRUCTOR_OVERLOAD_1_Z                             \
178       , BOOST_PARAMETER_CONSTRUCTOR_OVERLOAD_0_Z                             \
179     )(z, n, data)
180 /**/
181 
182 #include <boost/preprocessor/repetition/repeat_from_to.hpp>
183 
184 // Helper macro for BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOADS.
185 #define BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOADS_AUX(nm, impl, r, is_m, c) \
186     BOOST_PP_REPEAT_FROM_TO(                                                 \
187         BOOST_PP_TUPLE_ELEM(2, 0, r)                                         \
188       , BOOST_PP_TUPLE_ELEM(2, 1, r)                                         \
189       , BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOAD_Z                          \
190       , (                                                                    \
191             nm                                                               \
192           , impl                                                             \
193           , BOOST_PP_IF(                                                     \
194                 BOOST_PARAMETER_MEMBER_FUNCTION_IS_STATIC(nm)                \
195               , 0                                                            \
196               , is_m                                                         \
197             )                                                                \
198           , c                                                                \
199         )                                                                    \
200     )
201 /**/
202 
203 // Helper macro for BOOST_PARAMETER_CONSTRUCTOR_OVERLOADS.
204 #define BOOST_PARAMETER_CONSTRUCTOR_OVERLOADS_AUX(class_, base, range)       \
205     BOOST_PP_REPEAT_FROM_TO(                                                 \
206         BOOST_PP_TUPLE_ELEM(2, 0, range)                                     \
207       , BOOST_PP_TUPLE_ELEM(2, 1, range)                                     \
208       , BOOST_PARAMETER_CONSTRUCTOR_OVERLOAD_Z                               \
209       , (class_, base)                                                       \
210     )
211 /**/
212 
213 #include <boost/parameter/aux_/preprocessor/impl/arity_range.hpp>
214 
215 // Expands to the layer of forwarding functions for the function with the
216 // specified name, whose arguments determine the range of arities.
217 #define BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOADS(name, impl, a, is_m, c)   \
218     BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOADS_AUX(                          \
219         name, impl, BOOST_PARAMETER_ARITY_RANGE(a), is_m, c                  \
220     )
221 /**/
222 
223 // Expands to the layer of forwarding functions for the constructor in the
224 // specified class, whose arguments determine the range of arities.
225 #define BOOST_PARAMETER_CONSTRUCTOR_OVERLOADS(class_, base, args)            \
226     BOOST_PARAMETER_CONSTRUCTOR_OVERLOADS_AUX(                               \
227         class_, base, BOOST_PARAMETER_ARITY_RANGE(args)                      \
228     )
229 /**/
230 
231 #else   // !defined(BOOST_PARAMETER_HAS_PERFECT_FORWARDING)
232 
233 #include <boost/parameter/aux_/preprocessor/impl/parenthesized_type.hpp>
234 #include <boost/preprocessor/seq/seq.hpp>
235 #include <boost/preprocessor/tuple/elem.hpp>
236 #include <boost/preprocessor/cat.hpp>
237 
238 // Expands to the default constructor, whose job is to pass an empty argument
239 // pack back to the delegate constructor of the base class.
240 #define BOOST_PARAMETER_DEFAULT_CONSTRUCTOR(z, n, seq)                       \
241     inline                                                                   \
242     BOOST_PP_TUPLE_ELEM(2, 0, BOOST_PP_SEQ_HEAD(BOOST_PP_SEQ_TAIL(seq)))()   \
243       : BOOST_PARAMETER_PARENTHESIZED_TYPE(                                  \
244             BOOST_PP_TUPLE_ELEM(                                             \
245                 2, 1, BOOST_PP_SEQ_HEAD(BOOST_PP_SEQ_TAIL(seq))              \
246             )                                                                \
247         )(BOOST_PP_CAT(constructor_parameters, __LINE__)()())                \
248     {                                                                        \
249     }
250 /**/
251 
252 #include <boost/parameter/aux_/pp_impl/argument_pack.hpp>
253 #include <boost/parameter/aux_/preprocessor/impl/function_name.hpp>
254 #include <boost/preprocessor/control/expr_if.hpp>
255 
256 // Expands to a 0-arity forwarding function, whose job is to pass an empty
257 // argument pack to the front-end implementation function.
258 #define BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOAD_0_ARITY(z, n, seq)         \
259     BOOST_PARAMETER_MEMBER_FUNCTION_STATIC(                                  \
260         BOOST_PP_TUPLE_ELEM(                                                 \
261             4, 1, BOOST_PP_SEQ_HEAD(BOOST_PP_SEQ_TAIL(seq))                  \
262         )                                                                    \
263     )                                                                        \
264     inline BOOST_PARAMETER_FUNCTION_RESULT_NAME(                             \
265         BOOST_PP_TUPLE_ELEM(                                                 \
266             4, 1, BOOST_PP_SEQ_HEAD(BOOST_PP_SEQ_TAIL(seq))                  \
267         )                                                                    \
268       , BOOST_PP_TUPLE_ELEM(                                                 \
269             4, 3, BOOST_PP_SEQ_HEAD(BOOST_PP_SEQ_TAIL(seq))                  \
270         )                                                                    \
271     )<                                                                       \
272         ::boost::parameter::aux::argument_pack<                              \
273             BOOST_PARAMETER_FUNCTION_SPECIFICATION_NAME(                     \
274                 BOOST_PP_TUPLE_ELEM(                                         \
275                     4, 1, BOOST_PP_SEQ_HEAD(BOOST_PP_SEQ_TAIL(seq))          \
276                 )                                                            \
277               , BOOST_PP_TUPLE_ELEM(                                         \
278                     4, 3, BOOST_PP_SEQ_HEAD(BOOST_PP_SEQ_TAIL(seq))          \
279                 )                                                            \
280             )                                                                \
281         >::type                                                              \
282     >::type                                                                  \
283     BOOST_PARAMETER_MEMBER_FUNCTION_NAME(                                    \
284         BOOST_PP_TUPLE_ELEM(                                                 \
285             4, 0, BOOST_PP_SEQ_HEAD(BOOST_PP_SEQ_TAIL(seq))                  \
286         )                                                                    \
287     )() BOOST_PP_EXPR_IF(                                                    \
288         BOOST_PP_TUPLE_ELEM(                                                 \
289             4, 3, BOOST_PP_SEQ_HEAD(BOOST_PP_SEQ_TAIL(seq))                  \
290         )                                                                    \
291       , const                                                                \
292     )                                                                        \
293     {                                                                        \
294         return BOOST_PP_EXPR_IF(                                             \
295             BOOST_PP_TUPLE_ELEM(                                             \
296                 4, 2, BOOST_PP_SEQ_HEAD(BOOST_PP_SEQ_TAIL(seq))              \
297             )                                                                \
298           , this->                                                           \
299         ) BOOST_PARAMETER_FUNCTION_IMPL_NAME(                                \
300             BOOST_PP_TUPLE_ELEM(                                             \
301                 4, 1, BOOST_PP_SEQ_HEAD(BOOST_PP_SEQ_TAIL(seq))              \
302             )                                                                \
303           , BOOST_PP_TUPLE_ELEM(                                             \
304                 4, 3, BOOST_PP_SEQ_HEAD(BOOST_PP_SEQ_TAIL(seq))              \
305             )                                                                \
306         )(                                                                   \
307             BOOST_PARAMETER_FUNCTION_SPECIFICATION_NAME(                     \
308                 BOOST_PP_TUPLE_ELEM(                                         \
309                     4, 1, BOOST_PP_SEQ_HEAD(BOOST_PP_SEQ_TAIL(seq))          \
310                 )                                                            \
311               , BOOST_PP_TUPLE_ELEM(                                         \
312                     4, 3, BOOST_PP_SEQ_HEAD(BOOST_PP_SEQ_TAIL(seq))          \
313                 )                                                            \
314             )()()                                                            \
315         );                                                                   \
316     }
317 /**/
318 
319 #include <boost/parameter/aux_/preprocessor/binary_seq_to_args.hpp>
320 #include <boost/parameter/aux_/preprocessor/impl/function_forward_match.hpp>
321 #include <boost/preprocessor/comparison/equal.hpp>
322 #include <boost/preprocessor/repetition/enum_params.hpp>
323 #include <boost/preprocessor/seq/size.hpp>
324 
325 // Expands to a constructor whose job is to consolidate its arguments into a
326 // pack for the delegate constructor of the base class to take in.  Each
327 // element in BOOST_PP_SEQ_TAIL(seq) determines the const-ness of the
328 // corresponding argument.
329 #define BOOST_PARAMETER_CONSTRUCTOR_OVERLOAD_R(r, seq)                       \
330     template <                                                               \
331         BOOST_PP_ENUM_PARAMS(                                                \
332             BOOST_PP_SEQ_SIZE(BOOST_PP_SEQ_TAIL(seq))                        \
333           , typename ParameterArgumentType                                   \
334         )                                                                    \
335     >                                                                        \
336     BOOST_PP_EXPR_IF(                                                        \
337         BOOST_PP_EQUAL(BOOST_PP_SEQ_SIZE(BOOST_PP_SEQ_TAIL(seq)), 1)         \
338       , explicit                                                             \
339     )                                                                        \
340     inline BOOST_PP_TUPLE_ELEM(2, 0, BOOST_PP_SEQ_HEAD(seq))(                \
341         BOOST_PARAMETER_AUX_PP_BINARY_SEQ_TO_ARGS(                           \
342             BOOST_PP_SEQ_TAIL(seq), (ParameterArgumentType)(a)               \
343         )                                                                    \
344         BOOST_PARAMETER_FUNCTION_FORWARD_MATCH(                              \
345             BOOST_PP_CAT(constructor_parameters, __LINE__)                   \
346           , BOOST_PP_SEQ_SIZE(BOOST_PP_SEQ_TAIL(seq))                        \
347           , ParameterArgumentType                                            \
348         )                                                                    \
349     ) : BOOST_PARAMETER_PARENTHESIZED_TYPE(                                  \
350             BOOST_PP_TUPLE_ELEM(2, 1, BOOST_PP_SEQ_HEAD(seq))                \
351         )(                                                                   \
352             BOOST_PP_CAT(constructor_parameters, __LINE__)()(                \
353                 BOOST_PP_ENUM_PARAMS(                                        \
354                     BOOST_PP_SEQ_SIZE(BOOST_PP_SEQ_TAIL(seq)), a             \
355                 )                                                            \
356             )                                                                \
357         )                                                                    \
358     {                                                                        \
359     }
360 /**/
361 
362 // Expands to a forwarding function, whose job is to consolidate its arguments
363 // into a pack for the front-end implementation function to take in.  Each
364 // element in BOOST_PP_SEQ_TAIL(seq) determines the const-ness of the
365 // corresponding argument.
366 #define BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOAD_R(r, seq)                  \
367     template <                                                               \
368         BOOST_PP_ENUM_PARAMS(                                                \
369             BOOST_PP_SEQ_SIZE(BOOST_PP_SEQ_TAIL(seq))                        \
370           , typename ParameterArgumentType                                   \
371         )                                                                    \
372     >                                                                        \
373     BOOST_PARAMETER_MEMBER_FUNCTION_STATIC(                                  \
374         BOOST_PP_TUPLE_ELEM(4, 1, BOOST_PP_SEQ_HEAD(seq))                    \
375     )                                                                        \
376     inline typename BOOST_PARAMETER_FUNCTION_RESULT_NAME(                    \
377         BOOST_PP_TUPLE_ELEM(4, 1, BOOST_PP_SEQ_HEAD(seq))                    \
378       , BOOST_PP_TUPLE_ELEM(4, 3, BOOST_PP_SEQ_HEAD(seq))                    \
379     )<                                                                       \
380         typename ::boost::parameter::aux::argument_pack<                     \
381             BOOST_PARAMETER_FUNCTION_SPECIFICATION_NAME(                     \
382                 BOOST_PP_TUPLE_ELEM(4, 1, BOOST_PP_SEQ_HEAD(seq))            \
383               , BOOST_PP_TUPLE_ELEM(4, 3, BOOST_PP_SEQ_HEAD(seq))            \
384             )                                                                \
385           , BOOST_PARAMETER_AUX_PP_BINARY_SEQ_TO_ARGS(                       \
386                 BOOST_PP_SEQ_TAIL(seq), (ParameterArgumentType)              \
387             )                                                                \
388         >::type                                                              \
389     >::type                                                                  \
390     BOOST_PARAMETER_MEMBER_FUNCTION_NAME(                                    \
391         BOOST_PP_TUPLE_ELEM(4, 0, BOOST_PP_SEQ_HEAD(seq))                    \
392     )(                                                                       \
393         BOOST_PARAMETER_AUX_PP_BINARY_SEQ_TO_ARGS(                           \
394             BOOST_PP_SEQ_TAIL(seq), (ParameterArgumentType)(a)               \
395         )                                                                    \
396         BOOST_PARAMETER_FUNCTION_FORWARD_MATCH(                              \
397             BOOST_PARAMETER_FUNCTION_SPECIFICATION_NAME(                     \
398                 BOOST_PP_TUPLE_ELEM(4, 1, BOOST_PP_SEQ_HEAD(seq))            \
399               , BOOST_PP_TUPLE_ELEM(4, 3, BOOST_PP_SEQ_HEAD(seq))            \
400             )                                                                \
401           , BOOST_PP_SEQ_SIZE(BOOST_PP_SEQ_TAIL(seq))                        \
402           , ParameterArgumentType                                            \
403         )                                                                    \
404     ) BOOST_PP_EXPR_IF(                                                      \
405         BOOST_PP_TUPLE_ELEM(4, 3, BOOST_PP_SEQ_HEAD(seq)), const             \
406     )                                                                        \
407     {                                                                        \
408         return BOOST_PP_EXPR_IF(                                             \
409             BOOST_PP_TUPLE_ELEM(4, 2, BOOST_PP_SEQ_HEAD(seq))                \
410           , this->                                                           \
411         ) BOOST_PARAMETER_FUNCTION_IMPL_NAME(                                \
412             BOOST_PP_TUPLE_ELEM(4, 1, BOOST_PP_SEQ_HEAD(seq))                \
413           , BOOST_PP_TUPLE_ELEM(4, 3, BOOST_PP_SEQ_HEAD(seq))                \
414         )(                                                                   \
415             BOOST_PARAMETER_FUNCTION_SPECIFICATION_NAME(                     \
416                 BOOST_PP_TUPLE_ELEM(4, 1, BOOST_PP_SEQ_HEAD(seq))            \
417               , BOOST_PP_TUPLE_ELEM(4, 3, BOOST_PP_SEQ_HEAD(seq))            \
418             )()(                                                             \
419                 BOOST_PP_ENUM_PARAMS(                                        \
420                     BOOST_PP_SEQ_SIZE(BOOST_PP_SEQ_TAIL(seq)), a             \
421                 )                                                            \
422             )                                                                \
423         );                                                                   \
424     }
425 /**/
426 
427 #include <boost/parameter/aux_/preprocessor/binary_seq_for_each.hpp>
428 #include <boost/preprocessor/control/if.hpp>
429 
430 // Expands to all constructors that take in n arguments.  Enables
431 // BOOST_PARAMETER_CONSTRUCTOR_OVERLOADS_AUX to use
432 // BOOST_PARAMETER_CONSTRUCTOR_OVERLOAD_Z within BOOST_PP_REPEAT_FROM_TO.
433 #define BOOST_PARAMETER_CONSTRUCTOR_OVERLOAD_Z(z, n, data)                   \
434     BOOST_PP_IF(                                                             \
435         n                                                                    \
436       , BOOST_PARAMETER_AUX_PP_BINARY_SEQ_FOR_EACH_Z                         \
437       , BOOST_PARAMETER_DEFAULT_CONSTRUCTOR                                  \
438     )(z, n, (BOOST_PARAMETER_CONSTRUCTOR_OVERLOAD_R)(data))
439 /**/
440 
441 // Expands to all forwarding functions that take in n arguments.  Enables
442 // BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOADS_AUX to use
443 // BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOAD_Z within BOOST_PP_REPEAT_FROM_TO.
444 #define BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOAD_Z(z, n, data)              \
445     BOOST_PP_IF(                                                             \
446         n                                                                    \
447       , BOOST_PARAMETER_AUX_PP_BINARY_SEQ_FOR_EACH_Z                         \
448       , BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOAD_0_ARITY                    \
449     )(z, n, (BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOAD_R)(data))
450 /**/
451 
452 #include <boost/preprocessor/repetition/repeat_from_to.hpp>
453 
454 // Helper macro for BOOST_PARAMETER_CONSTRUCTOR_OVERLOADS.
455 #define BOOST_PARAMETER_CONSTRUCTOR_OVERLOADS_AUX(class_, base, range)       \
456     BOOST_PP_REPEAT_FROM_TO(                                                 \
457         BOOST_PP_TUPLE_ELEM(2, 0, range)                                     \
458       , BOOST_PP_TUPLE_ELEM(2, 1, range)                                     \
459       , BOOST_PARAMETER_CONSTRUCTOR_OVERLOAD_Z                               \
460       , (class_, base)                                                       \
461     )
462 /**/
463 
464 // Helper macro for BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOADS.
465 #define BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOADS_AUX(nm, impl, r, is_m, c) \
466     BOOST_PP_REPEAT_FROM_TO(                                                 \
467         BOOST_PP_TUPLE_ELEM(2, 0, r)                                         \
468       , BOOST_PP_TUPLE_ELEM(2, 1, r)                                         \
469       , BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOAD_Z                          \
470       , (                                                                    \
471             nm                                                               \
472           , impl                                                             \
473           , BOOST_PP_IF(                                                     \
474                 BOOST_PARAMETER_MEMBER_FUNCTION_IS_STATIC(impl)              \
475               , 0                                                            \
476               , is_m                                                         \
477             )                                                                \
478           , c                                                                \
479         )                                                                    \
480     )
481 /**/
482 
483 #include <boost/parameter/aux_/preprocessor/impl/arity_range.hpp>
484 
485 // Expands to the layer of forwarding functions for the constructor in the
486 // specified class, whose arguments determine the range of arities.
487 #define BOOST_PARAMETER_CONSTRUCTOR_OVERLOADS(class_, base, args)            \
488     BOOST_PARAMETER_CONSTRUCTOR_OVERLOADS_AUX(                               \
489         class_                                                               \
490       , base                                                                 \
491       , BOOST_PARAMETER_ARITY_RANGE(args)                                    \
492     )
493 /**/
494 
495 // Expands to the layer of forwarding functions for the function with the
496 // specified name, whose arguments determine the range of arities.
497 #define BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOADS(name, impl, a, is_m, c)   \
498     BOOST_PARAMETER_FUNCTION_FORWARD_OVERLOADS_AUX(                          \
499         name                                                                 \
500       , impl                                                                 \
501       , BOOST_PARAMETER_ARITY_RANGE(a)                                       \
502       , is_m                                                                 \
503       , c                                                                    \
504     )
505 /**/
506 
507 #endif  // BOOST_PARAMETER_HAS_PERFECT_FORWARDING
508 #endif  // include guard
509 
510