]> git.proxmox.com Git - ceph.git/blobdiff - ceph/src/boost/boost/spirit/repository/home/karma/nonterminal/subrule.hpp
update sources to ceph Nautilus 14.2.1
[ceph.git] / ceph / src / boost / boost / spirit / repository / home / karma / nonterminal / subrule.hpp
index a2893bc404b029e0cf35676851be72977a38dea7..4eaee8e33a49a1adabb59bccda5a716f7574594f 100644 (file)
 namespace boost { namespace spirit { namespace repository { namespace karma
 {
     ///////////////////////////////////////////////////////////////////////////
-    // subrule_group:
+    // subrule_group_generator:
     // - generator representing a group of subrule definitions (one or more),
     //   invokes first subrule on entry,
-    // - also a Proto terminal, so that a group behaves like any Spirit
-    //   expression.
     ///////////////////////////////////////////////////////////////////////////
     template <typename Defs>
-    struct subrule_group
-      : proto::extends<
-            typename proto::terminal<
-                spirit::karma::reference<subrule_group<Defs> const>
-            >::type
-          , subrule_group<Defs>
-        >
-      , spirit::karma::generator<subrule_group<Defs> >
+    struct subrule_group_generator
+      : spirit::karma::generator<subrule_group_generator<Defs> >
     {
-        struct properties
-            // Forward to first subrule.
-          : remove_reference<
-                typename fusion::result_of::front<Defs>::type
-            >::type::second_type::subject_type::properties {};
-
         // Fusion associative sequence, associating each subrule ID in this
         // group (as an MPL integral constant) with its definition
         typedef Defs defs_type;
 
-        typedef subrule_group<Defs> this_type;
-        typedef spirit::karma::reference<this_type const> reference_;
-        typedef typename proto::terminal<reference_>::type terminal;
-        typedef proto::extends<terminal, this_type> base_type;
-
-        static size_t const params_size =
-            // Forward to first subrule.
-            remove_reference<
-                typename fusion::result_of::front<Defs>::type
-            >::type::second_type::params_size;
-
-        subrule_group(subrule_group const& rhs)
-          : base_type(terminal::make(reference_(*this)))
-          , defs(rhs.defs)
-        {
-        }
+        typedef subrule_group_generator<Defs> this_type;
 
-        explicit subrule_group(Defs const& defs)
-          : base_type(terminal::make(reference_(*this)))
-          , defs(defs)
+        explicit subrule_group_generator(Defs const& defs)
+          : defs(defs)
         {
         }
-
         // from a subrule ID, get the type of a reference to its definition
         template <int ID>
         struct def_type
@@ -255,6 +224,47 @@ namespace boost { namespace spirit { namespace repository { namespace karma
             return fusion::front(defs).second.binder.g.what(context);
         }
 
+        Defs defs;
+    };
+
+    ///////////////////////////////////////////////////////////////////////////
+    // subrule_group:
+    // - a Proto terminal, so that a group behaves like any Spirit
+    //   expression.
+    ///////////////////////////////////////////////////////////////////////////
+    template <typename Defs>
+    struct subrule_group
+      : proto::extends<
+            typename proto::terminal<
+                subrule_group_generator<Defs>
+            >::type
+          , subrule_group<Defs>
+        >
+    {
+        typedef subrule_group_generator<Defs> generator_type;
+        typedef typename proto::terminal<generator_type>::type terminal;
+
+        struct properties
+            // Forward to first subrule.
+          : remove_reference<
+                typename fusion::result_of::front<Defs>::type
+            >::type::second_type::subject_type::properties {};
+
+        static size_t const params_size =
+            // Forward to first subrule.
+            remove_reference<
+                typename fusion::result_of::front<Defs>::type
+            >::type::second_type::params_size;
+
+        explicit subrule_group(Defs const& defs)
+          : subrule_group::proto_extends(terminal::make(generator_type(defs)))
+        {
+        }
+
+        generator_type const& generator() const { return proto::value(*this); }
+
+        Defs const& defs() const { return generator().defs; }
+
         template <typename Defs2>
         subrule_group<
             typename fusion::result_of::as_map<
@@ -266,15 +276,29 @@ namespace boost { namespace spirit { namespace repository { namespace karma
                 typename fusion::result_of::as_map<
                     typename fusion::result_of::join<
                         Defs const, Defs2 const>::type>::type> result_type;
-            return result_type(fusion::as_map(fusion::join(defs, other.defs)));
+            return result_type(fusion::as_map(fusion::join(defs(), other.defs())));
+        }
+
+        // non-const versions needed to suppress proto's comma op kicking in
+        template <typename Defs2>
+        friend subrule_group<
+            typename fusion::result_of::as_map<
+                typename fusion::result_of::join<
+                    Defs const, Defs2 const>::type>::type>
+#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
+        operator,(subrule_group&& left, subrule_group<Defs2>&& other)
+#else
+        operator,(subrule_group& left, subrule_group<Defs2>& other)
+#endif
+        {
+            return static_cast<subrule_group const&>(left)
+                .operator,(static_cast<subrule_group<Defs2> const&>(other));
         }
 
         // bring in the operator() overloads
-        this_type const& get_parameterized_subject() const { return *this; }
-        typedef this_type parameterized_subject_type;
+        generator_type const& get_parameterized_subject() const { return generator(); }
+        typedef generator_type parameterized_subject_type;
         #include <boost/spirit/home/karma/nonterminal/detail/fcall.hpp>
-
-        Defs defs;
     };
 
     ///////////////////////////////////////////////////////////////////////////
@@ -351,13 +375,20 @@ namespace boost { namespace spirit { namespace repository { namespace karma
 
         typedef mpl::vector<T1, T2> template_params;
 
-        // locals_type is a sequence of types to be used as local variables
+        // The subrule's locals_type: a sequence of types to be used as local variables
         typedef typename
             spirit::detail::extract_locals<template_params>::type
         locals_type;
 
+        // The subrule's encoding type
+        typedef typename
+            spirit::detail::extract_encoding<template_params>::type
+        encoding_type;
+
+        // The subrule's signature
         typedef typename
-            spirit::detail::extract_sig<template_params>::type
+            spirit::detail::extract_sig<template_params, encoding_type
+              , spirit::karma::domain>::type
         sig_type;
 
         // This is the subrule's attribute type
@@ -435,42 +466,34 @@ namespace boost { namespace spirit { namespace repository { namespace karma
                 def_type(compile<spirit::karma::domain>(expr), name_)));
         }
 
-        template <typename Expr>
-        friend typename group_type_helper<Expr, true>::type
-        operator%=(subrule const& sr, Expr const& expr)
-        {
-            typedef group_type_helper<Expr, true> helper;
-            typedef typename helper::def_type def_type;
-            typedef typename helper::type result_type;
-            return result_type(fusion::make_map<id_type>(
-                def_type(compile<spirit::karma::domain>(expr), sr.name_)));
-        }
+#define SUBRULE_MODULUS_ASSIGN_OPERATOR(lhs_ref, rhs_ref)                     \
+        template <typename Expr>                                              \
+        friend typename group_type_helper<Expr, true>::type                   \
+        operator%=(subrule lhs_ref sr, Expr rhs_ref expr)                     \
+        {                                                                     \
+            typedef group_type_helper<Expr, true> helper;                     \
+            typedef typename helper::def_type def_type;                       \
+            typedef typename helper::type result_type;                        \
+            return result_type(fusion::make_map<id_type>(                     \
+                def_type(compile<spirit::karma::domain>(expr), sr.name_)));   \
+        }                                                                     \
+        /**/
 
         // non-const versions needed to suppress proto's %= kicking in
-        template <typename Expr>
-        friend typename group_type_helper<Expr, true>::type
-        operator%=(subrule const& sr, Expr& expr)
-        {
-            return operator%=(
-                sr
-              , static_cast<Expr const&>(expr));
-        }
-        template <typename Expr>
-        friend typename group_type_helper<Expr, true>::type
-        operator%=(subrule& sr, Expr const& expr)
-        {
-            return operator%=(
-                static_cast<subrule const&>(sr)
-              , expr);
-        }
-        template <typename Expr>
-        friend typename group_type_helper<Expr, true>::type
-        operator%=(subrule& sr, Expr& expr)
-        {
-            return operator%=(
-                static_cast<subrule const&>(sr)
-              , static_cast<Expr const&>(expr));
-        }
+        SUBRULE_MODULUS_ASSIGN_OPERATOR(const&, const&)
+#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
+        SUBRULE_MODULUS_ASSIGN_OPERATOR(const&, &&)
+#else
+        SUBRULE_MODULUS_ASSIGN_OPERATOR(const&, &)
+#endif
+        SUBRULE_MODULUS_ASSIGN_OPERATOR(&, const&)
+#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
+        SUBRULE_MODULUS_ASSIGN_OPERATOR(&, &&)
+#else
+        SUBRULE_MODULUS_ASSIGN_OPERATOR(&, &)
+#endif
+
+#undef SUBRULE_MODULUS_ASSIGN_OPERATOR
 
         std::string const& name() const
         {