Gaudi Framework, version v22r4

Home   Generated: Fri Sep 2 2011

Grammars.h

Go to the documentation of this file.
00001 // ============================================================================
00002 #ifndef GAUDIKERNEL_GRAMMARS_H
00003 #define GAUDIKERNEL_GRAMMARS_H 1
00004 #ifdef __GNUC__
00005 #warning \
00006   The headers GaudiKernel/Grammars.h and GaudiKernel/Parsers.icpp are deprecated \
00007   and will be removed from the next release of Gaudi. You should migrate your \
00008   code the new pasers based on Boost.Spirit 2.
00009 #endif
00010 // ============================================================================
00011 // Include files
00012 // ============================================================================
00013 // STD & STL
00014 // ============================================================================
00015 #include <cctype>
00016 // ============================================================================
00017 // Boost.Spirit
00018 // ============================================================================
00019 #include <boost/version.hpp>
00020 #if BOOST_VERSION >= 103800
00021 // FIXME: Move to the new boost::spirit::classic namespace
00022 #if !defined(BOOST_SPIRIT_USE_OLD_NAMESPACE)
00023 #define BOOST_SPIRIT_USE_OLD_NAMESPACE
00024 #endif
00025 #include <boost/spirit/include/classic.hpp>
00026 #include <boost/spirit/include/phoenix1.hpp>
00027 #else
00028 #include <boost/spirit.hpp>
00029 #include <boost/spirit/phoenix.hpp>
00030 #endif
00031 #include <boost/bind.hpp>
00032 
00033 // ============================================================================
00044 // ============================================================================
00045 namespace Gaudi
00046 {
00047   namespace Parsers
00048   {
00049     // ========================================================================
00050     using namespace boost::spirit ;
00051     // ========================================================================
00052     using namespace phoenix ;
00053     // ========================================================================
00062    template <typename T>
00063     struct ClosureGrammar : public boost::spirit::closure < ClosureGrammar<T>,T >
00064     {
00065       typedef  boost::spirit::closure<ClosureGrammar, T> closure;
00066       typename closure::member1 val;
00067     };
00068     // ========================================================================
00079     template <typename T1,typename T2>
00080     struct AttributesClosureGrammar
00081       : public boost::spirit::closure<AttributesClosureGrammar<T1,T2>,T1,T2>
00082     {
00083       typedef boost::spirit::closure<AttributesClosureGrammar, T1,T2> closure;
00084       typename closure::member1 val;
00085       typename closure::member2 attrs;
00086     };
00087     // ========================================================================
00099     class BoolGrammar : public grammar
00100     <
00101       BoolGrammar,
00102       ClosureGrammar<bool>::context_t
00103     >
00104     {
00105     public:
00106       typedef bool ResultT;
00107     public:
00108       template <typename ScannerT>
00109       struct definition
00110       {
00111         definition( BoolGrammar const &self)
00112         {
00113           boolean_literal
00114             = true_literal[self.val = true] | false_literal[self.val = false];
00115           true_literal
00116             = str_p("true" ) | str_p("True" ) | str_p("TRUE" ) | str_p("1");
00117           false_literal
00118             = str_p("false") | str_p("False") | str_p("FALSE") | str_p("0");
00119         }
00120         rule<ScannerT> const& start() const
00121         { return boolean_literal;}
00122         rule<ScannerT> boolean_literal,true_literal,false_literal;
00123       };
00124     };
00125     // ========================================================================
00136     template<typename RT=char>
00137     class CharGrammar : public grammar
00138     <
00139       CharGrammar<RT> , typename ClosureGrammar<RT>::context_t
00140     >
00141     {
00142     public:
00143       typedef RT ResultT;
00144     public:
00145       template <typename ScannerT>
00146       struct definition
00147       {
00148         definition( CharGrammar<RT> const &self)
00149         {
00150           char_literal
00151             = int_parser<RT>()[self.val=arg1]
00152             | ('\''
00153                >> ( str_p("\\'")[self.val='\'']
00154                     | (anychar_p[self.val=arg1]-'\'') )>>'\'');
00155         }
00156         rule<ScannerT> const& start() const
00157         { return char_literal; }
00158         rule<ScannerT> char_literal;
00159       };
00160     };
00161     // ========================================================================
00173     template<typename RT=int>
00174     class IntGrammar : public grammar
00175     <
00176       IntGrammar<RT>,
00177       typename ClosureGrammar<RT>::context_t
00178     >
00179     {
00180     public:
00181       typedef RT ResultT;
00182     public:
00183       template <typename ScannerT>
00184       struct definition
00185       {
00186         definition( IntGrammar<RT> const &self)
00187         {
00188           int_literal = lexeme_d[int_parser<RT>()[self.val=arg1]
00189             >> !(ch_p('u') | ch_p('U') | ch_p('l') | ch_p('L'))];
00190         }
00191         rule<ScannerT> const& start() const { return int_literal; }
00192         rule<ScannerT> int_literal;
00193       };
00194     };
00195     // ========================================================================
00207     template<typename RT=double>
00208     class RealGrammar : public grammar
00209     <
00210       RealGrammar<RT>,typename ClosureGrammar<RT>::context_t
00211     >
00212     {
00213     public:
00214       typedef RT ResultT;
00215     public:
00216       template <typename ScannerT>
00217       struct definition
00218       {
00219         definition( RealGrammar const &self)
00220         {
00221           real_literal
00222             = lexeme_d[real_parser<RT,
00223             real_parser_policies<RT> >()[self.val = arg1]
00224             >> !(ch_p('f') | ch_p('F') | ch_p('l') | ch_p('L'))];
00225         }
00226         rule<ScannerT> const& start() const
00227         { return real_literal; }
00228         rule<ScannerT> real_literal;
00229       };
00230     };
00231     // ========================================================================
00246     class StringGrammar : public grammar
00247     <
00248       StringGrammar, ClosureGrammar<std::string>::context_t
00249     >
00250     {
00251     public:
00252       typedef std::string ResultT;
00261       void matchString() const
00262       {
00263         for ( std::string::iterator cur=this->val().begin();
00264               cur!=this->val().end();cur++)
00265         { if(std::isspace(*cur) ) { *cur = ' '; } }
00266       }
00267     public:
00268         template <typename ScannerT>
00269         struct definition
00270         {
00271           definition( StringGrammar const &self )
00272           {
00273             string_literal = (lexeme_d
00274               [
00275                ('"' >> (*( str_p("\\\"")
00276                            |
00277                            (anychar_p-'"') ))
00278                 [self.val = construct_<std::string>
00279                  (arg1,arg2)] >>
00280                 '"')
00281                |
00282                ('\'' >> (*( str_p("\\'")
00283                             |
00284                             (anychar_p-'\'') ))
00285                 [self.val = construct_<std::string>
00286                  (arg1,arg2)]>>
00287                 '\'')])[boost::bind(&StringGrammar::matchString,&self)];
00288           }
00289           rule<ScannerT> const& start() const { return string_literal; }
00290           rule<ScannerT> string_literal;
00291         };
00292       };
00293     // ========================================================================
00306     class SkipperGrammar : public grammar<SkipperGrammar>
00307     {
00308     public:
00312       SkipperGrammar ( const bool skipnewline = true )
00313         : m_skipnewline(skipnewline){}
00314     public:
00316       bool skipnewline() const{return m_skipnewline;}
00317     public:
00318       template <typename ScannerT>
00319       struct definition
00320       {
00321         definition( SkipperGrammar const& self)
00322         {
00323           if ( self.skipnewline() )
00324           {
00325             skip
00326               =   space_p
00327               |   comment_p("//")     // C++ comment
00328               |   comment_p("/*", "*/")     // C comment
00329               ;
00330           }
00331           else
00332           {
00333             skip
00334               =   (space_p-eol_p)
00335               |   comment_p("//")     // C++ comment
00336               |   comment_p("/*", "*/")     // C comment
00337               ;
00338           }
00339         }
00340         rule<ScannerT>  skip;
00341         rule<ScannerT> const& start() const { return skip; }
00342       };
00343     private:
00344       bool m_skipnewline;
00345     };
00346     // ========================================================================
00357     template <typename KeyGrammarT, typename ValueGrammarT>
00358     class PairGrammar : public grammar
00359     <
00360       PairGrammar<KeyGrammarT,ValueGrammarT>,
00361       typename ClosureGrammar<
00362       std::pair<typename KeyGrammarT::ResultT,
00363                 typename ValueGrammarT::ResultT> >::context_t
00364     >
00365     {
00366     public:
00367       typedef typename KeyGrammarT::ResultT KeyT;
00368       typedef typename ValueGrammarT::ResultT ValueT;
00369       typedef std::pair<KeyT,ValueT> ResultT;
00370     public:
00374       PairGrammar ( const std::string&  delim = "," )
00375         : m_delim(delim) {}
00376     public:
00378       void matchFirst  ( const KeyT&   first  ) const { this->val().first = first; }
00380       void matchSecond ( const ValueT& second ) const { this->val().second = second; }
00381     public:
00382       template <typename ScannerT>
00383       struct definition
00384       {
00385         definition( PairGrammar const &self)
00386         {
00387           para
00388             = (
00389                str_p("(")
00390                >> (grkey[boost::bind(&PairGrammar::matchFirst,&self,_1)])
00391                >> self.delim().c_str()
00392                >> (grvalue[boost::bind(&PairGrammar::matchSecond,&self,_1)])
00393                >> str_p(")")
00394                ) ;
00395         }
00396         rule<ScannerT> const& start() const { return para; }
00397         rule<ScannerT> para;
00398         KeyGrammarT grkey;
00399         ValueGrammarT grvalue;
00400       };
00401     public:
00403       const std::string& delim() const { return m_delim ; }
00407       void setDelim ( const std::string& delim ) { m_delim = delim;}
00408     private:
00409       std::string m_delim;
00410     };
00411     // ========================================================================
00423     template <typename GrammarT>
00424     class VectorGrammar : public grammar
00425     <
00426       VectorGrammar<GrammarT> ,
00427       typename ClosureGrammar<std::vector<typename GrammarT::ResultT> >::context_t
00428     >
00429     {
00430     public:
00431       typedef typename GrammarT::ResultT ValueT;
00432       typedef std::vector<ValueT> ResultT;
00433       typedef VectorGrammar<GrammarT> SelfT;
00434     public:
00436       void matchItem(const ValueT& value) const { this->val().push_back(value); }
00437     public:
00438       template <typename ScannerT>
00439       struct definition
00440       {
00441         definition(SelfT const &self)
00442         {
00443           inner =
00444             !(gr[boost::bind(&VectorGrammar::matchItem,&self,_1)]
00445               >> *(','>>gr[boost::bind(&VectorGrammar::matchItem,&self,_1)]));
00446           vec =
00447             '[' >> inner >> ']' |  // a'la python list
00448             '(' >> inner >> ')' |  // a'la python tuple
00449             '{' >> inner >> '}' ;  // like obsolete list from opts-grammar
00450         }
00451         rule<ScannerT> const& start() const { return vec; }
00452         rule<ScannerT> vec,inner;
00453         GrammarT gr;
00454       };
00455     };
00456     // ========================================================================
00471     template <typename KeyGrammarT, typename ValueGrammarT>
00472     class MapGrammar : public grammar
00473     <
00474       MapGrammar<KeyGrammarT,ValueGrammarT>,
00475       typename AttributesClosureGrammar
00476       < std::map<typename KeyGrammarT::ResultT,
00477                  typename ValueGrammarT::ResultT>,
00478         std::pair<typename KeyGrammarT::ResultT,
00479                   typename ValueGrammarT::ResultT> >::context_t
00480     >
00481     {
00482     public:
00483       typedef typename KeyGrammarT::ResultT KeyT;
00484       typedef typename ValueGrammarT::ResultT ValueT;
00485       typedef std::map<KeyT,ValueT> ResultT;
00486     public:
00488       void matchItem  () const
00489       {
00490         //this->val().insert(this->attrs());
00491         this->val()[this->attrs().first] = this->attrs().second ;
00492       }
00494       void matchFirst ( const KeyT&   value ) const {  this->attrs().first = value ; }
00496       void matchSecond( const ValueT& value ) const { this->attrs().second = value ; }
00497     public:
00498       template <typename ScannerT>
00499       struct definition
00500       {
00501         definition( MapGrammar const &self)
00502         {
00503           vec
00504             = ('{'>> inner_list >> '}') | ('['>>inner_list>>']');
00505           inner_list
00506             =
00507             !( inner[boost::bind(&MapGrammar::matchItem,&self)]
00508                >> *( ch_p(',') >>
00509                      inner[boost::bind(&MapGrammar::matchItem,&self)] )
00510                );
00511           inner
00512             =
00513             grKey[boost ::bind(&MapGrammar::matchFirst,&self,_1)]
00514               >> ( ch_p('=') | ch_p(':'))
00515               >> grValue[boost::bind(&MapGrammar::matchSecond,&self,_1)] ;
00516         }
00517         KeyGrammarT grKey;
00518         ValueGrammarT grValue;
00519         rule<ScannerT> const& start() const { return vec; }
00520         rule<ScannerT> vec,inner, inner_list ;
00521       };
00522     };
00523     // ========================================================================
00524   } // end of namespace Gaudi::Parsers
00525 } // end of namespace Gaudi
00526 // ============================================================================
00527 // The END
00528 // ============================================================================
00529 #endif // GAUDIKERNEL_GRAMMARS_H
00530 // ============================================================================
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Defines

Generated at Fri Sep 2 2011 16:24:21 for Gaudi Framework, version v22r4 by Doxygen version 1.7.2 written by Dimitri van Heesch, © 1997-2004