我正在尝试为经过重新分析和重新标记的kconfig文件编写一个ANTLR语法(重新设计以解决一些歧义)。语法的简化版本是:
grammar FailureExample;
options {
language = Java;
}
@lexer::header {
package parse.failure.example;
}
reload
: configStatement*
EOF
;
configStatement
: CONFIG IDENT
configOptions
;
configOptions
: (type
| defConfigStatement
| dependsOnStatement
| helpStatement
| rangeStatement
| defaultStatement
| selectStatement
| visibleIfStatement
| prompt
)*
;
type : FAKE1;
dependsOnStatement: FAKE2;
helpStatement: FAKE3;
rangeStatement: FAKE4;
defaultStatement: FAKE5;
selectStatement:FAKE6;
visibleIfStatement:FAKE7;
prompt:FAKE8;
defConfigStatement
: defConfigType expression
;
defConfigType
: DEF_BOOL
;
//expression parsing
primative
: IDENT
| L_PAREN expression R_PAREN
;
negationExpression
: NOT* primative
;
orExpression
: negationExpression (OR negationExpression)*
;
andExpression
: orExpression (AND orExpression)*
;
unequalExpression
: andExpression (NOT_EQUAL andExpression)?
;
equalExpression
: unequalExpression (EQUAL unequalExpression)?
;
expression
: equalExpression (BECOMES equalExpression)?
;
DEF_BOOL: 'def_bool';
CONFIG : 'config';
COMMENT : '#' .* ('\n'|'\r') {$channel = HIDDEN;};
AND : '&&';
OR : '||';
NOT : '!';
L_PAREN : '(';
R_PAREN : ')';
BECOMES : '::=';
EQUAL : '=';
NOT_EQUAL : '!=';
FAKE1 : 'fake1';
FAKE2: 'fake2';
FAKE3: 'fake3';
FAKE4: 'fake4';
FAKE5: 'fake5';
FAKE6: 'fake6';
FAKE7: 'fake7';
FAKE8: 'fake8';
IDENT : (LETTER | DIGIT | '_')*;
WS : ( ' '
| '\t'
| '\r'
| '\n'
) {$channel=HIDDEN;}
;
fragment LETTER : ('a'..'z' | 'A'..'Z') ;
fragment DIGIT : '0'..'9';
输入:
config HAVE_DEBUG_RAM_SETUP
def_bool n
我可以设置antlrworks来解析第二行(注释掉第一行),然后我得到正确的defConfigStatement标记,并带有正确的表达式。但是,如果我运行configOptions规则或configStatement规则(第一行取消注释),我的configOptions会产生一个空集,并抛出NoViableAlt异常。
什么会导致这种行为?我知道defConfigStatement规则是准确的并且可以正确解析,但是一旦它作为另一个规则中的潜在选项添加,它就会失败。我知道我没有冲突的规则,并且我已经将DEF_BOOL和DEF_TRISTATE规则放在我的词法分析器规则列表的顶部,因此它们优先于其他词法分析器规则。
/ 自编辑后添加 / 为了进一步使问题复杂化,如果我在configOptions规则中移动defConfigStatement选项,它将起作用,但其他规则将失败。
编辑:使用完整,简化的语法。
简而言之,为什么规则本身有效,但在configOptions中失败(特别是因为configOptions是(A | B | C)*形式)?
答案 0 :(得分:1)
当我解析输入时:
config HAVE_DEBUG_RAM_SETUP
def_bool n
使用语法生成的解析器,我得到以下解析树:
所以,我认为这里没有问题。我的猜测是你正在使用ANTLRWorks'口译员:不要。它的马车。总是用自己的课程测试你的语法,或者使用ANTLWorks'调试器(按 CTRL + D 启动)。调试器就像一个魅力(没有包声明,顺便说一句)。我上面发布的图像是调试器的导出。
如果调试器不起作用,请尝试(暂时)删除包声明(请注意,您只是为词法分析器而不是解析器声明包,但这可能是由于发布了最小的语法)。您还可以尝试更改调试器应连接的端口号。可能是端口已在使用中(请参阅:文件 ->
首选项 ->
调试器 -tab)。