1# -* text -*- 2## PE grammar for the grammar specification language accepted by the 3## LEMON parser generator. 4 5 6## Questions: 7## Are directives always at the beginning of a line ? 8## Or can they start within a line ? 9 10## The ifdef/ifndef/endif directives are not documented. 11## Nor are the cmdline options 12 13 14PEG pg::peg::lemon (LemonGrammar) 15 16LemonGrammar <- SPACE Statement + EOF; 17 18Statement <- ( Directive 19 / Rule 20 ) SPACE; 21 22Rule <- Identifier Label? ASSIGN Definition DOT Precedence? Codeblock? ; 23Definition <- (Identifier Label?)* ; 24Label <- LPAREN Identifier RPAREN; 25Precedence <- LBRACKET Identifier RBRACKET; 26 27Directive <- DINTRO ( Code / DefaultDestructor 28 / DefaultType / Destructor 29 / ExtraArgument / Include 30 / Left / Name 31 / Nonassoc / ParseAccept 32 / ParseFailure / Right 33 / StackOverflow / Stacksize 34 / StartSymbol / SyntaxError 35 / TokenDestructor / TokenPrefix 36 / TokenType / Type 37 / Fallback 38 ); 39 40Code <- DCODE Codeblock; 41DefaultDestructor <- DDEFDEST Identifier Codeblock; 42DefaultType <- DDEFTYPE Codeblock; 43Destructor <- DDEST Identifier Codeblock; 44ExtraArgument <- DEXTRA Codeblock; 45Include <- DINCL Codeblock; 46Left <- DLEFT Identifier+ DOT; 47Name <- DNAME Identifier ; 48Nonassoc <- DNON Identifier+ DOT; 49ParseAccept <- DPACC Codeblock; 50ParseFailure <- DPFAIL Codeblock; 51Right <- DRIGHT Identifier+ DOT; 52StackOverflow <- DSTKOVER Codeblock; 53Stacksize <- DSTKSZ NaturalNumber; 54StartSymbol <- DSTART Identifier; 55SyntaxError <- DSYNERR Codeblock; 56TokenDestructor <- DTOKDEST Identifier Codeblock; 57TokenPrefix <- DTOKPFX Identifier; 58TokenType <- DTOKTYPE Codeblock; 59Type <- DTYPE Identifier Codeblock; 60Fallback <- DFALLBK Identifier+ DOT; 61 62 63# Lexical layer 64 65match: Codeblock <- LBRACE ( Codeblock 66 / C_COMMENT 67 / Cplusplus_COMMENT 68 / (!RBRACE .) 69 )* RBRACE ; 70 71 Identifier <- Ident SPACE; 72match: Ident <- (<alpha>/'_') (<alnum>/'_')*; 73 74 NaturalNumber <- NatNum SPACE; 75match: NatNum <- [0-9]+; 76 77void: ASSIGN <- '::=' SPACE; 78void: DOT <- '.' SPACE; 79void: LPAREN <- '(' SPACE; 80void: RPAREN <- ')' SPACE; 81void: LBRACKET <- '[' SPACE; 82void: RBRACKET <- ']' SPACE; 83void: LBRACE <- '{'; 84void: RBRACE <- '}'; 85 86void: DINTRO <- '%'; 87void: DCODE <- 'code' SPACE; 88void: DDEFDEST <- 'default_destructor' SPACE; 89void: DDEFTYPE <- 'default_type' SPACE; 90void: DDEST <- 'destructor' SPACE; 91void: DEXTRA <- 'extra_argument' SPACE; 92void: DINCL <- 'include' SPACE; 93void: DLEFT <- 'left' SPACE; 94void: DNAME <- 'name' SPACE; 95void: DNON <- 'nonassoc' SPACE; 96void: DPACC <- 'parse_accept' SPACE; 97void: DPFAIL <- 'parse_failure' SPACE; 98void: DRIGHT <- 'right' SPACE; 99void: DSTKOVER <- 'stack_overflow' SPACE; 100void: DSTKSZ <- 'stack_size' SPACE; 101void: DSTART <- 'start_symbol' SPACE; 102void: DSYNERR <- 'syntax_error' SPACE; 103void: DTOKDEST <- 'token_destructor' SPACE; 104void: DTOKPFX <- 'token_prefix' SPACE; 105void: DTOKTYPE <- 'token_type' SPACE; 106void: DTYPE <- 'type' SPACE; 107void: DFALLBK <- 'fallback' SPACE; 108 109# These have % in their definition because they 110# are not part of the regular directives. 111void: DIFDEF <- '%ifdef' SPACE; 112void: DIFNDEF <- '%ifndef' SPACE; 113void: DENDIF <- '%endif' SPACE; 114 115# Directives we do not really know about. They are in the SQLite 116# parse.y file, but are not documented for LEMON. We treat them as 117# whitespace for now, see below. 118 119Ifdef <- DIFDEF Identifier; 120Ifndef <- DIFNDEF Identifier; 121Endif <- DENDIF; 122 123 124# Whitespace 125 126void: SPACE <- ( [ \t\n\r] 127 / C_COMMENT 128 / Cplusplus_COMMENT 129 / Ifndef / Ifdef / Endif 130 )*; 131 132C_COMMENT <- CCOM_OPEN (!CCOM_CLOSE .)* CCOM_CLOSE; 133CCOM_OPEN <- '/*'; 134CCOM_CLOSE <- '*/'; 135 136Cplusplus_COMMENT <- '//' (!EOL .)* EOL; 137EOL <- '\r\n' / '\r' / '\n'; 138 139EOF <- !.; 140 141END; 142