]> git.proxmox.com Git - ceph.git/blobdiff - ceph/src/boost/boost/spirit/home/x3/nonterminal/rule.hpp
update ceph source to reef 18.1.2
[ceph.git] / ceph / src / boost / boost / spirit / home / x3 / nonterminal / rule.hpp
index b71c2e0ddd764f10cfa8305de67ad3a96efbebc4..0c8c9bcab59aa681b54ad3c2a9fa1b799c8be4b2 100644 (file)
 namespace boost { namespace spirit { namespace x3
 {
     // default parse_rule implementation
-    template <typename ID, typename Attribute, typename Iterator
+    template <typename ID, typename Iterator
       , typename Context, typename ActualAttribute>
     inline detail::default_parse_rule_result
     parse_rule(
-        rule<ID, Attribute> /* rule_ */
+        detail::rule_id<ID>
       , Iterator& first, Iterator const& last
       , Context const& context, ActualAttribute& attr)
     {
-        static_assert(!is_same<decltype(get<ID>(context)), unused_type>::value,
+        static_assert(!is_same<decltype(x3::get<ID>(context)), unused_type>::value,
             "BOOST_SPIRIT_DEFINE undefined for this rule.");
-        return get<ID>(context).parse(first, last, context, unused, attr);
+        return x3::get<ID>(context).parse(first, last, context, unused, attr);
     }
 
-    template <typename ID, typename RHS, typename Attribute, bool force_attribute_>
+    template <typename ID, typename RHS, typename Attribute, bool force_attribute_, bool skip_definition_injection = false>
     struct rule_definition : parser<rule_definition<ID, RHS, Attribute, force_attribute_>>
     {
-        typedef rule_definition<ID, RHS, Attribute, force_attribute_> this_type;
+        typedef rule_definition<ID, RHS, Attribute, force_attribute_, skip_definition_injection> this_type;
         typedef ID id;
         typedef RHS rhs_type;
-        typedef rule<ID, Attribute> lhs_type;
+        typedef rule<ID, Attribute, force_attribute_> lhs_type;
         typedef Attribute attribute_type;
 
         static bool const has_attribute =
@@ -58,7 +58,7 @@ namespace boost { namespace spirit { namespace x3
         bool parse(Iterator& first, Iterator const& last
           , Context const& context, unused_type, Attribute_& attr) const
         {
-            return detail::rule_parser<attribute_type, ID>
+            return detail::rule_parser<attribute_type, ID, skip_definition_injection>
                 ::call_rule_definition(
                     rhs, name, first, last
                   , context
@@ -71,7 +71,7 @@ namespace boost { namespace spirit { namespace x3
     };
 
     template <typename ID, typename Attribute, bool force_attribute_>
-    struct rule : parser<rule<ID, Attribute>>
+    struct rule : parser<rule<ID, Attribute, force_attribute_>>
     {
         static_assert(!std::is_reference<Attribute>::value,
                       "Reference qualifier on rule attribute type is meaningless");
@@ -105,7 +105,7 @@ namespace boost { namespace spirit { namespace x3
         template <typename RHS>
         constexpr rule_definition<
             ID, typename extension::as_parser<RHS>::value_type, Attribute, force_attribute_>
-        operator=(RHS const& rhs) const
+        operator=(RHS const& rhs) const&
         {
             return { as_parser(rhs), name };
         }
@@ -113,7 +113,27 @@ namespace boost { namespace spirit { namespace x3
         template <typename RHS>
         constexpr rule_definition<
             ID, typename extension::as_parser<RHS>::value_type, Attribute, true>
-        operator%=(RHS const& rhs) const
+        operator%=(RHS const& rhs) const&
+        {
+            return { as_parser(rhs), name };
+        }
+
+        // When a rule placeholder constructed and immediately consumed it cannot be used recursively,
+        // that's why the rule definition injection into a parser context can be skipped.
+        // This optimization has a huge impact on compile times because immediate rules are commonly
+        // used to cast an attribute like `as`/`attr_cast` does in Qi.
+        template <typename RHS>
+        constexpr rule_definition<
+            ID, typename extension::as_parser<RHS>::value_type, Attribute, force_attribute_, true>
+        operator=(RHS const& rhs) const&&
+        {
+            return { as_parser(rhs), name };
+        }
+
+        template <typename RHS>
+        constexpr rule_definition<
+            ID, typename extension::as_parser<RHS>::value_type, Attribute, true, true>
+        operator%=(RHS const& rhs) const&&
         {
             return { as_parser(rhs), name };
         }
@@ -132,7 +152,7 @@ namespace boost { namespace spirit { namespace x3
             using transform_attr = typename transform::type;
             transform_attr attr_ = transform::pre(attr);
 
-            if (parse_rule(*this, first, last, context, attr_)) {
+            if (parse_rule(detail::rule_id<ID>{}, first, last, context, attr_)) {
                 transform::post(attr, std::forward<transform_attr>(attr_));
                 return true;
             }
@@ -145,7 +165,7 @@ namespace boost { namespace spirit { namespace x3
         {
             // make sure we pass exactly the rule attribute type
             attribute_type no_attr{};
-            return parse_rule(*this, first, last, context, no_attr);
+            return parse_rule(detail::rule_id<ID>{}, first, last, context, no_attr);
         }
 
         char const* name;
@@ -156,11 +176,11 @@ namespace boost { namespace spirit { namespace x3
         template <typename T, typename Enable = void>
         struct is_rule : mpl::false_ {};
 
-        template <typename ID, typename Attribute>
-        struct is_rule<rule<ID, Attribute>> : mpl::true_ {};
+        template <typename ID, typename Attribute, bool force_attribute>
+        struct is_rule<rule<ID, Attribute, force_attribute>> : mpl::true_ {};
 
-        template <typename ID, typename Attribute, typename RHS, bool force_attribute>
-        struct is_rule<rule_definition<ID, RHS, Attribute, force_attribute>> : mpl::true_ {};
+        template <typename ID, typename Attribute, typename RHS, bool force_attribute, bool skip_definition_injection>
+        struct is_rule<rule_definition<ID, RHS, Attribute, force_attribute, skip_definition_injection>> : mpl::true_ {};
     }
 
     template <typename T>
@@ -177,7 +197,7 @@ namespace boost { namespace spirit { namespace x3
 #define BOOST_SPIRIT_DECLARE_(r, data, rule_type)                               \
     template <typename Iterator, typename Context>                              \
     bool parse_rule(                                                            \
-        rule_type rule_                                                         \
+        ::boost::spirit::x3::detail::rule_id<rule_type::id>                     \
       , Iterator& first, Iterator const& last                                   \
       , Context const& context, rule_type::attribute_type& attr);               \
     /***/
@@ -191,26 +211,34 @@ namespace boost { namespace spirit { namespace x3
     using BOOST_PP_CAT(rule_name, _synonym) = decltype(rule_name);              \
     template <typename Iterator, typename Context>                              \
     inline bool parse_rule(                                                     \
-        BOOST_PP_CAT(rule_name, _synonym) /* rule_ */                           \
+        ::boost::spirit::x3::detail::rule_id<BOOST_PP_CAT(rule_name, _synonym)::id> \
       , Iterator& first, Iterator const& last                                   \
       , Context const& context, BOOST_PP_CAT(rule_name, _synonym)::attribute_type& attr) \
     {                                                                           \
-        using boost::spirit::x3::unused;                                        \
-        static auto const def_ = (rule_name = BOOST_PP_CAT(rule_name, _def));   \
-        return def_.parse(first, last, context, unused, attr);                  \
+        using rule_t = BOOST_JOIN(rule_name, _synonym);                         \
+        return ::boost::spirit::x3::detail                                      \
+            ::rule_parser<typename rule_t::attribute_type, rule_t::id, true>    \
+            ::call_rule_definition(                                             \
+                BOOST_JOIN(rule_name, _def), rule_name.name                     \
+              , first, last, context, attr                                      \
+              , ::boost::mpl::bool_<rule_t::force_attribute>());                \
     }                                                                           \
     /***/
 #else
 #define BOOST_SPIRIT_DEFINE_(r, data, rule_name)                                \
     template <typename Iterator, typename Context>                              \
     inline bool parse_rule(                                                     \
-        decltype(rule_name) /* rule_ */                                         \
+        ::boost::spirit::x3::detail::rule_id<decltype(rule_name)::id>           \
       , Iterator& first, Iterator const& last                                   \
       , Context const& context, decltype(rule_name)::attribute_type& attr)      \
     {                                                                           \
-        using boost::spirit::x3::unused;                                        \
-        static auto const def_ = (rule_name = BOOST_PP_CAT(rule_name, _def));   \
-        return def_.parse(first, last, context, unused, attr);                  \
+        using rule_t = decltype(rule_name);                                     \
+        return ::boost::spirit::x3::detail                                      \
+            ::rule_parser<typename rule_t::attribute_type, rule_t::id, true>    \
+            ::call_rule_definition(                                             \
+                BOOST_JOIN(rule_name, _def), rule_name.name                     \
+              , first, last, context, attr                                      \
+              , ::boost::mpl::bool_<rule_t::force_attribute>());                \
     }                                                                           \
     /***/
 #endif
@@ -221,7 +249,7 @@ namespace boost { namespace spirit { namespace x3
 
 #define BOOST_SPIRIT_INSTANTIATE(rule_type, Iterator, Context)                  \
     template bool parse_rule<Iterator, Context>(                                \
-        rule_type rule_                                                         \
+        ::boost::spirit::x3::detail::rule_id<rule_type::id>                     \
       , Iterator& first, Iterator const& last                                   \
       , Context const& context, rule_type::attribute_type&);                    \
     /***/