00001 #ifndef CommonTools_Utils_Grammar_h
00002 #define CommonTools_Utils_Grammar_h
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013 #include "boost/spirit/include/classic_core.hpp"
00014 #include "boost/spirit/include/classic_grammar_def.hpp"
00015 #include "boost/spirit/include/classic_chset.hpp"
00016 #include <functional>
00017 #include "CommonTools/Utils/src/ExpressionNumberSetter.h"
00018 #include "CommonTools/Utils/src/ExpressionVarSetter.h"
00019 #include "CommonTools/Utils/src/ExpressionFunctionSetter.h"
00020 #include "CommonTools/Utils/src/ExpressionConditionSetter.h"
00021 #include "CommonTools/Utils/src/ComparisonSetter.h"
00022 #include "CommonTools/Utils/src/BinarySelectorSetter.h"
00023 #include "CommonTools/Utils/src/TrinarySelectorSetter.h"
00024 #include "CommonTools/Utils/src/IntSetter.h"
00025 #include "CommonTools/Utils/src/MethodStack.h"
00026 #include "CommonTools/Utils/src/MethodArgumentStack.h"
00027 #include "CommonTools/Utils/src/TypeStack.h"
00028 #include "CommonTools/Utils/src/IntStack.h"
00029 #include "CommonTools/Utils/src/FunctionSetter.h"
00030 #include "CommonTools/Utils/src/CutSetter.h"
00031 #include "CommonTools/Utils/src/BinaryCutSetter.h"
00032 #include "CommonTools/Utils/src/UnaryCutSetter.h"
00033 #include "CommonTools/Utils/src/ExpressionSetter.h"
00034 #include "CommonTools/Utils/src/ExpressionBinaryOperatorSetter.h"
00035 #include "CommonTools/Utils/src/ExpressionUnaryOperatorSetter.h"
00036 #include "CommonTools/Utils/src/ExpressionSelectorSetter.h"
00037 #include "CommonTools/Utils/src/MethodSetter.h"
00038 #include "CommonTools/Utils/src/MethodArgumentSetter.h"
00039 #include "CommonTools/Utils/interface/Exception.h"
00040
00041
00042 namespace reco {
00043 namespace parser {
00044 struct Grammar : public boost::spirit::classic::grammar<Grammar> {
00045
00046 SelectorPtr dummySel_;
00047 ExpressionPtr dummyExpr_;
00048 SelectorPtr * sel_;
00049 ExpressionPtr * expr_;
00050 bool lazy_;
00051 mutable ExpressionStack exprStack;
00052 mutable ComparisonStack cmpStack;
00053 mutable SelectorStack selStack;
00054 mutable FunctionStack funStack, finalFunStack;
00055 mutable MethodStack methStack;
00056 mutable LazyMethodStack lazyMethStack;
00057 mutable MethodArgumentStack methArgStack;
00058 mutable TypeStack typeStack;
00059 mutable IntStack intStack;
00060
00061 Grammar(SelectorPtr & sel, const Reflex::Type& iType, bool lazy=false) :
00062 sel_(& sel), expr_(& dummyExpr_), lazy_(lazy) {
00063 typeStack.push_back(iType);
00064 }
00065
00066 Grammar(ExpressionPtr & expr, const Reflex::Type& iType, bool lazy=false) :
00067 sel_(& dummySel_), expr_(& expr), lazy_(lazy) {
00068 typeStack.push_back(iType);
00069 }
00070 template <typename ScannerT>
00071 struct definition :
00072 public boost::spirit::classic::grammar_def<boost::spirit::classic::rule<ScannerT>,
00073 boost::spirit::classic::same,
00074 boost::spirit::classic::same>{
00075 typedef boost::spirit::classic::rule<ScannerT> rule;
00076 rule number, var, arrayAccess, metharg, method, term, power, factor, function1, function2, function4, expression,
00077 comparison_op, binary_comp, trinary_comp,
00078 logical_combiner, logical_expression, nocond_expression, cond_expression, logical_factor, logical_term,
00079 or_op, and_op, cut, fun;
00080 definition(const Grammar & self) {
00081 using namespace boost::spirit::classic;
00082 using namespace std;
00083
00084 ExpressionNumberSetter number_s(self.exprStack);
00085 IntSetter int_s(self.intStack);
00086 ExpressionVarSetter var_s(self.exprStack, self.methStack, self.lazyMethStack, self.typeStack);
00087 ExpressionConditionSetter cond_s(self.exprStack, self.selStack);
00088 MethodArgumentSetter methodArg_s(self.methArgStack);
00089 MethodSetter method_s(self.methStack, self.lazyMethStack, self.typeStack, self.methArgStack, self.lazy_);
00090 ComparisonSetter<less_equal<double> > less_equal_s(self.cmpStack);
00091 ComparisonSetter<less<double> > less_s(self.cmpStack);
00092 ComparisonSetter<equal_to<double> > equal_to_s(self.cmpStack);
00093 ComparisonSetter<greater_equal<double> > greater_equal_s(self.cmpStack);
00094 ComparisonSetter<greater<double> > greater_s(self.cmpStack);
00095 ComparisonSetter<not_equal_to<double> > not_equal_to_s(self.cmpStack);
00096 FunctionSetter
00097 abs_s(kAbs, self.funStack), acos_s(kAcos, self.funStack), asin_s(kAsin, self.funStack),
00098 atan2_s(kAtan, self.funStack), atan_s(kAtan, self.funStack),
00099 chi2prob_s(kChi2Prob, self.funStack),
00100 cosh_s(kCosh, self.funStack),
00101 cos_s(kCos, self.funStack), exp_s(kExp, self.funStack), hypot_s(kHypot, self.funStack), log_s(kLog, self.funStack),
00102 log10_s(kLog10, self.funStack), max_s(kMax, self.funStack), min_s(kMin, self.funStack),
00103 pow_s(kPow, self.funStack), sinh_s(kSinh, self.funStack),
00104 sin_s(kSin, self.funStack), sqrt_s(kSqrt, self.funStack), tanh_s(kTanh, self.funStack),
00105 tan_s(kTan, self.funStack),
00106 deltaPhi_s(kDeltaPhi, self.funStack), deltaR_s(kDeltaR, self.funStack),
00107 test_bit_s(kTestBit, self.funStack);
00108 FunctionSetterCommit funOk_s(self.funStack, self.finalFunStack);
00109 TrinarySelectorSetter trinary_s(self.selStack, self.cmpStack, self.exprStack);
00110 BinarySelectorSetter binary_s(self.selStack, self.cmpStack, self.exprStack);
00111 ExpressionSelectorSetter expr_sel_s(self.selStack, self.exprStack);
00112 BinaryCutSetter<logical_and<bool> > and_s(self.selStack);
00113 BinaryCutSetter<logical_or<bool> > or_s(self.selStack);
00114 UnaryCutSetter<logical_not<bool> > not_s(self.selStack);
00115 CutSetter cut_s(* self.sel_, self.selStack);
00116 ExpressionSetter expr_s(* self.expr_, self.exprStack);
00117 ExpressionBinaryOperatorSetter<plus<double> > plus_s(self.exprStack);
00118 ExpressionBinaryOperatorSetter<minus<double> > minus_s(self.exprStack);
00119 ExpressionBinaryOperatorSetter<multiplies<double> > multiplies_s(self.exprStack);
00120 ExpressionBinaryOperatorSetter<divides<double> > divides_s(self.exprStack);
00121 ExpressionBinaryOperatorSetter<power_of<double> > power_of_s(self.exprStack);
00122 ExpressionUnaryOperatorSetter<negate<double> > negate_s(self.exprStack);
00123 ExpressionFunctionSetter fun_s(self.exprStack, self.finalFunStack);
00124
00125 BOOST_SPIRIT_DEBUG_RULE(var);
00126 BOOST_SPIRIT_DEBUG_RULE(arrayAccess);
00127 BOOST_SPIRIT_DEBUG_RULE(method);
00128 BOOST_SPIRIT_DEBUG_RULE(logical_expression);
00129 BOOST_SPIRIT_DEBUG_RULE(cond_expression);
00130 BOOST_SPIRIT_DEBUG_RULE(logical_term);
00131 BOOST_SPIRIT_DEBUG_RULE(logical_factor);
00132 BOOST_SPIRIT_DEBUG_RULE(number);
00133 BOOST_SPIRIT_DEBUG_RULE(metharg);
00134 BOOST_SPIRIT_DEBUG_RULE(function1);
00135 BOOST_SPIRIT_DEBUG_RULE(function2);
00136 BOOST_SPIRIT_DEBUG_RULE(function4);
00137 BOOST_SPIRIT_DEBUG_RULE(expression);
00138 BOOST_SPIRIT_DEBUG_RULE(term);
00139 BOOST_SPIRIT_DEBUG_RULE(power);
00140 BOOST_SPIRIT_DEBUG_RULE(factor);
00141 BOOST_SPIRIT_DEBUG_RULE(or_op);
00142 BOOST_SPIRIT_DEBUG_RULE(and_op);
00143 BOOST_SPIRIT_DEBUG_RULE(comparison_op);
00144 BOOST_SPIRIT_DEBUG_RULE(binary_comp);
00145 BOOST_SPIRIT_DEBUG_RULE(trinary_comp);
00146 BOOST_SPIRIT_DEBUG_RULE(cut);
00147 BOOST_SPIRIT_DEBUG_RULE(fun);
00148
00149 boost::spirit::classic::assertion<SyntaxErrors> expectParenthesis(kMissingClosingParenthesis);
00150 boost::spirit::classic::assertion<SyntaxErrors> expect(kSyntaxError);
00151
00152 number =
00153 real_p [ number_s ];
00154 metharg = ( strict_real_p [ methodArg_s ] ) |
00155 ( int_p [ methodArg_s ] ) |
00156 ( ch_p('"' ) >> *(~ch_p('"' )) >> ch_p('"' ) ) [ methodArg_s ] |
00157 ( ch_p('\'') >> *(~ch_p('\'')) >> ch_p('\'') ) [ methodArg_s ];
00158 var =
00159 (lexeme_d[alpha_p >> * chset<>("a-zA-Z0-9_")] >>
00160 ch_p('(') >> metharg >> * (ch_p(',') >> metharg ) >> expectParenthesis(ch_p(')'))) [ method_s ] |
00161 ( (lexeme_d[alpha_p >> * chset<>("a-zA-Z0-9_")]) [ method_s ] >> ! (ch_p('(') >> ch_p(')')) ) ;
00162 arrayAccess = ( ch_p('[') >> metharg >> * (ch_p(',') >> metharg ) >> expectParenthesis(ch_p(']'))) [ method_s ];
00163 method =
00164 (var >> * (arrayAccess | (ch_p('.') >> expect(var)))) [ var_s ];
00165 function1 =
00166 chseq_p("abs") [ abs_s ] | chseq_p("acos") [ acos_s ] | chseq_p("asin") [ asin_s ] |
00167 chseq_p("atan") [ atan_s ] | chseq_p("cosh") [ cosh_s ] | chseq_p("cos") [ cos_s ] |
00168 chseq_p("exp") [ exp_s ] | chseq_p("log") [ log_s ] | chseq_p("log10") [ log10_s ] |
00169 chseq_p("sinh") [ sinh_s ] | chseq_p("sin") [ sin_s ] | chseq_p("sqrt") [ sqrt_s ] |
00170 chseq_p("tanh") [ tanh_s ] | chseq_p("tan") [ tan_s ];
00171 function2 =
00172 chseq_p("atan2") [ atan2_s ] | chseq_p("chi2prob") [ chi2prob_s ] | chseq_p("pow") [ pow_s ] |
00173 chseq_p("min") [ min_s ] | chseq_p("max") [ max_s ] | chseq_p("deltaPhi") [deltaPhi_s] | chseq_p("hypot") [hypot_s] | chseq_p("test_bit") [test_bit_s] ;
00174 function4 =
00175 chseq_p("deltaR") [deltaR_s];
00176 expression =
00177 cond_expression |
00178 nocond_expression;
00179 nocond_expression =
00180 term >> (* (('+' >> expect(term)) [ plus_s ] |
00181 ('-' >> expect(term)) [ minus_s ]));
00182 cond_expression =
00183 (ch_p('?') >> logical_expression >> ch_p('?') >> expect(expression) >> ch_p(":") >> expect(expression)) [cond_s];
00184 term =
00185 power >> * (('*' >> expect(power)) [ multiplies_s ] |
00186 ('/' >> expect(power)) [ divides_s ]);
00187 power =
00188 factor >> * (('^' >> expect(factor)) [ power_of_s ]);
00189 factor =
00190 number |
00191 (function1 >> ch_p('(') [funOk_s ] >> expect(expression) >> expectParenthesis(ch_p(')'))) [ fun_s ] |
00192 (function2 >> ch_p('(') [funOk_s ] >> expect(expression) >>
00193 expect(ch_p(',')) >> expect(expression) >> expectParenthesis(ch_p(')'))) [ fun_s ] |
00194 (function4 >> ch_p('(') [funOk_s ] >> expect(expression) >> expect(ch_p(',')) >> expect(expression) >> expect(ch_p(',')) >> expect(expression) >>
00195 expect(ch_p(',')) >> expect(expression) >> expectParenthesis(ch_p(')'))) [ fun_s ] |
00196
00197 method |
00198
00199
00200
00201
00202
00203
00204
00205 ch_p('(') >> expression >> ch_p(')') |
00206 (ch_p('-') >> factor) [ negate_s ] |
00207 (ch_p('+') >> factor);
00208 comparison_op =
00209 (ch_p('<') >> ch_p('=') [ less_equal_s ]) |
00210 (ch_p('<') [ less_s ]) |
00211 (ch_p('=') >> ch_p('=') [ equal_to_s ]) |
00212 (ch_p('=') [ equal_to_s ]) |
00213 (ch_p('>') >> ch_p('=') [ greater_equal_s ]) |
00214 (ch_p('>') [ greater_s ]) |
00215 (ch_p('!') >> ch_p('=') [ not_equal_to_s ]);
00216 binary_comp =
00217 (expression >> comparison_op >> expect(expression)) [ binary_s ];
00218 trinary_comp =
00219 (expression >> comparison_op >> expect(expression) >> comparison_op >> expect(expression)) [ trinary_s ];
00220 or_op = ch_p('|') >> ch_p('|') | ch_p('|');
00221 and_op = ch_p('&') >> ch_p('&') | ch_p('&');
00222 logical_expression =
00223 logical_term >> * (or_op >> expect(logical_term)) [ or_s ];
00224 logical_term =
00225 logical_factor >> * (and_op >> expect(logical_factor)) [ and_s ];
00226 logical_factor =
00227 trinary_comp |
00228 binary_comp |
00229 ch_p('(') >> logical_expression >> expectParenthesis(ch_p(')')) |
00230 (ch_p('!') >> expect(logical_factor)) [ not_s ] |
00231 expression [ expr_sel_s ];
00232 ;
00233 cut = logical_expression [ cut_s ];
00234 fun = expression [ expr_s ];
00235 start_parsers(cut, fun);
00236 }
00237 };
00238 };
00239 }
00240 }
00241
00242
00243 #endif