Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-01-18 09:53:51

0001 ///////////////////////////////////////////////////////////////////////////////
0002 // grammar.hpp
0003 //
0004 //  Copyright 2008 Eric Niebler. Distributed under the Boost
0005 //  Software License, Version 1.0. (See accompanying file
0006 //  LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
0007 
0008 #ifndef BOOST_XPRESSIVE_DETAIL_STATIC_GRAMMAR_HPP_EAN_11_12_2006
0009 #define BOOST_XPRESSIVE_DETAIL_STATIC_GRAMMAR_HPP_EAN_11_12_2006
0010 
0011 // MS compatible compilers support #pragma once
0012 #if defined(_MSC_VER)
0013 # pragma once
0014 #endif
0015 
0016 #include <boost/mpl/if.hpp>
0017 #include <boost/mpl/bool.hpp>
0018 #include <boost/mpl/assert.hpp>
0019 #include <boost/proto/core.hpp>
0020 #include <boost/xpressive/detail/static/is_pure.hpp>
0021 #include <boost/xpressive/detail/static/transforms/as_matcher.hpp>
0022 #include <boost/xpressive/detail/static/transforms/as_alternate.hpp>
0023 #include <boost/xpressive/detail/static/transforms/as_sequence.hpp>
0024 #include <boost/xpressive/detail/static/transforms/as_quantifier.hpp>
0025 #include <boost/xpressive/detail/static/transforms/as_marker.hpp>
0026 #include <boost/xpressive/detail/static/transforms/as_set.hpp>
0027 #include <boost/xpressive/detail/static/transforms/as_independent.hpp>
0028 #include <boost/xpressive/detail/static/transforms/as_modifier.hpp>
0029 #include <boost/xpressive/detail/static/transforms/as_inverse.hpp>
0030 #include <boost/xpressive/detail/static/transforms/as_action.hpp>
0031 #include <boost/xpressive/detail/detail_fwd.hpp>
0032 
0033 #define BOOST_XPRESSIVE_CHECK_REGEX(Expr, Char)\
0034     BOOST_MPL_ASSERT\
0035     ((\
0036         typename boost::mpl::if_c<\
0037             boost::xpressive::is_valid_regex<Expr, Char>::value\
0038           , boost::mpl::true_\
0039           , boost::xpressive::INVALID_REGULAR_EXPRESSION\
0040         >::type\
0041     ));
0042 
0043 //////////////////////////////////////////////////////////////////////////
0044 //**********************************************************************//
0045 //*                            << NOTE! >>                             *//
0046 //*                                                                    *//
0047 //* Whenever you change this grammar, you MUST also make corresponding *//
0048 //* changes to width_of.hpp and is_pure.hpp.                           *//
0049 //*                                                                    *//
0050 //**********************************************************************//
0051 //////////////////////////////////////////////////////////////////////////
0052 
0053 namespace boost { namespace xpressive
0054 {
0055     template<typename Char>
0056     struct Grammar;
0057 
0058     template<typename Char>
0059     struct ActionableGrammar;
0060 
0061     namespace grammar_detail
0062     {
0063         ///////////////////////////////////////////////////////////////////////////
0064         // CharLiteral
0065         template<typename Char>
0066         struct CharLiteral;
0067 
0068         ///////////////////////////////////////////////////////////////////////////
0069         // ListSet
0070         template<typename Char>
0071         struct ListSet;
0072 
0073         ///////////////////////////////////////////////////////////////////////////
0074         // as_repeat
0075         template<typename Char, typename Gram, typename Greedy>
0076         struct as_repeat
0077           : if_<
0078                 make<detail::use_simple_repeat<_child, Char> >
0079               , as_simple_quantifier<Gram, Greedy>
0080               , as_default_quantifier<Greedy>
0081             >
0082         {};
0083 
0084         ///////////////////////////////////////////////////////////////////////////
0085         // NonGreedyRepeatCases
0086         template<typename Gram>
0087         struct NonGreedyRepeatCases
0088         {
0089             template<typename Tag, typename Dummy = void>
0090             struct case_
0091               : not_<_>
0092             {};
0093 
0094             template<typename Dummy>
0095             struct case_<tag::dereference, Dummy>
0096               : dereference<Gram>
0097             {};
0098 
0099             template<typename Dummy>
0100             struct case_<tag::unary_plus, Dummy>
0101               : unary_plus<Gram>
0102             {};
0103 
0104             template<typename Dummy>
0105             struct case_<tag::logical_not, Dummy>
0106               : logical_not<Gram>
0107             {};
0108 
0109             template<uint_t Min, uint_t Max, typename Dummy>
0110             struct case_<detail::generic_quant_tag<Min, Max>, Dummy>
0111               : unary_expr<detail::generic_quant_tag<Min, Max>, Gram>
0112             {};
0113         };
0114 
0115         ///////////////////////////////////////////////////////////////////////////
0116         // InvertibleCases
0117         template<typename Char, typename Gram>
0118         struct InvertibleCases
0119         {
0120             template<typename Tag, typename Dummy = void>
0121             struct case_
0122               : not_<_>
0123             {};
0124 
0125             template<typename Dummy>
0126             struct case_<tag::comma, Dummy>
0127               : when<ListSet<Char>, as_list_set_matcher<Char> >
0128             {};
0129 
0130             template<typename Dummy>
0131             struct case_<tag::assign, Dummy>
0132               : when<ListSet<Char>, as_list_set_matcher<Char> >
0133             {};
0134 
0135             template<typename Dummy>
0136             struct case_<tag::subscript, Dummy>
0137               : when<subscript<detail::set_initializer_type, Gram>, call<as_set_matcher<Gram>(_right)> >
0138             {};
0139 
0140             template<typename Dummy>
0141             struct case_<detail::lookahead_tag, Dummy>
0142               : when<
0143                     unary_expr<detail::lookahead_tag, Gram>
0144                   , as_lookahead<Gram>
0145                 >
0146             {};
0147 
0148             template<typename Dummy>
0149             struct case_<detail::lookbehind_tag, Dummy>
0150               : when<
0151                     unary_expr<detail::lookbehind_tag, Gram>
0152                   , as_lookbehind<Gram>
0153                 >
0154             {};
0155 
0156             template<typename Dummy>
0157             struct case_<tag::terminal, Dummy>
0158               : when<
0159                     or_<
0160                         CharLiteral<Char>
0161                       , terminal<detail::posix_charset_placeholder>
0162                       , terminal<detail::range_placeholder<_> >
0163                       , terminal<detail::logical_newline_placeholder>
0164                       , terminal<detail::assert_word_placeholder<detail::word_boundary<mpl::true_> > >
0165                     >
0166                   , as_matcher
0167                 >
0168             {};
0169         };
0170 
0171         ///////////////////////////////////////////////////////////////////////////
0172         // Cases
0173         template<typename Char, typename Gram>
0174         struct Cases
0175         {
0176             template<typename Tag, typename Dummy = void>
0177             struct case_
0178               : not_<_>
0179             {};
0180 
0181             template<typename Dummy>
0182             struct case_<tag::terminal, Dummy>
0183               : when<
0184                     _
0185                   , in_sequence<as_matcher>
0186                 >
0187             {};
0188 
0189             template<typename Dummy>
0190             struct case_<tag::shift_right, Dummy>
0191               : when<
0192                     shift_right<Gram, Gram>
0193                   , reverse_fold<_, _state, Gram>
0194                 >
0195             {};
0196 
0197             template<typename Dummy>
0198             struct case_<tag::bitwise_or, Dummy>
0199               : when<
0200                     bitwise_or<Gram, Gram>
0201                   , in_sequence<
0202                         as_alternate_matcher<
0203                             reverse_fold_tree<_, make<fusion::nil>, in_alternate_list<Gram> >
0204                         >
0205                     >
0206                 >
0207             {};
0208 
0209             template<typename Dummy, typename Greedy>
0210             struct case_<optional_tag<Greedy> , Dummy>
0211               : when<
0212                     unary_expr<optional_tag<Greedy>, Gram>
0213                   , in_sequence<call<as_optional<Gram, Greedy>(_child)> >
0214                 >
0215             {};
0216 
0217             template<typename Dummy>
0218             struct case_<tag::dereference, Dummy>
0219               : when<
0220                     dereference<Gram>
0221                   , call<Gram(as_repeat<Char, Gram, mpl::true_>)>
0222                 >
0223             {};
0224 
0225             template<typename Dummy>
0226             struct case_<tag::unary_plus, Dummy>
0227               : when<
0228                     unary_plus<Gram>
0229                   , call<Gram(as_repeat<Char, Gram, mpl::true_>)>
0230                 >
0231             {};
0232 
0233             template<typename Dummy>
0234             struct case_<tag::logical_not, Dummy>
0235               : when<
0236                     logical_not<Gram>
0237                   , call<Gram(as_repeat<Char, Gram, mpl::true_>)>
0238                 >
0239             {};
0240 
0241             template<uint_t Min, uint_t Max, typename Dummy>
0242             struct case_<detail::generic_quant_tag<Min, Max>, Dummy>
0243               : when<
0244                     unary_expr<detail::generic_quant_tag<Min, Max>, Gram>
0245                   , call<Gram(as_repeat<Char, Gram, mpl::true_>)>
0246                 >
0247             {};
0248 
0249             template<typename Dummy>
0250             struct case_<tag::negate, Dummy>
0251               : when<
0252                     negate<switch_<NonGreedyRepeatCases<Gram> > >
0253                   , call<Gram(call<as_repeat<Char, Gram, mpl::false_>(_child)>)>
0254                 >
0255             {};
0256 
0257             template<typename Dummy>
0258             struct case_<tag::complement, Dummy>
0259               : when<
0260                     complement<switch_<InvertibleCases<Char, Gram> > >
0261                   , in_sequence<call<as_inverse(call<switch_<InvertibleCases<Char, Gram> >(_child)>)> >
0262                 >
0263             {};
0264 
0265             template<typename Dummy>
0266             struct case_<detail::modifier_tag, Dummy>
0267               : when<binary_expr<detail::modifier_tag, _, Gram>, as_modifier<Gram> >
0268             {};
0269 
0270             template<typename Dummy>
0271             struct case_<detail::lookahead_tag, Dummy>
0272               : when<
0273                     unary_expr<detail::lookahead_tag, Gram>
0274                   , in_sequence<as_lookahead<Gram> >
0275                 >
0276             {};
0277 
0278             template<typename Dummy>
0279             struct case_<detail::lookbehind_tag, Dummy>
0280               : when<
0281                     unary_expr<detail::lookbehind_tag, Gram>
0282                   , in_sequence<as_lookbehind<Gram> >
0283                 >
0284             {};
0285 
0286             template<typename Dummy>
0287             struct case_<detail::keeper_tag, Dummy>
0288               : when<
0289                     unary_expr<detail::keeper_tag, Gram>
0290                   , in_sequence<as_keeper<Gram> >
0291                 >
0292             {};
0293 
0294             template<typename Dummy>
0295             struct case_<tag::comma, Dummy>
0296               : when<ListSet<Char>, in_sequence<as_list_set_matcher<Char> > >
0297             {};
0298 
0299             template<typename Dummy>
0300             struct case_<tag::assign, Dummy>
0301               : or_<
0302                     when<assign<detail::basic_mark_tag, Gram>, call<Gram(as_marker)> >
0303                   , when<ListSet<Char>, in_sequence<as_list_set_matcher<Char> > >
0304                 >
0305             {};
0306 
0307             template<typename Dummy>
0308             struct case_<tag::subscript, Dummy>
0309               : or_<
0310                     when<subscript<detail::set_initializer_type, Gram>, in_sequence<call<as_set_matcher<Gram>(_right)> > >
0311                   , when<subscript<ActionableGrammar<Char>, _>, call<ActionableGrammar<Char>(as_action)> >
0312                 >
0313             {};
0314         };
0315 
0316         ///////////////////////////////////////////////////////////////////////////
0317         // ActionableCases
0318         template<typename Char, typename Gram>
0319         struct ActionableCases
0320         {
0321             template<typename Tag, typename Dummy = void>
0322             struct case_
0323               : Cases<Char, Gram>::template case_<Tag>
0324             {};
0325 
0326             // Only in sub-expressions with actions attached do we allow attribute assignements
0327             template<typename Dummy>
0328             struct case_<proto::tag::assign, Dummy>
0329               : or_<
0330                     typename Cases<Char, Gram>::template case_<proto::tag::assign>
0331                   , when<proto::assign<terminal<detail::attribute_placeholder<_> >, _>, in_sequence<as_attr_matcher> >
0332                 >
0333             {};
0334         };
0335 
0336     } // namespace detail
0337 
0338     ///////////////////////////////////////////////////////////////////////////
0339     // Grammar
0340     template<typename Char>
0341     struct Grammar
0342       : proto::switch_<grammar_detail::Cases<Char, Grammar<Char> > >
0343     {};
0344 
0345     template<typename Char>
0346     struct ActionableGrammar
0347       : proto::switch_<grammar_detail::ActionableCases<Char, ActionableGrammar<Char> > >
0348     {};
0349 
0350     ///////////////////////////////////////////////////////////////////////////
0351     // INVALID_REGULAR_EXPRESSION
0352     struct INVALID_REGULAR_EXPRESSION
0353       : mpl::false_
0354     {};
0355 
0356     ///////////////////////////////////////////////////////////////////////////
0357     // is_valid_regex
0358     template<typename Expr, typename Char>
0359     struct is_valid_regex
0360       : proto::matches<Expr, Grammar<Char> >
0361     {};
0362 
0363 }} // namespace boost::xpressive
0364 
0365 #endif