Compile time (LR) type safe parser generator for C++
A parser is defined using the LrParser class. An LrParser type takes a variadic number of template arguments, where each argument is a Production type. A Production type takes 3 arguments:
- A nonterminal (See "Nonterminals" for more information)
- A std::tuple-type, which takes a variable number of nonterminals and terminals
- A semantic action, which is something that is calleble (See "Semantic Actions" for more information)
using namespace parse; using d = Terminal<0>; using c = Terminal<1>; using a = Terminal<2>; using Parser = LrParser< Production< Z, std::tuple<d>, Rule1 >, Production< Z, std::tuple<X, Y, Z>, Rule2 >, Production< Y, std::tuple<>, Rule3 >, Production< Y, std::tuple<c>, Rule4 >, Production< X, std::tuple<Y>, Rule5 >, Production< X, std::tuple<a>, Rule6 > >;A Nonterminal class A must obey the following:
Amust publically derive fromNonterminal<A>
A Terminal must obey the following:
- Must have type
Terminal<n>, wherenis an integer that satisfies that two terminalsTerminal<n>andTerminal<m>are equal if and only ifn == m. These Terminal-types model token classes returned from some lexer.
A semantic action R valid if and only if:
- Given a
Productionof the following form
Production< A, std::tuple<B1, B2, ..., BN>, R >then an instance of type R is callable with arguments b1, b2, ..., bN, (where decltype(bi) = Bi) and the result of R{}(b1, b2, ..., bN) is of type A.
- The number of rows or columns in the LR parsing table can be no more than
BOOST_PP_LIMIT_REPEAT, which sadly is a very real limitation when parsing complex languages. - Due to the amount of template meta-programming used within the library, the compile time can be quite long
