[antlr-interest] Puzzled
Brad Cox
bradjcox at gmail.com
Mon Mar 26 16:59:30 PDT 2012
Could someone please explain why I'm getting this error? Or better yet, how
to fix it?
[19:39:46] error(211): XacmlPL.g:64:35: [fatal] rule boolean has non-LL(*)
decision due to recursive rule invocations reachable from alts 2,3.
Resolve by left-factoring or using syntactic predicates or using
backtrack=true option.
Here's the grammar. Its a VERY rough first cut at a friendlier notation for
XACML than the XML razor wire defined by the standard. I included the whole
thing for completeness; the errors are in the very first rule (boolean).
grammar XacmlPL;
tokens
{
EQ='eq' ;
GE='ge' ;
GT='gt' ;
LE='le' ;
LT='lt' ;
NOF='nof' ;
NOT='not' ;
ADD='add' ;
ABS='abs' ;
DBL='dbl' ;
DIV='div' ;
FLR='flr' ;
INT='int' ;
MOD='mod' ;
MUL= 'mul' ;
NLS='normalizeSpace' ;
NLC='normalizeToLowerCase' ;
RND='rnd' ;
SUB= 'sub' ;
QUOT='"' ;
ANYURI= 'anyUri';
BASE64= 'base64';
BOOLEAN= 'boolean';
DATE= 'date';
DATETIME= 'dateTime';
DAYTIMEDURATION= 'dayTimeDuration';
DOUBLE= 'double';
HEX= 'hex';
INTEGER= 'integer';
RFC822= 'rfc822';
STRING= 'string';
TIME= 'time';
X500= 'x500';
YEARMONTHDURATION= 'yearMonthDuration';
}
@members
{
public static void main(String[] args) throws Exception
{
SimpleCalcLexer lex = new SimpleCalcLexer(new
ANTLRFileStream(args[0]));
CommonTokenStream tokens = new CommonTokenStream(lex);
SimpleCalcParser parser = new SimpleCalcParser(tokens);
try
{
parser.expr();
}
catch (RecognitionException e)
{
e.printStackTrace();
}
}
}
/*
| EQ date ',' date ')'
| EQ dateTime ',' dateTime ')'
*/
boolean
: BOOLEAN_CONSTANT
| ( EQ | GE | GT | LT | LE ) '(' ( (string ',' string) | (integer ','
integer) | (double ',' double) ) ')'
| (NOF | NOT) '(' boolean ')'
;
integer
: INTEGER_CONSTANT
| (ADD | SUB | MUL | DIV) '(' (integer ',' integer) ')'
| (MOD | ABS) '(' integer ')'
// | INT '(' double ')'
;
double
: DOUBLE_CONSTANT
| (ADD | SUB | MUL | DIV) '(' ( double ',' double ) ')'
| (ABS | RND | FLR) '(' double ')'
// | DBL '(' integer ')'
;
string
: STRING_CONSTANT
| (NLS | NLC) '(' string ')'
;
/*
dateTime
: ADD dateTime ',' dayTimeDuration ')'
// | ADD dateTime ',' yearMonthDuration ')'
| SUB dateTime ',' dayTimeDuration ')'
| SUB dateTime ',' yearMonthDuration ')'
;
date
: ADD date ',' yearMonthDuration ')'
| SUB date ',' yearMonthDuration ')'
;
*/
anyUriBag
: ANYURI STRING_LIST
;
base64Bag
: BASE64 STRING_LIST
;
booleanBag
: BOOLEAN STRING_LIST
;
dateBag
: DATE STRING_LIST
;
dateTimeBag
: DATETIME STRING_LIST
;
dayTimeDurationBag
: DAYTIMEDURATION STRING_LIST
;
doubleBag
: DOUBLE STRING_LIST
;
hexBag
: HEX STRING_LIST
;
integerBag
: INTEGER STRING_LIST
;
rfc822Bag
: RFC822 STRING_LIST
;
stringBag
: STRING STRING_LIST
;
timeBag
: TIME STRING_LIST
;
x500Bag
: X500 STRING_LIST
;
yearMonthDurationBag
: YEARMONTHDURATION STRING_LIST
;
time
: 'time()'
;
dayTimeDuration
: 'dayTimeDuration()'
;
yearMonthDuration
: 'yearMonthDuration()'
;
anyUri
: 'anyUri()'
;
x500Name
: 'x500Name()'
;
rfc822Name
: 'rfc822Name()'
;
hexBinary
: 'hexBinary()'
;
base64
: 'base64()'
;
COMMENT
: '//' ~('\n'|'\r')* '\r'? '\n' {$channel=HIDDEN;}
| '/*' ( options {greedy=false;} : . )* '*/' {$channel=HIDDEN;}
;
WS
:( ' '
| '\t'
| '\r'
| '\n'
) {$channel=HIDDEN;}
;
fragment BOOLEAN_CONSTANT
: 'true'
| 'false'
;
fragment INTEGER_CONSTANT
: (DIGIT)+
;
DOUBLE_CONSTANT
: INTEGER_CONSTANT? '.' INTEGER_CONSTANT EXPONENT?
// | '.' INTEGER_CONSTANT + EXPONENT?
// | ('0'..'9')+ EXPONENT
;
STRING_CONSTANT
: '"' ( ESC_SEQ | ~('\\'|'"') )* '"'
;
STRING_LIST
: '(' STRING_CONSTANT ( ',' STRING_CONSTANT )* ')'
;
CHAR
: '\'' ( ESC_SEQ | ~('\''|'\\') ) '\''
;
fragment DIGIT
: '0'..'9'
;
fragment EXPONENT
: ('e'|'E') ('+'|'-')? ('0'..'9')+
;
fragment HEX_DIGIT
: ('0'..'9'|'a'..'f'|'A'..'F')
;
fragment ESC_SEQ
: '\\' ('b'|'t'|'n'|'f'|'r'|'\"'|'\''|'\\')
| UNICODE_ESC
| OCTAL_ESC
;
fragment OCTAL_ESC
: '\\' ('0'..'3') ('0'..'7') ('0'..'7')
| '\\' ('0'..'7') ('0'..'7')
| '\\' ('0'..'7')
;
fragment UNICODE_ESC
: '\\' 'u' HEX_DIGIT HEX_DIGIT HEX_DIGIT HEX_DIGIT
;
fragment SIGN
: ('+'|'-')
;
NUMBER_OR_RANGEOP
: SIGN? DIGIT+
(
{ input.LA(2) != '.' }? => '.' DIGIT* { $type = DECIMAL; }
| { $type = INTEGER; }
)
| SIGN '.' DIGIT+ { $type = DECIMAL; }
| '.'
(
DIGIT+ { $type = DECIMAL; }
| '.' {$type = RANGEOP; }
| {$type = DEREF; } )
;
/*
ID
: ('a'..'z'|'A'..'Z'|'_') ('a'..'z'|'A'..'Z'|'0'..'9'|'_')*
;
*/
More information about the antlr-interest
mailing list