]> git.lyx.org Git - lyx.git/blob - 3rdparty/boost/boost/parameter/parameters.hpp
Update to boost 1.72
[lyx.git] / 3rdparty / boost / boost / parameter / parameters.hpp
1 // Copyright David Abrahams, Daniel Wallin 2003.
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_PARAMETERS_031014_HPP
8 #define BOOST_PARAMETERS_031014_HPP
9
10 #include <boost/parameter/config.hpp>
11
12 #if defined(BOOST_PARAMETER_HAS_PERFECT_FORWARDING)
13
14 namespace boost { namespace parameter { namespace aux {
15
16     // The make_arg_list<> metafunction produces a reversed arg_list,
17     // so pass the arguments to the arg_list constructor reversed in turn.
18     template <typename ArgList, typename ...Args>
19     struct arg_list_factory;
20 }}} // namespace boost::parameter::aux
21
22 #include <boost/parameter/aux_/arg_list.hpp>
23 #include <utility>
24
25 #if defined(BOOST_PARAMETER_CAN_USE_MP11)
26 #include <boost/mp11/utility.hpp>
27 #include <type_traits>
28 #else
29 #include <boost/mpl/if.hpp>
30 #include <boost/type_traits/is_same.hpp>
31 #endif
32
33 namespace boost { namespace parameter { namespace aux {
34
35     // TODO: Reduce template code bloat. -- Cromwell D. Enage
36     template <typename ArgList>
37     struct arg_list_factory<ArgList>
38     {
39         template <typename ...ReversedArgs>
40         static inline BOOST_CONSTEXPR ArgList
41             reverse(ReversedArgs&&... reversed_args)
42         {
43             return ArgList(
44 #if defined(BOOST_PARAMETER_CAN_USE_MP11)
45                 ::boost::mp11::mp_if<
46                     ::std::is_same<
47 #else
48                 typename ::boost::mpl::if_<
49                     ::boost::is_same<
50 #endif
51                         typename ArgList::tagged_arg::value_type
52                       , ::boost::parameter::void_
53                     >
54                   , ::boost::parameter::aux::value_type_is_void
55                   , ::boost::parameter::aux::value_type_is_not_void
56 #if defined(BOOST_PARAMETER_CAN_USE_MP11)
57                 >()
58 #else
59                 >::type()
60 #endif
61               , ::std::forward<ReversedArgs>(reversed_args)...
62             );
63         }
64     };
65
66     template <typename ArgList, typename A0, typename ...Args>
67     struct arg_list_factory<ArgList,A0,Args...>
68     {
69         template <typename ...ReversedArgs>
70         static inline BOOST_CONSTEXPR ArgList
71             reverse(A0&& a0, Args&&... args, ReversedArgs&&... reversed_args)
72         {
73             return ::boost::parameter::aux
74             ::arg_list_factory<ArgList,Args...>::reverse(
75                 ::std::forward<Args>(args)...
76               , ::std::forward<A0>(a0)
77               , ::std::forward<ReversedArgs>(reversed_args)...
78             );
79         }
80     };
81 }}} // namespace boost::parameter::aux
82
83 #include <boost/parameter/aux_/void.hpp>
84 #include <boost/parameter/aux_/pack/make_arg_list.hpp>
85 #include <boost/parameter/aux_/pack/make_parameter_spec_items.hpp>
86 #include <boost/parameter/aux_/pack/tag_keyword_arg.hpp>
87 #include <boost/parameter/aux_/pack/tag_template_keyword_arg.hpp>
88
89 #if defined(BOOST_PARAMETER_CAN_USE_MP11)
90 #include <boost/mp11/integral.hpp>
91 #include <boost/mp11/list.hpp>
92 #else
93 #include <boost/mpl/bool.hpp>
94 #include <boost/mpl/pair.hpp>
95 #include <boost/mpl/identity.hpp>
96 #endif
97
98 #if !defined(BOOST_PARAMETER_VARIADIC_MPL_SEQUENCE)
99 #if defined(BOOST_PARAMETER_CAN_USE_MP11)
100 //#include <boost/mp11/mpl.hpp>
101 #define BOOST_PARAMETER_VARIADIC_MPL_SEQUENCE ::boost::mp11::mp_list
102 #else
103 #include <boost/fusion/container/list/list_fwd.hpp>
104
105 // Newer versions of MSVC fail on the evaluate_category and
106 // preprocessor_eval_category test programs when parameters uses
107 // boost::fusion::list.
108 // -- Cromwell D. Enage
109 #if defined(BOOST_FUSION_HAS_VARIADIC_LIST) && ( \
110         !defined(BOOST_MSVC) || (BOOST_MSVC < 1800) \
111     )
112 #include <boost/fusion/container/list.hpp>
113 #include <boost/fusion/mpl.hpp>
114 #define BOOST_PARAMETER_VARIADIC_MPL_SEQUENCE ::boost::fusion::list
115 #else
116 #include <boost/fusion/container/deque/deque_fwd.hpp>
117
118 #if defined(BOOST_FUSION_HAS_VARIADIC_DEQUE)
119 #include <boost/fusion/container/deque.hpp>
120 #include <boost/fusion/mpl.hpp>
121 #define BOOST_PARAMETER_VARIADIC_MPL_SEQUENCE ::boost::fusion::deque
122 #else
123 #include <boost/mpl/vector.hpp>
124 #define BOOST_PARAMETER_VARIADIC_MPL_SEQUENCE ::boost::mpl::vector
125 #endif  // BOOST_FUSION_HAS_VARIADIC_DEQUE
126 #endif  // BOOST_FUSION_HAS_VARIADIC_LIST
127 #endif  // BOOST_PARAMETER_CAN_USE_MP11
128 #endif  // BOOST_PARAMETER_VARIADIC_MPL_SEQUENCE
129
130 namespace boost { namespace parameter {
131
132     template <typename ...Spec>
133     struct parameters
134     {
135         typedef BOOST_PARAMETER_VARIADIC_MPL_SEQUENCE<Spec...> parameter_spec;
136
137         typedef typename ::boost::parameter::aux
138         ::make_deduced_list<parameter_spec>::type deduced_list;
139
140         // If the elements of NamedList match the criteria of overload
141         // resolution, returns a type which can be constructed from
142         // parameters.  Otherwise, this is not a valid metafunction
143         // (no nested ::type).
144         template <typename ArgumentPackAndError>
145         struct match_base
146 #if !defined(BOOST_PARAMETER_CAN_USE_MP11)
147           : ::boost::mpl::if_<
148                 typename ::boost::parameter::aux::match_parameters_base_cond<
149                     ArgumentPackAndError
150                   , parameter_spec
151                 >::type
152               , ::boost::mpl::identity<
153                     ::boost::parameter::parameters<Spec...>
154                 >
155               , ::boost::parameter::void_
156             >
157 #endif
158         {
159 #if defined(BOOST_PARAMETER_CAN_USE_MP11)
160             using type = ::boost::mp11::mp_if<
161                 typename ::boost::parameter::aux::match_parameters_base_cond<
162                     ArgumentPackAndError
163                   , parameter_spec
164                 >::type
165               , ::boost::mp11::mp_identity<
166                     ::boost::parameter::parameters<Spec...>
167                 >
168               , ::boost::parameter::void_
169             >;
170 #endif
171         };
172
173         // Specializations are to be used as an optional argument
174         // to eliminate overloads via SFINAE.
175         template <typename ...Args>
176         struct match
177           : ::boost::parameter::parameters<Spec...>
178             ::BOOST_NESTED_TEMPLATE match_base<
179                 typename ::boost::parameter::aux::make_arg_list<
180                     typename ::boost::parameter::aux
181                     ::make_parameter_spec_items<parameter_spec,Args...>::type
182                   , deduced_list
183                   , ::boost::parameter::aux::tag_keyword_arg
184                     // Don't emit errors when doing SFINAE.
185 #if defined(BOOST_PARAMETER_CAN_USE_MP11)
186                   , ::boost::mp11::mp_false
187 #else
188                   , ::boost::mpl::false_
189 #endif
190                 >::type
191             >::type
192         {
193         };
194
195         // Metafunction that returns an ArgumentPack.
196         template <typename ...Args>
197         struct bind
198 #if !defined(BOOST_PARAMETER_CAN_USE_MP11)
199           : ::boost::mpl::first<
200                 typename ::boost::parameter::aux::make_arg_list<
201                     typename ::boost::parameter::aux
202                     ::make_parameter_spec_items<parameter_spec,Args...>::type
203                   , deduced_list
204                   , ::boost::parameter::aux::tag_template_keyword_arg
205                 >::type
206             >
207 #endif
208         {
209 #if defined(BOOST_PARAMETER_CAN_USE_MP11)
210             using type = ::boost::mp11::mp_at_c<
211                 typename ::boost::parameter::aux::make_arg_list<
212                     typename ::boost::parameter::aux
213                     ::make_parameter_spec_items<parameter_spec,Args...>::type
214                   , deduced_list
215                   , ::boost::parameter::aux::tag_template_keyword_arg
216                 >::type
217               , 0
218             >;
219 #endif
220         };
221
222         // The function call operator is used to build an arg_list that
223         // labels the positional parameters and maintains whatever other
224         // tags may have been specified by the caller.
225         inline ::boost::parameter::aux::empty_arg_list operator()() const
226         {
227             return ::boost::parameter::aux::empty_arg_list();
228         }
229
230         template <typename A0, typename ...Args>
231 #if defined(BOOST_PARAMETER_CAN_USE_MP11)
232         inline ::boost::mp11::mp_at_c<
233 #else
234         inline typename ::boost::mpl::first<
235 #endif
236             typename ::boost::parameter::aux::make_arg_list<
237                 typename ::boost::parameter::aux
238                 ::make_parameter_spec_items<parameter_spec,A0,Args...>::type
239               , deduced_list
240               , ::boost::parameter::aux::tag_keyword_arg
241             >::type
242 #if defined(BOOST_PARAMETER_CAN_USE_MP11)
243           , 0
244         >
245 #else
246         >::type
247 #endif
248             operator()(A0&& a0, Args&& ...args) const
249         {
250             typedef typename ::boost::parameter::aux::make_arg_list<
251                 typename ::boost::parameter::aux
252                 ::make_parameter_spec_items<parameter_spec,A0,Args...>::type
253               , deduced_list
254               , ::boost::parameter::aux::tag_keyword_arg
255             >::type list_error_pair;
256
257 #if defined(BOOST_PARAMETER_CAN_USE_MP11)
258             using result_type = ::boost::mp11::mp_at_c<list_error_pair,0>;
259
260             using error = ::boost::mp11::mp_at_c<list_error_pair,1>;
261 #else
262             typedef typename ::boost::mpl
263             ::first<list_error_pair>::type result_type;
264
265             typedef typename ::boost::mpl
266             ::second<list_error_pair>::type error;
267 #endif
268
269             error();
270
271             return ::boost::parameter::aux
272             ::arg_list_factory<result_type,A0,Args...>::reverse(
273                 ::std::forward<A0>(a0)
274               , ::std::forward<Args>(args)...
275             );
276         }
277     };
278 }} // namespace boost::parameter
279
280 #else   // !defined(BOOST_PARAMETER_HAS_PERFECT_FORWARDING)
281
282 #include <boost/parameter/aux_/void.hpp>
283 #include <boost/parameter/aux_/arg_list.hpp>
284 #include <boost/parameter/aux_/pack/make_arg_list.hpp>
285 #include <boost/parameter/aux_/pack/make_items.hpp>
286 #include <boost/parameter/aux_/pack/make_deduced_items.hpp>
287 #include <boost/parameter/aux_/pack/tag_template_keyword_arg.hpp>
288 #include <boost/parameter/aux_/preprocessor/binary_seq_for_each.hpp>
289 #include <boost/preprocessor/arithmetic/inc.hpp>
290 #include <boost/preprocessor/repetition/enum_shifted.hpp>
291 #include <boost/preprocessor/repetition/repeat.hpp>
292 #include <boost/preprocessor/selection/min.hpp>
293
294 #if ( \
295         BOOST_PARAMETER_EXPONENTIAL_OVERLOAD_THRESHOLD_ARITY < \
296         BOOST_PARAMETER_MAX_ARITY \
297     )
298 #include <boost/parameter/aux_/pack/tag_keyword_arg_ref.hpp>
299 #include <boost/mpl/pair.hpp>
300 #include <boost/preprocessor/arithmetic/dec.hpp>
301 #include <boost/preprocessor/arithmetic/sub.hpp>
302 #include <boost/preprocessor/facilities/intercept.hpp>
303 #include <boost/preprocessor/iteration/iterate.hpp>
304 #include <boost/preprocessor/repetition/enum.hpp>
305 #include <boost/preprocessor/repetition/enum_trailing_params.hpp>
306 #endif
307
308 #if !defined(BOOST_NO_SFINAE) && \
309     !BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x592))
310 #include <boost/parameter/aux_/pack/tag_keyword_arg.hpp>
311 #include <boost/mpl/bool.hpp>
312 #include <boost/mpl/if.hpp>
313 #include <boost/mpl/identity.hpp>
314 #include <boost/type_traits/is_same.hpp>
315 #endif
316
317 #if BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x564))
318 #include <boost/preprocessor/repetition/enum_params.hpp>
319 #else
320 #include <boost/preprocessor/repetition/enum_binary_params.hpp>
321 #endif
322
323 #include <boost/parameter/aux_/preprocessor/no_perfect_forwarding_begin.hpp>
324
325 namespace boost { namespace parameter {
326
327     template <
328         typename PS0
329       , BOOST_PP_ENUM_SHIFTED(
330             BOOST_PARAMETER_MAX_ARITY
331           , BOOST_PARAMETER_template_args
332           , PS
333         )
334     >
335     struct parameters
336     {
337         typedef typename BOOST_PARAMETER_build_deduced_list(
338             BOOST_PARAMETER_MAX_ARITY
339           , ::boost::parameter::aux::make_deduced_items
340           , PS
341         )::type deduced_list;
342
343         // If the elements of NamedList match the criteria of overload
344         // resolution, returns a type which can be constructed from
345         // parameters.  Otherwise, this is not a valid metafunction
346         // (no nested ::type).
347 #if !defined(BOOST_NO_SFINAE) && \
348     !BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x592))
349         // If NamedList satisfies the PS0, PS1, ..., this is a metafunction
350         // returning parameters.  Otherwise it has no nested ::type.
351         template <typename ArgumentPackAndError>
352         struct match_base
353           : ::boost::mpl::if_<
354                 // ::boost::mpl::and_<
355                 //    aux::satisfies_requirements_of<NamedList,PS0>
356                 //  , ::boost::mpl::and_<
357                 //       aux::satisfies_requirements_of<NamedList,PS1>...
358                 //           ..., ::boost::mpl::true_
359                 // ...> >
360                 typename BOOST_PP_REPEAT(
361                     BOOST_PARAMETER_MAX_ARITY
362                   , BOOST_PARAMETER_satisfies_begin
363                   , PS
364                 )
365                 ::boost::is_same<
366                     typename ::boost::mpl
367                     ::second<ArgumentPackAndError>::type
368                   , ::boost::parameter::void_
369                 >
370                 BOOST_PP_REPEAT(
371                     BOOST_PARAMETER_MAX_ARITY
372                   , BOOST_PARAMETER_satisfies_end
373                   , ::boost::mpl::false_
374                 )::type
375               , ::boost::mpl::identity<
376                     ::boost::parameter::parameters<
377                         BOOST_PP_ENUM_PARAMS(BOOST_PARAMETER_MAX_ARITY, PS)
378                     >
379                 >
380               , ::boost::parameter::void_
381             >
382         {
383         };
384 #endif  // SFINAE enabled, not Borland
385
386         // Specializations are to be used as an optional argument
387         // to eliminate overloads via SFINAE.
388         template <
389 #if BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x564))
390             // Borland simply can't handle default arguments in member
391             // class templates.  People wishing to write portable code can
392             // explicitly specify BOOST_PARAMETER_MAX_ARITY arguments.
393             BOOST_PP_ENUM_PARAMS(BOOST_PARAMETER_MAX_ARITY, typename A)
394 #else
395             BOOST_PP_ENUM_BINARY_PARAMS(
396                 BOOST_PARAMETER_MAX_ARITY
397               , typename A
398               , = ::boost::parameter::void_ BOOST_PP_INTERCEPT
399             )
400 #endif
401         >
402         struct match
403 #if !defined(BOOST_NO_SFINAE) && \
404     !BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x592))
405           : ::boost::parameter::parameters<
406                 BOOST_PP_ENUM_PARAMS(BOOST_PARAMETER_MAX_ARITY, PS)
407             >::BOOST_NESTED_TEMPLATE match_base<
408                 typename ::boost::parameter::aux::make_arg_list<
409                     typename BOOST_PARAMETER_build_arg_list(
410                         BOOST_PARAMETER_MAX_ARITY
411                       , ::boost::parameter::aux::make_items
412                       , PS
413                       , A
414                     )::type
415                   , deduced_list
416                   , ::boost::parameter::aux::tag_keyword_arg
417                     // Don't emit errors when doing SFINAE.
418                   , ::boost::mpl::false_
419                 >::type
420             >::type
421         {
422         };
423 #else
424         {
425             typedef ::boost::parameter::parameters<
426                 BOOST_PP_ENUM_PARAMS(BOOST_PARAMETER_MAX_ARITY, PS)
427             > type;
428         };
429 #endif  // SFINAE enabled, not Borland
430
431         // Metafunction that returns an ArgumentPack.
432
433         // TODO, bind has to instantiate the error type in the result
434         // of make_arg_list.
435
436         template <
437 #if BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x564))
438             // Borland simply can't handle default arguments in member
439             // class templates.  People wishing to write portable code can
440             // explicitly specify BOOST_PARAMETER_MAX_ARITY arguments.
441             BOOST_PP_ENUM_PARAMS(BOOST_PARAMETER_MAX_ARITY, typename A)
442 #else
443             BOOST_PP_ENUM_BINARY_PARAMS(
444                 BOOST_PARAMETER_MAX_ARITY
445               , typename A
446               , = ::boost::parameter::void_ BOOST_PP_INTERCEPT
447             )
448 #endif
449         >
450         struct bind
451         {
452             typedef typename ::boost::parameter::aux::make_arg_list<
453                 typename BOOST_PARAMETER_build_arg_list(
454                     BOOST_PARAMETER_MAX_ARITY
455                   , ::boost::parameter::aux::make_items
456                   , PS
457                   , A
458                 )::type
459               , deduced_list
460               , ::boost::parameter::aux::tag_template_keyword_arg
461             >::type result;
462
463             typedef typename ::boost::mpl::first<result>::type type;
464         };
465
466         BOOST_PP_REPEAT(
467             BOOST_PARAMETER_MAX_ARITY
468           , BOOST_PARAMETER_forward_typedef
469           , (PS)(parameter_spec)
470         )
471
472         // The function call operator is used to build an arg_list that
473         // labels the positional parameters and maintains whatever other
474         // tags may have been specified by the caller.
475         //
476         // !!!NOTE!!!
477         //
478         // The make_arg_list<> metafunction produces a reversed arg_list,
479         // so pass the arguments to the arg_list constructor reversed in turn.
480         inline ::boost::parameter::aux::empty_arg_list operator()() const
481         {
482             return ::boost::parameter::aux::empty_arg_list();
483         }
484
485 #if (0 < BOOST_PARAMETER_EXPONENTIAL_OVERLOAD_THRESHOLD_ARITY)
486         BOOST_PP_REPEAT(
487             BOOST_PP_MIN(
488                 BOOST_PP_INC(BOOST_PARAMETER_MAX_ARITY)
489               , BOOST_PARAMETER_EXPONENTIAL_OVERLOAD_THRESHOLD_ARITY
490             )
491           , BOOST_PARAMETER_AUX_PP_BINARY_SEQ_FOR_EACH_Z
492           , (BOOST_PARAMETER_function_call_op_overload_R)(_)
493         )
494 #if ( \
495         BOOST_PARAMETER_EXPONENTIAL_OVERLOAD_THRESHOLD_ARITY < \
496         BOOST_PARAMETER_MAX_ARITY \
497     )
498 #define BOOST_PP_ITERATION_PARAMS_1 \
499     (3,( \
500         BOOST_PARAMETER_EXPONENTIAL_OVERLOAD_THRESHOLD_ARITY \
501       , BOOST_PARAMETER_MAX_ARITY \
502       , <boost/parameter/aux_/preprocessor/overloads.hpp> \
503     ))
504 #include BOOST_PP_ITERATE()
505 #endif
506 #else   // (0 == BOOST_PARAMETER_EXPONENTIAL_OVERLOAD_THRESHOLD_ARITY)
507         template <typename A0>
508         inline typename ::boost::mpl::first<
509             typename ::boost::parameter::aux::make_arg_list<
510                 ::boost::parameter::aux::item<
511                     PS0,A0
512                 >
513               , deduced_list
514               , ::boost::parameter::aux::tag_keyword_arg_ref
515             >::type
516         >::type
517             operator()(A0& a0) const
518         {
519             typedef typename ::boost::parameter::aux::make_arg_list<
520                 ::boost::parameter::aux::item<
521                     PS0,A0
522                 >
523               , deduced_list
524               , ::boost::parameter::aux::tag_keyword_arg_ref
525             >::type result;
526
527             typedef typename ::boost::mpl::first<result>::type result_type;
528             typedef typename ::boost::mpl::second<result>::type error;
529             error();
530
531             return result_type(
532                 a0
533                 // , void_(), void_(), void_() ...
534                 BOOST_PP_ENUM_TRAILING_PARAMS(
535                     BOOST_PP_SUB(BOOST_PARAMETER_COMPOSE_MAX_ARITY, 1)
536                   , ::boost::parameter::aux::void_reference() BOOST_PP_INTERCEPT
537                 )
538             );
539         }
540
541         template <typename A0, typename A1>
542         inline typename ::boost::mpl::first<
543             typename ::boost::parameter::aux::make_arg_list<
544                 ::boost::parameter::aux::item<
545                     PS0,A0
546                   , ::boost::parameter::aux::item<
547                         PS1,A1
548                     >
549                 >
550               , deduced_list
551               , ::boost::parameter::aux::tag_keyword_arg_ref
552             >::type
553         >::type
554             operator()(A0& a0, A1& a1) const
555         {
556             typedef typename ::boost::parameter::aux::make_arg_list<
557                 ::boost::parameter::aux::item<
558                     PS0,A0
559                   , ::boost::parameter::aux::item<
560                         PS1,A1
561                     >
562                 >
563               , deduced_list
564               , ::boost::parameter::aux::tag_keyword_arg
565             >::type result;
566
567             typedef typename ::boost::mpl::first<result>::type result_type;
568             typedef typename ::boost::mpl::second<result>::type error;
569             error();
570
571             return result_type(
572                 a1
573               , a0
574                 // , void_(), void_() ...
575                 BOOST_PP_ENUM_TRAILING_PARAMS(
576                     BOOST_PP_SUB(BOOST_PARAMETER_COMPOSE_MAX_ARITY, 2)
577                   , ::boost::parameter::aux::void_reference() BOOST_PP_INTERCEPT
578                 )
579             );
580         }
581
582 #if (2 < BOOST_PARAMETER_MAX_ARITY)
583         // Higher arities are handled by the preprocessor
584 #define BOOST_PP_ITERATION_PARAMS_1 \
585     (3,( \
586         3 \
587       , BOOST_PARAMETER_MAX_ARITY \
588       , <boost/parameter/aux_/preprocessor/overloads.hpp> \
589     ))
590 #include BOOST_PP_ITERATE()
591 #endif
592 #endif  // exponential overloads
593     };
594 }} // namespace boost::parameter
595
596 #include <boost/parameter/aux_/preprocessor/no_perfect_forwarding_end.hpp>
597
598 #endif  // BOOST_PARAMETER_HAS_PERFECT_FORWARDING
599 #endif  // include guard
600