File indexing completed on 2025-11-03 09:16:45
0001 
0002 
0003 
0004 
0005 
0006 
0007 
0008 
0009 
0010 
0011 #ifndef BOOST_ASIO_PREFER_HPP
0012 #define BOOST_ASIO_PREFER_HPP
0013 
0014 #if defined(_MSC_VER) && (_MSC_VER >= 1200)
0015 # pragma once
0016 #endif 
0017 
0018 #include <boost/asio/detail/config.hpp>
0019 #include <boost/asio/detail/type_traits.hpp>
0020 #include <boost/asio/is_applicable_property.hpp>
0021 #include <boost/asio/traits/prefer_free.hpp>
0022 #include <boost/asio/traits/prefer_member.hpp>
0023 #include <boost/asio/traits/require_free.hpp>
0024 #include <boost/asio/traits/require_member.hpp>
0025 #include <boost/asio/traits/static_require.hpp>
0026 
0027 #include <boost/asio/detail/push_options.hpp>
0028 
0029 #if defined(GENERATING_DOCUMENTATION)
0030 
0031 namespace boost {
0032 namespace asio {
0033 
0034 
0035 
0036 
0037 
0038 
0039 
0040 
0041 
0042 
0043 
0044 
0045 
0046 
0047 
0048 
0049 
0050 
0051 
0052 
0053 
0054 
0055 
0056 
0057 
0058 
0059 
0060 
0061 
0062 
0063 
0064 
0065 
0066 
0067 
0068 
0069 
0070 
0071 
0072 
0073 
0074 
0075 
0076 
0077 inline constexpr unspecified prefer = unspecified;
0078 
0079 
0080 
0081 
0082 
0083 
0084 
0085 template <typename T, typename... Properties>
0086 struct can_prefer :
0087   integral_constant<bool, automatically_determined>
0088 {
0089 };
0090 
0091 
0092 
0093 
0094 
0095 
0096 
0097 template <typename T, typename... Properties>
0098 struct is_nothrow_prefer :
0099   integral_constant<bool, automatically_determined>
0100 {
0101 };
0102 
0103 
0104 
0105 
0106 
0107 
0108 
0109 template <typename T, typename... Properties>
0110 struct prefer_result
0111 {
0112   
0113   typedef automatically_determined type;
0114 };
0115 
0116 } 
0117 } 
0118 
0119 #else 
0120 
0121 namespace boost_asio_prefer_fn {
0122 
0123 using boost::asio::conditional_t;
0124 using boost::asio::decay_t;
0125 using boost::asio::declval;
0126 using boost::asio::enable_if_t;
0127 using boost::asio::is_applicable_property;
0128 using boost::asio::traits::prefer_free;
0129 using boost::asio::traits::prefer_member;
0130 using boost::asio::traits::require_free;
0131 using boost::asio::traits::require_member;
0132 using boost::asio::traits::static_require;
0133 
0134 void prefer();
0135 void require();
0136 
0137 enum overload_type
0138 {
0139   identity,
0140   call_require_member,
0141   call_require_free,
0142   call_prefer_member,
0143   call_prefer_free,
0144   two_props,
0145   n_props,
0146   ill_formed
0147 };
0148 
0149 template <typename Impl, typename T, typename Properties,
0150     typename = void, typename = void, typename = void, typename = void,
0151     typename = void, typename = void, typename = void>
0152 struct call_traits
0153 {
0154   static constexpr overload_type overload = ill_formed;
0155   static constexpr bool is_noexcept = false;
0156   typedef void result_type;
0157 };
0158 
0159 template <typename Impl, typename T, typename Property>
0160 struct call_traits<Impl, T, void(Property),
0161   enable_if_t<
0162     is_applicable_property<
0163       decay_t<T>,
0164       decay_t<Property>
0165     >::value
0166   >,
0167   enable_if_t<
0168     decay_t<Property>::is_preferable
0169   >,
0170   enable_if_t<
0171     static_require<T, Property>::is_valid
0172   >>
0173 {
0174   static constexpr overload_type overload = identity;
0175   static constexpr bool is_noexcept = true;
0176 
0177   typedef T&& result_type;
0178 };
0179 
0180 template <typename Impl, typename T, typename Property>
0181 struct call_traits<Impl, T, void(Property),
0182   enable_if_t<
0183     is_applicable_property<
0184       decay_t<T>,
0185       decay_t<Property>
0186     >::value
0187   >,
0188   enable_if_t<
0189     decay_t<Property>::is_preferable
0190   >,
0191   enable_if_t<
0192     !static_require<T, Property>::is_valid
0193   >,
0194   enable_if_t<
0195     require_member<typename Impl::template proxy<T>::type, Property>::is_valid
0196   >> :
0197   require_member<typename Impl::template proxy<T>::type, Property>
0198 {
0199   static constexpr overload_type overload = call_require_member;
0200 };
0201 
0202 template <typename Impl, typename T, typename Property>
0203 struct call_traits<Impl, T, void(Property),
0204   enable_if_t<
0205     is_applicable_property<
0206       decay_t<T>,
0207       decay_t<Property>
0208     >::value
0209   >,
0210   enable_if_t<
0211     decay_t<Property>::is_preferable
0212   >,
0213   enable_if_t<
0214     !static_require<T, Property>::is_valid
0215   >,
0216   enable_if_t<
0217     !require_member<typename Impl::template proxy<T>::type, Property>::is_valid
0218   >,
0219   enable_if_t<
0220     require_free<T, Property>::is_valid
0221   >> :
0222   require_free<T, Property>
0223 {
0224   static constexpr overload_type overload = call_require_free;
0225 };
0226 
0227 template <typename Impl, typename T, typename Property>
0228 struct call_traits<Impl, T, void(Property),
0229   enable_if_t<
0230     is_applicable_property<
0231       decay_t<T>,
0232       decay_t<Property>
0233     >::value
0234   >,
0235   enable_if_t<
0236     decay_t<Property>::is_preferable
0237   >,
0238   enable_if_t<
0239     !static_require<T, Property>::is_valid
0240   >,
0241   enable_if_t<
0242     !require_member<typename Impl::template proxy<T>::type, Property>::is_valid
0243   >,
0244   enable_if_t<
0245     !require_free<T, Property>::is_valid
0246   >,
0247   enable_if_t<
0248     prefer_member<typename Impl::template proxy<T>::type, Property>::is_valid
0249   >> :
0250   prefer_member<typename Impl::template proxy<T>::type, Property>
0251 {
0252   static constexpr overload_type overload = call_prefer_member;
0253 };
0254 
0255 template <typename Impl, typename T, typename Property>
0256 struct call_traits<Impl, T, void(Property),
0257   enable_if_t<
0258     is_applicable_property<
0259       decay_t<T>,
0260       decay_t<Property>
0261     >::value
0262   >,
0263   enable_if_t<
0264     decay_t<Property>::is_preferable
0265   >,
0266   enable_if_t<
0267     !static_require<T, Property>::is_valid
0268   >,
0269   enable_if_t<
0270     !require_member<typename Impl::template proxy<T>::type, Property>::is_valid
0271   >,
0272   enable_if_t<
0273     !require_free<T, Property>::is_valid
0274   >,
0275   enable_if_t<
0276     !prefer_member<typename Impl::template proxy<T>::type, Property>::is_valid
0277   >,
0278   enable_if_t<
0279     prefer_free<T, Property>::is_valid
0280   >> :
0281   prefer_free<T, Property>
0282 {
0283   static constexpr overload_type overload = call_prefer_free;
0284 };
0285 
0286 template <typename Impl, typename T, typename Property>
0287 struct call_traits<Impl, T, void(Property),
0288   enable_if_t<
0289     is_applicable_property<
0290       decay_t<T>,
0291       decay_t<Property>
0292     >::value
0293   >,
0294   enable_if_t<
0295     decay_t<Property>::is_preferable
0296   >,
0297   enable_if_t<
0298     !static_require<T, Property>::is_valid
0299   >,
0300   enable_if_t<
0301     !require_member<typename Impl::template proxy<T>::type, Property>::is_valid
0302   >,
0303   enable_if_t<
0304     !require_free<T, Property>::is_valid
0305   >,
0306   enable_if_t<
0307     !prefer_member<typename Impl::template proxy<T>::type, Property>::is_valid
0308   >,
0309   enable_if_t<
0310     !prefer_free<T, Property>::is_valid
0311   >>
0312 {
0313   static constexpr overload_type overload = identity;
0314   static constexpr bool is_noexcept = true;
0315 
0316   typedef T&& result_type;
0317 };
0318 
0319 template <typename Impl, typename T, typename P0, typename P1>
0320 struct call_traits<Impl, T, void(P0, P1),
0321   enable_if_t<
0322     call_traits<Impl, T, void(P0)>::overload != ill_formed
0323   >,
0324   enable_if_t<
0325     call_traits<
0326       Impl,
0327       typename call_traits<Impl, T, void(P0)>::result_type,
0328       void(P1)
0329     >::overload != ill_formed
0330   >>
0331 {
0332   static constexpr overload_type overload = two_props;
0333 
0334   static constexpr bool is_noexcept =
0335     (
0336       call_traits<Impl, T, void(P0)>::is_noexcept
0337       &&
0338       call_traits<
0339         Impl,
0340         typename call_traits<Impl, T, void(P0)>::result_type,
0341         void(P1)
0342       >::is_noexcept
0343     );
0344 
0345   typedef decay_t<
0346     typename call_traits<
0347       Impl,
0348       typename call_traits<Impl, T, void(P0)>::result_type,
0349       void(P1)
0350     >::result_type
0351   > result_type;
0352 };
0353 
0354 template <typename Impl, typename T, typename P0,
0355     typename P1, typename... PN>
0356 struct call_traits<Impl, T, void(P0, P1, PN...),
0357   enable_if_t<
0358     call_traits<Impl, T, void(P0)>::overload != ill_formed
0359   >,
0360   enable_if_t<
0361     call_traits<
0362       Impl,
0363       typename call_traits<Impl, T, void(P0)>::result_type,
0364       void(P1, PN...)
0365     >::overload != ill_formed
0366   >>
0367 {
0368   static constexpr overload_type overload = n_props;
0369 
0370   static constexpr bool is_noexcept =
0371     (
0372       call_traits<Impl, T, void(P0)>::is_noexcept
0373       &&
0374       call_traits<
0375         Impl,
0376         typename call_traits<Impl, T, void(P0)>::result_type,
0377         void(P1, PN...)
0378       >::is_noexcept
0379     );
0380 
0381   typedef decay_t<
0382     typename call_traits<
0383       Impl,
0384       typename call_traits<Impl, T, void(P0)>::result_type,
0385       void(P1, PN...)
0386     >::result_type
0387   > result_type;
0388 };
0389 
0390 struct impl
0391 {
0392   template <typename T>
0393   struct proxy
0394   {
0395 #if defined(BOOST_ASIO_HAS_DEDUCED_REQUIRE_MEMBER_TRAIT) \
0396   && defined(BOOST_ASIO_HAS_DEDUCED_PREFER_MEMBER_TRAIT)
0397     struct type
0398     {
0399       template <typename P>
0400       auto require(P&& p)
0401         noexcept(
0402           noexcept(
0403             declval<conditional_t<true, T, P>>().require(static_cast<P&&>(p))
0404           )
0405         )
0406         -> decltype(
0407           declval<conditional_t<true, T, P>>().require(static_cast<P&&>(p))
0408         );
0409 
0410       template <typename P>
0411       auto prefer(P&& p)
0412         noexcept(
0413           noexcept(
0414             declval<conditional_t<true, T, P>>().prefer(static_cast<P&&>(p))
0415           )
0416         )
0417         -> decltype(
0418           declval<conditional_t<true, T, P>>().prefer(static_cast<P&&>(p))
0419         );
0420     };
0421 #else 
0422       
0423     typedef T type;
0424 #endif 
0425        
0426   };
0427 
0428   template <typename T, typename Property>
0429   BOOST_ASIO_NODISCARD constexpr enable_if_t<
0430     call_traits<impl, T, void(Property)>::overload == identity,
0431     typename call_traits<impl, T, void(Property)>::result_type
0432   >
0433   operator()(T&& t, Property&&) const
0434     noexcept(call_traits<impl, T, void(Property)>::is_noexcept)
0435   {
0436     return static_cast<T&&>(t);
0437   }
0438 
0439   template <typename T, typename Property>
0440   BOOST_ASIO_NODISCARD constexpr enable_if_t<
0441     call_traits<impl, T, void(Property)>::overload == call_require_member,
0442     typename call_traits<impl, T, void(Property)>::result_type
0443   >
0444   operator()(T&& t, Property&& p) const
0445     noexcept(call_traits<impl, T, void(Property)>::is_noexcept)
0446   {
0447     return static_cast<T&&>(t).require(static_cast<Property&&>(p));
0448   }
0449 
0450   template <typename T, typename Property>
0451   BOOST_ASIO_NODISCARD constexpr enable_if_t<
0452     call_traits<impl, T, void(Property)>::overload == call_require_free,
0453     typename call_traits<impl, T, void(Property)>::result_type
0454   >
0455   operator()(T&& t, Property&& p) const
0456     noexcept(call_traits<impl, T, void(Property)>::is_noexcept)
0457   {
0458     return require(static_cast<T&&>(t), static_cast<Property&&>(p));
0459   }
0460 
0461   template <typename T, typename Property>
0462   BOOST_ASIO_NODISCARD constexpr enable_if_t<
0463     call_traits<impl, T, void(Property)>::overload == call_prefer_member,
0464     typename call_traits<impl, T, void(Property)>::result_type
0465   >
0466   operator()(T&& t, Property&& p) const
0467     noexcept(call_traits<impl, T, void(Property)>::is_noexcept)
0468   {
0469     return static_cast<T&&>(t).prefer(static_cast<Property&&>(p));
0470   }
0471 
0472   template <typename T, typename Property>
0473   BOOST_ASIO_NODISCARD constexpr enable_if_t<
0474     call_traits<impl, T, void(Property)>::overload == call_prefer_free,
0475     typename call_traits<impl, T, void(Property)>::result_type
0476   >
0477   operator()(T&& t, Property&& p) const
0478     noexcept(call_traits<impl, T, void(Property)>::is_noexcept)
0479   {
0480     return prefer(static_cast<T&&>(t), static_cast<Property&&>(p));
0481   }
0482 
0483   template <typename T, typename P0, typename P1>
0484   BOOST_ASIO_NODISCARD constexpr enable_if_t<
0485     call_traits<impl, T, void(P0, P1)>::overload == two_props,
0486     typename call_traits<impl, T, void(P0, P1)>::result_type
0487   >
0488   operator()(T&& t, P0&& p0, P1&& p1) const
0489     noexcept(call_traits<impl, T, void(P0, P1)>::is_noexcept)
0490   {
0491     return (*this)(
0492         (*this)(static_cast<T&&>(t), static_cast<P0&&>(p0)),
0493         static_cast<P1&&>(p1));
0494   }
0495 
0496   template <typename T, typename P0, typename P1,
0497     typename... PN>
0498   BOOST_ASIO_NODISCARD constexpr enable_if_t<
0499     call_traits<impl, T, void(P0, P1, PN...)>::overload == n_props,
0500     typename call_traits<impl, T, void(P0, P1, PN...)>::result_type
0501   >
0502   operator()(T&& t, P0&& p0, P1&& p1, PN&&... pn) const
0503     noexcept(call_traits<impl, T, void(P0, P1, PN...)>::is_noexcept)
0504   {
0505     return (*this)(
0506         (*this)(static_cast<T&&>(t), static_cast<P0&&>(p0)),
0507         static_cast<P1&&>(p1), static_cast<PN&&>(pn)...);
0508   }
0509 };
0510 
0511 template <typename T = impl>
0512 struct static_instance
0513 {
0514   static const T instance;
0515 };
0516 
0517 template <typename T>
0518 const T static_instance<T>::instance = {};
0519 
0520 } 
0521 namespace boost {
0522 namespace asio {
0523 namespace {
0524 
0525 static constexpr const boost_asio_prefer_fn::impl&
0526   prefer = boost_asio_prefer_fn::static_instance<>::instance;
0527 
0528 } 
0529 
0530 typedef boost_asio_prefer_fn::impl prefer_t;
0531 
0532 template <typename T, typename... Properties>
0533 struct can_prefer :
0534   integral_constant<bool,
0535     boost_asio_prefer_fn::call_traits<
0536       prefer_t, T, void(Properties...)>::overload
0537         != boost_asio_prefer_fn::ill_formed>
0538 {
0539 };
0540 
0541 #if defined(BOOST_ASIO_HAS_VARIABLE_TEMPLATES)
0542 
0543 template <typename T, typename... Properties>
0544 constexpr bool can_prefer_v
0545   = can_prefer<T, Properties...>::value;
0546 
0547 #endif 
0548 
0549 template <typename T, typename... Properties>
0550 struct is_nothrow_prefer :
0551   integral_constant<bool,
0552     boost_asio_prefer_fn::call_traits<
0553       prefer_t, T, void(Properties...)>::is_noexcept>
0554 {
0555 };
0556 
0557 #if defined(BOOST_ASIO_HAS_VARIABLE_TEMPLATES)
0558 
0559 template <typename T, typename... Properties>
0560 constexpr bool is_nothrow_prefer_v = is_nothrow_prefer<T, Properties...>::value;
0561 
0562 #endif 
0563 
0564 template <typename T, typename... Properties>
0565 struct prefer_result
0566 {
0567   typedef typename boost_asio_prefer_fn::call_traits<
0568       prefer_t, T, void(Properties...)>::result_type type;
0569 };
0570 
0571 template <typename T, typename... Properties>
0572 using prefer_result_t = typename prefer_result<T, Properties...>::type;
0573 
0574 } 
0575 } 
0576 
0577 #endif 
0578 
0579 #include <boost/asio/detail/pop_options.hpp>
0580 
0581 #endif