refactoring resolving; alts know about rules and those know about grammars.

[git-p4: depot-paths = "//depot/code/antlr4/main/": change = 6688]
This commit is contained in:
parrt 2010-02-12 15:41:56 -08:00
parent b3f7c8e3cc
commit 172851245e
21 changed files with 2358 additions and 2210 deletions

View File

@ -117,13 +117,13 @@ CANNOT_ALIAS_TOKENS_IN_LEXER(arg) ::=
ATTRIBUTE_REF_NOT_IN_RULE(arg,arg2) ::=
"reference to attribute outside of a rule: <arg><if(arg2)>.<arg2><endif>"
UNKNOWN_ATTRIBUTE_IN_SCOPE(arg,arg2) ::=
"unknown attribute for <arg>: <arg2>"
"attribute <arg> isn't a valid property in <arg2>"
UNKNOWN_RULE_ATTRIBUTE(arg,arg2) ::=
"unknown attribute for rule <arg>: <arg2>"
UNKNOWN_SIMPLE_ATTRIBUTE(arg,args2) ::=
"attribute is not a token, parameter, or return value: <arg>"
ISOLATED_RULE_SCOPE(arg) ::=
"missing attribute access on rule scope: <arg>"
UNKNOWN_SIMPLE_ATTRIBUTE(arg,arg2) ::=
"unknown attribute reference <arg> in <arg2>"
ISOLATED_RULE_SCOPE(arg,arg2) ::=
"missing attribute access on rule reference <arg> in <arg2>"
INVALID_RULE_PARAMETER_REF(arg,arg2) ::=
"cannot access rule <arg>'s parameter: <arg2>"
INVALID_RULE_SCOPE_ATTRIBUTE_REF(arg,arg2) ::=
@ -199,8 +199,6 @@ DOUBLE_QUOTES_ILLEGAL(arg) ::=
"string literals must use single quotes (such as \'begin\'): <arg>"
INVALID_TEMPLATE_ACTION(arg) ::=
"invalid StringTemplate % shorthand syntax: '<arg>'"
MISSING_ATTRIBUTE_NAME() ::=
"missing attribute name on $ reference"
ARG_INIT_VALUES_ILLEGAL(arg) ::=
"rule parameters may not have init values: <arg>"
REWRITE_OR_OP_WITH_NO_OUTPUT_OPTION(arg) ::=

View File

@ -1,4 +1,4 @@
// $ANTLR 3.2.1-SNAPSHOT Jan 26, 2010 15:12:28 ANTLRLexer.g 2010-02-11 11:14:45
// $ANTLR 3.2.1-SNAPSHOT Jan 26, 2010 15:12:28 ANTLRLexer.g 2010-02-12 14:08:47
/*
[The "BSD licence"]

View File

@ -330,7 +330,7 @@ tokenSpec
// the grammar spec, rather than being declared within and therefore associated
// with, a specific rule.
attrScope
: SCOPE id ACTION -> ^(SCOPE id ACTION)
: SCOPE id ACTION -> ^(SCOPE id ACTION<ActionAST>)
;
// A declaration of a language target specifc section,
@ -338,7 +338,7 @@ attrScope
// sections, they are just passed on to the language target.
/** Match stuff like @parser::members {int i;} */
action
: AT (actionScopeName COLONCOLON)? id ACTION -> ^(AT actionScopeName? id ACTION)
: AT (actionScopeName COLONCOLON)? id ACTION -> ^(AT actionScopeName? id ACTION<ActionAST>)
;
/** Sometimes the scope names will collide with keywords; allow them as
@ -436,13 +436,13 @@ exceptionGroup
// Specifies a handler for a particular type of exception
// thrown by a rule
exceptionHandler
: CATCH ARG_ACTION ACTION -> ^(CATCH ARG_ACTION ACTION)
: CATCH ARG_ACTION ACTION -> ^(CATCH ARG_ACTION ACTION<ActionAST>)
;
// Specifies a block of code to run after the rule and any
// expcetion blocks have exceuted.
finallyClause
: FINALLY ACTION -> ^(FINALLY ACTION)
: FINALLY ACTION -> ^(FINALLY ACTION<ActionAST>)
;
// An individual rule level configuration as referenced by the ruleActions
@ -499,7 +499,7 @@ ruleScopeSpec
//
/** Match stuff like @init {int i;} */
ruleAction
: AT id ACTION -> ^(AT id ACTION)
: AT id ACTION -> ^(AT id ACTION<ActionAST>)
;
// A set of access modifiers that may be applied to rule declarations
@ -563,7 +563,7 @@ element
| -> atom
)
| ebnf
| ACTION
| ACTION<ActionAST>
| SEMPRED
( IMPLIES -> GATED_SEMPRED[$IMPLIES]
| -> SEMPRED
@ -683,35 +683,13 @@ notTerminal
// of options, which apply only to that block.
//
block
: LPAREN
: LPAREN
// A new blocked altlist may have a set of options set sepcifically
// for it.
//
optionsSpec?
(
// Optional @ sections OR an action, however we allow both
// to be present and will let the semantic checking phase determine
// what is allowable.
//
ra+=ruleAction*
ACTION?
// COLON is optional with a block
//
COLON
)?
// List of alts for this Paren block
//
altList
( optionsSpec? ra+=ruleAction* COLON )?
altList
RPAREN
// Rewrite as a block
//
-> ^(BLOCK<BlockAST> optionsSpec? $ra* ACTION? altList )
-> ^(BLOCK<BlockAST> optionsSpec? $ra* altList )
;
// ----------------
@ -845,7 +823,7 @@ rewriteTreeAtom
| RULE_REF
| STRING_LITERAL elementOptions? -> ^(STRING_LITERAL<TerminalAST> elementOptions?)
| DOLLAR id -> LABEL[$DOLLAR,$id.text] // reference to a label in a rewrite rule
| ACTION
| ACTION<ActionAST>
;
rewriteTreeEbnf
@ -887,7 +865,7 @@ rewriteTemplate
rewriteIndirectTemplateHead
| // -> {...}
ACTION
ACTION<ActionAST>
;
/** -> foo(a={...}, ...) */
@ -899,7 +877,7 @@ rewriteTemplateRef
/** -> ({expr})(a={...}, ...) */
rewriteIndirectTemplateHead
: lp=LPAREN ACTION RPAREN LPAREN rewriteTemplateArgs RPAREN
-> ^(TEMPLATE[$lp,"TEMPLATE"] ACTION rewriteTemplateArgs?)
-> ^(TEMPLATE[$lp,"TEMPLATE"] ACTION<ActionAST> rewriteTemplateArgs?)
;
rewriteTemplateArgs
@ -909,7 +887,7 @@ rewriteTemplateArgs
;
rewriteTemplateArg
: id ASSIGN ACTION -> ^(ARG[$ASSIGN] id ACTION)
: id ASSIGN ACTION -> ^(ARG[$ASSIGN] id ACTION<ActionAST>)
;
// The name of the grammar, and indeed some other grammar elements may

File diff suppressed because it is too large Load Diff

View File

@ -1,4 +1,4 @@
// $ANTLR 3.2.1-SNAPSHOT Jan 26, 2010 15:12:28 ASTVerifier.g 2010-02-11 11:14:48
// $ANTLR 3.2.1-SNAPSHOT Jan 26, 2010 15:12:28 ASTVerifier.g 2010-02-12 14:08:50
/*
[The "BSD license"]

View File

@ -45,20 +45,20 @@ LINE_COMMENT
SET_QUALIFIED_ATTR
: '$' x=ID '.' y=ID WS? '=' expr=ATTR_VALUE_EXPR ';'
{delegate.setQualifiedAttr($x, $y, $expr);}
{delegate.setQualifiedAttr($text, $x, $y, $expr);}
;
QUALIFIED_ATTR
: '$' x=ID '.' y=ID {input.LA(1)!='('}? {delegate.qualifiedAttr($x, $y);}
: '$' x=ID '.' y=ID {input.LA(1)!='('}? {delegate.qualifiedAttr($text, $x, $y);}
;
SET_DYNAMIC_SCOPE_ATTR
: '$' x=ID '::' y=ID WS? '=' expr=ATTR_VALUE_EXPR ';'
{delegate.setDynamicScopeAttr($x, $y, $expr);}
{delegate.setDynamicScopeAttr($text, $x, $y, $expr);}
;
DYNAMIC_SCOPE_ATTR
: '$' x=ID '::' y=ID {delegate.dynamicScopeAttr($x, $y);}
: '$' x=ID '::' y=ID {delegate.dynamicScopeAttr($text, $x, $y);}
;
/** To access deeper (than top of stack) scopes, use the notation:
@ -72,31 +72,31 @@ DYNAMIC_SCOPE_ATTR
SET_DYNAMIC_NEGATIVE_INDEXED_SCOPE_ATTR
: '$' x=ID '[' '-' index=SCOPE_INDEX_EXPR ']' '::' y=ID
WS? ('=' expr=ATTR_VALUE_EXPR ';')?
{delegate.setDynamicNegativeIndexedScopeAttr($x, $y, $index, $expr);}
{delegate.setDynamicNegativeIndexedScopeAttr($text, $x, $y, $index, $expr);}
;
DYNAMIC_NEGATIVE_INDEXED_SCOPE_ATTR
: '$' x=ID '[' '-' index=SCOPE_INDEX_EXPR ']' '::' y=ID
{delegate.dynamicNegativeIndexedScopeAttr($x, $y, $index);}
{delegate.dynamicNegativeIndexedScopeAttr($text, $x, $y, $index);}
;
SET_DYNAMIC_ABSOLUTE_INDEXED_SCOPE_ATTR
: '$' x=ID '[' index=SCOPE_INDEX_EXPR ']' '::' y=ID
WS? ('=' expr=ATTR_VALUE_EXPR ';')?
{delegate.setDynamicAbsoluteIndexedScopeAttr($x, $y, $index, $expr);}
WS? '=' expr=ATTR_VALUE_EXPR ';'
{delegate.setDynamicAbsoluteIndexedScopeAttr($text, $x, $y, $index, $expr);}
;
DYNAMIC_ABSOLUTE_INDEXED_SCOPE_ATTR
: '$' x=ID '[' index=SCOPE_INDEX_EXPR ']' '::' y=ID
{delegate.dynamicAbsoluteIndexedScopeAttr($x, $y, $index);}
{delegate.dynamicAbsoluteIndexedScopeAttr($text, $x, $y, $index);}
;
SET_ATTR
: '$' x=ID WS? '=' expr=ATTR_VALUE_EXPR ';' {delegate.setAttr($x, $expr);}
: '$' x=ID WS? '=' expr=ATTR_VALUE_EXPR ';' {delegate.setAttr($text, $x, $expr);}
;
ATTR
: '$' x=ID {delegate.attr($x);}
: '$' x=ID {delegate.attr($text, $x);}
;
/** %foo(a={},b={},...) ctor */

File diff suppressed because it is too large Load Diff

View File

@ -4,23 +4,23 @@ import org.antlr.runtime.Token;
/** */
public interface ActionSplitterListener {
void setQualifiedAttr(Token x, Token y, Token expr);
void qualifiedAttr(Token x, Token y);
void setAttr(Token x, Token expr);
void attr(Token x);
void setQualifiedAttr(String expr, Token x, Token y, Token rhs);
void qualifiedAttr(String expr, Token x, Token y);
void setAttr(String expr, Token x, Token rhs);
void attr(String expr, Token x);
void setDynamicScopeAttr(Token x, Token y, Token expr);
void dynamicScopeAttr(Token x, Token y);
void setDynamicNegativeIndexedScopeAttr(Token x, Token y, Token index, Token expr);
void dynamicNegativeIndexedScopeAttr(Token x, Token y, Token index);
void setDynamicAbsoluteIndexedScopeAttr(Token x, Token y, Token index, Token expr);
void dynamicAbsoluteIndexedScopeAttr(Token x, Token y, Token index);
void setDynamicScopeAttr(String expr, Token x, Token y, Token rhs);
void dynamicScopeAttr(String expr, Token x, Token y);
void setDynamicNegativeIndexedScopeAttr(String expr, Token x, Token y, Token index, Token rhs);
void dynamicNegativeIndexedScopeAttr(String expr, Token x, Token y, Token index);
void setDynamicAbsoluteIndexedScopeAttr(String expr, Token x, Token y, Token index, Token rhs);
void dynamicAbsoluteIndexedScopeAttr(String expr, Token x, Token y, Token index);
void templateInstance();
void indirectTemplateInstance();
void setExprAttribute();
void setAttribute();
void templateExpr();
void templateInstance(String expr);
void indirectTemplateInstance(String expr);
void setExprAttribute(String expr);
void setAttribute(String expr);
void templateExpr(String expr);
void unknownSyntax(String text);
void text(String text);

View File

@ -11,20 +11,7 @@ public class GrammarASTAdaptor extends CommonTreeAdaptor {
public GrammarASTAdaptor(CharStream input) { this.input = input; }
public Object create(Token token) {
if ( token==null ) return new GrammarAST(token);
switch ( token.getType() ) {
// case ANTLRParser.BLOCK :
// return new BlockAST(token);
// case ANTLRParser.RULE :
// return new RuleAST(token);
// case ANTLRParser.PARSER_GRAMMAR :
// case ANTLRParser.COMBINED_GRAMMAR :
// case ANTLRParser.TREE_GRAMMAR :
// case ANTLRParser.LEXER_GRAMMAR :
// return new GrammarRootAST(token);
default :
return new GrammarAST(token);
}
return new GrammarAST(token);
}
@Override

View File

@ -12,11 +12,11 @@ import java.util.List;
public class AttributeChecks implements ActionSplitterListener {
public Grammar g;
public Rule r; // null if action outside of rule
public Alternative alt; // null if action outside of rule
public GrammarAST node;
public Alternative alt; // null if action outside of alt; could be in rule
public ActionAST node;
public String action;
public AttributeChecks(Grammar g, Rule r, Alternative alt, GrammarAST node, String action) {
public AttributeChecks(Grammar g, Rule r, Alternative alt, ActionAST node, String action) {
this.g = g;
this.r = r;
this.alt = alt;
@ -24,62 +24,112 @@ public class AttributeChecks implements ActionSplitterListener {
this.action = action;
}
public void examine() {
public static void checkAllAttributeExpressions(Grammar g, List<Rule> rules) {
for (Rule r : rules) {
for (ActionAST a : r.namedActions.values()) {
AttributeChecks checker = new AttributeChecks(g, r, null, a, a.getText());
checker.examineAction();
}
for (int i=1; i<=r.numberOfAlts; i++) {
Alternative alt = r.alt[i];
for (ActionAST a : alt.actions) {
AttributeChecks checker =
new AttributeChecks(g, r, alt, a, a.getText());
checker.examineAction();
}
}
for (ActionAST a : r.exceptionActions) {
AttributeChecks checker = new AttributeChecks(g, r, null, a, a.getText());
checker.examineAction();
}
}
}
public void examineAction() {
ANTLRStringStream in = new ANTLRStringStream(action);
in.setLine(node.getLine());
in.setCharPositionInLine(node.getCharPositionInLine());
ActionSplitter splitter = new ActionSplitter(in, this);
splitter.getActionChunks(); // forces eval, fills extractor
List<Token> chunks = splitter.getActionChunks(); // forces eval, fills extractor
//System.out.println(chunks);
}
// LISTENER METHODS
public void setQualifiedAttr(Token x, Token y, Token expr) {
System.out.println(x+"."+y+"="+expr);
new AttributeChecks(g, r, alt, node, expr.getText()).examine();
public void setQualifiedAttr(String expr, Token x, Token y, Token rhs) {
if ( !node.space.resolves(x.getText(), y.getText(), node) ) {
ErrorManager.grammarError(ErrorType.UNKNOWN_SIMPLE_ATTRIBUTE, // TODO; not right error
g.fileName, x, x.getText(), expr);
}
new AttributeChecks(g, r, alt, node, rhs.getText()).examineAction();
}
public void qualifiedAttr(Token x, Token y) {
System.out.println(x+"."+y);
AttributeScope s = r.resolveScope(x.getText(), alt);
if ( s==null ) {
System.err.println("not found: "+x);
public void qualifiedAttr(String expr, Token x, Token y) {
if ( !node.space.resolves(x.getText(), node) ) {
ErrorManager.grammarError(ErrorType.UNKNOWN_SIMPLE_ATTRIBUTE,
g.fileName, x, x.getText(), expr);
return;
}
// ???if y is not prop of x, we don't care; we'll ignore and leave as simple attr
if ( !node.space.resolves(x.getText(), y.getText(), node) ) {
if ( node.space.resolveToRuleRef(x.getText(), node) ) {
ErrorManager.grammarError(ErrorType.INVALID_RULE_PARAMETER_REF,
g.fileName, y, y.getText(), expr);
}
else {
ErrorManager.grammarError(ErrorType.UNKNOWN_ATTRIBUTE_IN_SCOPE,
g.fileName, y, y.getText(), expr);
}
}
}
public void setAttr(Token x, Token expr) {
System.out.println(x+"="+expr);
if ( !r.resolves(x.getText(), alt) ) System.err.println("not found: "+x);
new AttributeChecks(g, r, alt, node, expr.getText()).examine();
public void setAttr(String expr, Token x, Token rhs) {
if ( !node.space.resolves(x.getText(), node) ) {
ErrorManager.grammarError(ErrorType.UNKNOWN_SIMPLE_ATTRIBUTE,
g.fileName, x, x.getText(), expr);
}
new AttributeChecks(g, r, alt, node, rhs.getText()).examineAction();
}
public void attr(Token x) { // arg, retval, predefined, token ref, rule ref, current rule
System.out.println(x);
if ( !r.resolves(x.getText(), alt) ) System.err.println("not found: "+x);
public void attr(String expr, Token x) { // arg, retval, predefined, token ref, rule ref, current rule
// TODO: check for isolated rule ref "+x+" in "+expr);
if ( node.space.resolveToRuleRef(x.getText(), node) ) {
ErrorManager.grammarError(ErrorType.ISOLATED_RULE_SCOPE,
g.fileName, x, x.getText(), expr);
return;
}
if ( !node.space.resolves(x.getText(), node) ) {
ErrorManager.grammarError(ErrorType.UNKNOWN_SIMPLE_ATTRIBUTE,
g.fileName, x, x.getText(), expr);
}
}
public void setDynamicScopeAttr(Token x, Token y, Token expr) { }
public void setDynamicScopeAttr(String expr, Token x, Token y, Token rhs) { }
public void dynamicScopeAttr(Token x, Token y) { }
public void dynamicScopeAttr(String expr, Token x, Token y) {
}
public void setDynamicNegativeIndexedScopeAttr(Token x, Token y, Token index, Token expr) { }
public void setDynamicNegativeIndexedScopeAttr(String expr, Token x, Token y, Token index, Token rhs) { }
public void dynamicNegativeIndexedScopeAttr(Token x, Token y, Token index) { }
public void dynamicNegativeIndexedScopeAttr(String expr, Token x, Token y, Token index) { }
public void setDynamicAbsoluteIndexedScopeAttr(Token x, Token y, Token index, Token expr) { }
public void setDynamicAbsoluteIndexedScopeAttr(String expr, Token x, Token y, Token index, Token rhs) { }
public void dynamicAbsoluteIndexedScopeAttr(Token x, Token y, Token index) { }
public void dynamicAbsoluteIndexedScopeAttr(String expr, Token x, Token y, Token index) { }
public void unknownSyntax(String text) { }
public void unknownSyntax(String text) {
System.err.println("unknown: "+text);
}
public void text(String text) { }
// don't care
public void templateInstance() { }
public void indirectTemplateInstance() { }
public void setExprAttribute() { }
public void setAttribute() { }
public void templateExpr() { }
public void templateInstance(String expr) { }
public void indirectTemplateInstance(String expr) { }
public void setExprAttribute(String expr) { }
public void setAttribute(String expr) { }
public void templateExpr(String expr) { }
}

View File

@ -1,4 +1,4 @@
// $ANTLR 3.2.1-SNAPSHOT Jan 26, 2010 15:12:28 BasicSemanticTriggers.g 2010-02-11 12:59:15
// $ANTLR 3.2.1-SNAPSHOT Jan 26, 2010 15:12:28 BasicSemanticTriggers.g 2010-02-12 14:54:09
/*
[The "BSD license"]
@ -26,15 +26,14 @@
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
package org.antlr.v4.semantics;
import org.antlr.v4.tool.*;
import org.antlr.runtime.*;
import org.antlr.runtime.tree.*;import java.util.Stack;
import java.util.List;
import org.antlr.runtime.tree.TreeNodeStream;
import org.antlr.runtime.tree.TreeRuleReturnScope;
import org.antlr.v4.tool.*;
import java.util.ArrayList;
import java.util.Map;
import java.util.HashMap;
import java.util.List;
/** Triggers for the basic semantics of the input. Side-effects:
* Set token, block, rule options in the tree. Load field option
* with grammar options. Only legal options are set.

View File

@ -153,19 +153,36 @@ finishRule
rulelNamedAction
: {inContext("RULE")}? ^(AT ID ACTION)
{currentRule.namedActions.put($ID.text,$ACTION);}
{
currentRule.namedActions.put($ID.text,(ActionAST)$ACTION);
((ActionAST)$ACTION).space = currentRule;
}
;
ruleAction
: {inContext("RULE ...")}? ACTION {currentRule.alt[currentAlt].actions.add($ACTION);}
: {inContext("RULE ...")&&!inContext("SCOPE")&&
!inContext("CATCH")&&!inContext("FINALLY")}?
ACTION
{
currentRule.alt[currentAlt].actions.add((ActionAST)$ACTION);
((ActionAST)$ACTION).space = currentRule.alt[currentAlt];
}
;
exceptionHandler
: ^(CATCH ARG_ACTION ACTION) {currentRule.exceptionActions.add($ACTION);}
: ^(CATCH ARG_ACTION ACTION)
{
currentRule.exceptionActions.add((ActionAST)$ACTION);
((ActionAST)$ACTION).space = currentRule;
}
;
finallyClause
: ^(FINALLY ACTION) {currentRule.exceptionActions.add($ACTION);}
: ^(FINALLY ACTION)
{
currentRule.exceptionActions.add((ActionAST)$ACTION);
((ActionAST)$ACTION).space = currentRule;
}
;
ruleArg
@ -205,8 +222,8 @@ rewriteElement
labeledElement
@after {
LabelElementPair lp = new LabelElementPair(g, $id, $e, $start.getType());
currentRule.labelDefs.map($id.text, lp);
currentRule.alt[currentAlt].labelDefs.map($id.text, $id);
//currentRule.labelDefs.map($id.text, lp);
currentRule.alt[currentAlt].labelDefs.map($id.text, lp);
}
: {inContext("RULE ...")}?
( ^(ASSIGN id=ID e=.)

View File

@ -1,4 +1,4 @@
// $ANTLR 3.2.1-SNAPSHOT Jan 26, 2010 15:12:28 CollectSymbols.g 2010-02-11 12:59:15
// $ANTLR 3.2.1-SNAPSHOT Jan 26, 2010 15:12:28 CollectSymbols.g 2010-02-12 14:54:08
/*
[The "BSD license"]
@ -26,19 +26,15 @@
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
package org.antlr.v4.semantics;
import org.antlr.v4.tool.*;
import org.antlr.v4.parse.*;
import java.util.Set;
import java.util.HashSet;
import org.stringtemplate.v4.misc.MultiMap;
import org.antlr.runtime.*;
import org.antlr.runtime.tree.*;import java.util.Stack;
import java.util.List;
import org.antlr.runtime.tree.TreeNodeStream;
import org.antlr.runtime.tree.TreeRuleReturnScope;
import org.antlr.v4.parse.ScopeParser;
import org.antlr.v4.tool.*;
import java.util.ArrayList;
import java.util.Map;
import java.util.HashMap;
import java.util.List;
/** Collects rules, terminals, strings, actions, scopes etc... from AST
* Side-effects: None
*/
@ -737,7 +733,10 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
match(input, Token.UP, null); if (state.failed) return ;
if ( state.backtracking==1 ) {
currentRule.namedActions.put((ID6!=null?ID6.getText():null),ACTION7);
currentRule.namedActions.put((ID6!=null?ID6.getText():null),(ActionAST)ACTION7);
((ActionAST)ACTION7).space = currentRule;
}
}
@ -755,21 +754,25 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
// $ANTLR start "ruleAction"
// CollectSymbols.g:159:1: ruleAction : {...}? ACTION ;
// CollectSymbols.g:162:1: ruleAction : {...}? ACTION ;
public final void ruleAction() throws RecognitionException {
GrammarAST ACTION8=null;
try {
// CollectSymbols.g:160:2: ({...}? ACTION )
// CollectSymbols.g:160:4: {...}? ACTION
// CollectSymbols.g:163:2: ({...}? ACTION )
// CollectSymbols.g:163:4: {...}? ACTION
{
if ( !((inContext("RULE ..."))) ) {
if ( !((inContext("RULE ...")&&!inContext("SCOPE")&&
!inContext("CATCH")&&!inContext("FINALLY"))) ) {
if (state.backtracking>0) {state.failed=true; return ;}
throw new FailedPredicateException(input, "ruleAction", "inContext(\"RULE ...\")");
throw new FailedPredicateException(input, "ruleAction", "inContext(\"RULE ...\")&&!inContext(\"SCOPE\")&&\n\t\t !inContext(\"CATCH\")&&!inContext(\"FINALLY\")");
}
ACTION8=(GrammarAST)match(input,ACTION,FOLLOW_ACTION_in_ruleAction430); if (state.failed) return ;
ACTION8=(GrammarAST)match(input,ACTION,FOLLOW_ACTION_in_ruleAction432); if (state.failed) return ;
if ( state.backtracking==1 ) {
currentRule.alt[currentAlt].actions.add(ACTION8);
currentRule.alt[currentAlt].actions.add((ActionAST)ACTION8);
((ActionAST)ACTION8).space = currentRule.alt[currentAlt];
}
}
@ -787,23 +790,26 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
// $ANTLR start "exceptionHandler"
// CollectSymbols.g:163:1: exceptionHandler : ^( CATCH ARG_ACTION ACTION ) ;
// CollectSymbols.g:172:1: exceptionHandler : ^( CATCH ARG_ACTION ACTION ) ;
public final void exceptionHandler() throws RecognitionException {
GrammarAST ACTION9=null;
try {
// CollectSymbols.g:164:2: ( ^( CATCH ARG_ACTION ACTION ) )
// CollectSymbols.g:164:4: ^( CATCH ARG_ACTION ACTION )
// CollectSymbols.g:173:2: ( ^( CATCH ARG_ACTION ACTION ) )
// CollectSymbols.g:173:4: ^( CATCH ARG_ACTION ACTION )
{
match(input,CATCH,FOLLOW_CATCH_in_exceptionHandler444); if (state.failed) return ;
match(input,CATCH,FOLLOW_CATCH_in_exceptionHandler448); if (state.failed) return ;
match(input, Token.DOWN, null); if (state.failed) return ;
match(input,ARG_ACTION,FOLLOW_ARG_ACTION_in_exceptionHandler446); if (state.failed) return ;
ACTION9=(GrammarAST)match(input,ACTION,FOLLOW_ACTION_in_exceptionHandler448); if (state.failed) return ;
match(input,ARG_ACTION,FOLLOW_ARG_ACTION_in_exceptionHandler450); if (state.failed) return ;
ACTION9=(GrammarAST)match(input,ACTION,FOLLOW_ACTION_in_exceptionHandler452); if (state.failed) return ;
match(input, Token.UP, null); if (state.failed) return ;
if ( state.backtracking==1 ) {
currentRule.exceptionActions.add(ACTION9);
currentRule.exceptionActions.add((ActionAST)ACTION9);
((ActionAST)ACTION9).space = currentRule;
}
}
@ -821,22 +827,25 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
// $ANTLR start "finallyClause"
// CollectSymbols.g:167:1: finallyClause : ^( FINALLY ACTION ) ;
// CollectSymbols.g:180:1: finallyClause : ^( FINALLY ACTION ) ;
public final void finallyClause() throws RecognitionException {
GrammarAST ACTION10=null;
try {
// CollectSymbols.g:168:2: ( ^( FINALLY ACTION ) )
// CollectSymbols.g:168:4: ^( FINALLY ACTION )
// CollectSymbols.g:181:2: ( ^( FINALLY ACTION ) )
// CollectSymbols.g:181:4: ^( FINALLY ACTION )
{
match(input,FINALLY,FOLLOW_FINALLY_in_finallyClause463); if (state.failed) return ;
match(input,FINALLY,FOLLOW_FINALLY_in_finallyClause469); if (state.failed) return ;
match(input, Token.DOWN, null); if (state.failed) return ;
ACTION10=(GrammarAST)match(input,ACTION,FOLLOW_ACTION_in_finallyClause465); if (state.failed) return ;
ACTION10=(GrammarAST)match(input,ACTION,FOLLOW_ACTION_in_finallyClause471); if (state.failed) return ;
match(input, Token.UP, null); if (state.failed) return ;
if ( state.backtracking==1 ) {
currentRule.exceptionActions.add(ACTION10);
currentRule.exceptionActions.add((ActionAST)ACTION10);
((ActionAST)ACTION10).space = currentRule;
}
}
@ -854,19 +863,19 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
// $ANTLR start "ruleArg"
// CollectSymbols.g:171:1: ruleArg : {...}? ARG_ACTION ;
// CollectSymbols.g:188:1: ruleArg : {...}? ARG_ACTION ;
public final void ruleArg() throws RecognitionException {
GrammarAST ARG_ACTION11=null;
try {
// CollectSymbols.g:172:2: ({...}? ARG_ACTION )
// CollectSymbols.g:172:4: {...}? ARG_ACTION
// CollectSymbols.g:189:2: ({...}? ARG_ACTION )
// CollectSymbols.g:189:4: {...}? ARG_ACTION
{
if ( !((inContext("RULE"))) ) {
if (state.backtracking>0) {state.failed=true; return ;}
throw new FailedPredicateException(input, "ruleArg", "inContext(\"RULE\")");
}
ARG_ACTION11=(GrammarAST)match(input,ARG_ACTION,FOLLOW_ARG_ACTION_in_ruleArg485); if (state.failed) return ;
ARG_ACTION11=(GrammarAST)match(input,ARG_ACTION,FOLLOW_ARG_ACTION_in_ruleArg491); if (state.failed) return ;
if ( state.backtracking==1 ) {
currentRule.args = ScopeParser.parseTypeList((ARG_ACTION11!=null?ARG_ACTION11.getText():null));
@ -889,18 +898,18 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
// $ANTLR start "ruleReturns"
// CollectSymbols.g:179:1: ruleReturns : ^( RETURNS ARG_ACTION ) ;
// CollectSymbols.g:196:1: ruleReturns : ^( RETURNS ARG_ACTION ) ;
public final void ruleReturns() throws RecognitionException {
GrammarAST ARG_ACTION12=null;
try {
// CollectSymbols.g:180:2: ( ^( RETURNS ARG_ACTION ) )
// CollectSymbols.g:180:4: ^( RETURNS ARG_ACTION )
// CollectSymbols.g:197:2: ( ^( RETURNS ARG_ACTION ) )
// CollectSymbols.g:197:4: ^( RETURNS ARG_ACTION )
{
match(input,RETURNS,FOLLOW_RETURNS_in_ruleReturns502); if (state.failed) return ;
match(input,RETURNS,FOLLOW_RETURNS_in_ruleReturns508); if (state.failed) return ;
match(input, Token.DOWN, null); if (state.failed) return ;
ARG_ACTION12=(GrammarAST)match(input,ARG_ACTION,FOLLOW_ARG_ACTION_in_ruleReturns504); if (state.failed) return ;
ARG_ACTION12=(GrammarAST)match(input,ARG_ACTION,FOLLOW_ARG_ACTION_in_ruleReturns510); if (state.failed) return ;
match(input, Token.UP, null); if (state.failed) return ;
if ( state.backtracking==1 ) {
@ -925,21 +934,21 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
// $ANTLR start "ruleScopeSpec"
// CollectSymbols.g:187:1: ruleScopeSpec : {...}? ( ^( SCOPE ACTION ) | ^( SCOPE (ids+= ID )+ ) ) ;
// CollectSymbols.g:204:1: ruleScopeSpec : {...}? ( ^( SCOPE ACTION ) | ^( SCOPE (ids+= ID )+ ) ) ;
public final void ruleScopeSpec() throws RecognitionException {
GrammarAST ACTION13=null;
GrammarAST ids=null;
List list_ids=null;
try {
// CollectSymbols.g:188:2: ({...}? ( ^( SCOPE ACTION ) | ^( SCOPE (ids+= ID )+ ) ) )
// CollectSymbols.g:188:4: {...}? ( ^( SCOPE ACTION ) | ^( SCOPE (ids+= ID )+ ) )
// CollectSymbols.g:205:2: ({...}? ( ^( SCOPE ACTION ) | ^( SCOPE (ids+= ID )+ ) ) )
// CollectSymbols.g:205:4: {...}? ( ^( SCOPE ACTION ) | ^( SCOPE (ids+= ID )+ ) )
{
if ( !((inContext("RULE"))) ) {
if (state.backtracking>0) {state.failed=true; return ;}
throw new FailedPredicateException(input, "ruleScopeSpec", "inContext(\"RULE\")");
}
// CollectSymbols.g:189:3: ( ^( SCOPE ACTION ) | ^( SCOPE (ids+= ID )+ ) )
// CollectSymbols.g:206:3: ( ^( SCOPE ACTION ) | ^( SCOPE (ids+= ID )+ ) )
int alt6=2;
int LA6_0 = input.LA(1);
@ -980,12 +989,12 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
}
switch (alt6) {
case 1 :
// CollectSymbols.g:189:5: ^( SCOPE ACTION )
// CollectSymbols.g:206:5: ^( SCOPE ACTION )
{
match(input,SCOPE,FOLLOW_SCOPE_in_ruleScopeSpec527); if (state.failed) return ;
match(input,SCOPE,FOLLOW_SCOPE_in_ruleScopeSpec533); if (state.failed) return ;
match(input, Token.DOWN, null); if (state.failed) return ;
ACTION13=(GrammarAST)match(input,ACTION,FOLLOW_ACTION_in_ruleScopeSpec529); if (state.failed) return ;
ACTION13=(GrammarAST)match(input,ACTION,FOLLOW_ACTION_in_ruleScopeSpec535); if (state.failed) return ;
match(input, Token.UP, null); if (state.failed) return ;
if ( state.backtracking==1 ) {
@ -998,12 +1007,12 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
}
break;
case 2 :
// CollectSymbols.g:194:5: ^( SCOPE (ids+= ID )+ )
// CollectSymbols.g:211:5: ^( SCOPE (ids+= ID )+ )
{
match(input,SCOPE,FOLLOW_SCOPE_in_ruleScopeSpec542); if (state.failed) return ;
match(input,SCOPE,FOLLOW_SCOPE_in_ruleScopeSpec548); if (state.failed) return ;
match(input, Token.DOWN, null); if (state.failed) return ;
// CollectSymbols.g:194:16: (ids+= ID )+
// CollectSymbols.g:211:16: (ids+= ID )+
int cnt5=0;
loop5:
do {
@ -1017,9 +1026,9 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
switch (alt5) {
case 1 :
// CollectSymbols.g:194:16: ids+= ID
// CollectSymbols.g:211:16: ids+= ID
{
ids=(GrammarAST)match(input,ID,FOLLOW_ID_in_ruleScopeSpec546); if (state.failed) return ;
ids=(GrammarAST)match(input,ID,FOLLOW_ID_in_ruleScopeSpec552); if (state.failed) return ;
if (list_ids==null) list_ids=new ArrayList();
list_ids.add(ids);
@ -1066,14 +1075,14 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
};
// $ANTLR start "rewriteElement"
// CollectSymbols.g:198:1: rewriteElement : {...}? ( TOKEN_REF | RULE_REF | STRING_LITERAL | LABEL ) ;
// CollectSymbols.g:215:1: rewriteElement : {...}? ( TOKEN_REF | RULE_REF | STRING_LITERAL | LABEL ) ;
public final CollectSymbols.rewriteElement_return rewriteElement() throws RecognitionException {
CollectSymbols.rewriteElement_return retval = new CollectSymbols.rewriteElement_return();
retval.start = input.LT(1);
try {
// CollectSymbols.g:200:2: ({...}? ( TOKEN_REF | RULE_REF | STRING_LITERAL | LABEL ) )
// CollectSymbols.g:201:6: {...}? ( TOKEN_REF | RULE_REF | STRING_LITERAL | LABEL )
// CollectSymbols.g:217:2: ({...}? ( TOKEN_REF | RULE_REF | STRING_LITERAL | LABEL ) )
// CollectSymbols.g:218:6: {...}? ( TOKEN_REF | RULE_REF | STRING_LITERAL | LABEL )
{
if ( !((inContext("RESULT ..."))) ) {
if (state.backtracking>0) {state.failed=true; return retval;}
@ -1110,7 +1119,7 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
};
// $ANTLR start "labeledElement"
// CollectSymbols.g:205:1: labeledElement : {...}? ( ^( ASSIGN id= ID e= . ) | ^( PLUS_ASSIGN id= ID e= . ) ) ;
// CollectSymbols.g:222:1: labeledElement : {...}? ( ^( ASSIGN id= ID e= . ) | ^( PLUS_ASSIGN id= ID e= . ) ) ;
public final CollectSymbols.labeledElement_return labeledElement() throws RecognitionException {
CollectSymbols.labeledElement_return retval = new CollectSymbols.labeledElement_return();
retval.start = input.LT(1);
@ -1119,14 +1128,14 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
GrammarAST e=null;
try {
// CollectSymbols.g:211:2: ({...}? ( ^( ASSIGN id= ID e= . ) | ^( PLUS_ASSIGN id= ID e= . ) ) )
// CollectSymbols.g:211:4: {...}? ( ^( ASSIGN id= ID e= . ) | ^( PLUS_ASSIGN id= ID e= . ) )
// CollectSymbols.g:228:2: ({...}? ( ^( ASSIGN id= ID e= . ) | ^( PLUS_ASSIGN id= ID e= . ) ) )
// CollectSymbols.g:228:4: {...}? ( ^( ASSIGN id= ID e= . ) | ^( PLUS_ASSIGN id= ID e= . ) )
{
if ( !((inContext("RULE ..."))) ) {
if (state.backtracking>0) {state.failed=true; return retval;}
throw new FailedPredicateException(input, "labeledElement", "inContext(\"RULE ...\")");
}
// CollectSymbols.g:212:3: ( ^( ASSIGN id= ID e= . ) | ^( PLUS_ASSIGN id= ID e= . ) )
// CollectSymbols.g:229:3: ( ^( ASSIGN id= ID e= . ) | ^( PLUS_ASSIGN id= ID e= . ) )
int alt7=2;
int LA7_0 = input.LA(1);
@ -1145,12 +1154,12 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
}
switch (alt7) {
case 1 :
// CollectSymbols.g:212:5: ^( ASSIGN id= ID e= . )
// CollectSymbols.g:229:5: ^( ASSIGN id= ID e= . )
{
match(input,ASSIGN,FOLLOW_ASSIGN_in_labeledElement610); if (state.failed) return retval;
match(input,ASSIGN,FOLLOW_ASSIGN_in_labeledElement616); if (state.failed) return retval;
match(input, Token.DOWN, null); if (state.failed) return retval;
id=(GrammarAST)match(input,ID,FOLLOW_ID_in_labeledElement614); if (state.failed) return retval;
id=(GrammarAST)match(input,ID,FOLLOW_ID_in_labeledElement620); if (state.failed) return retval;
e=(GrammarAST)input.LT(1);
matchAny(input); if (state.failed) return retval;
@ -1159,12 +1168,12 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
}
break;
case 2 :
// CollectSymbols.g:213:5: ^( PLUS_ASSIGN id= ID e= . )
// CollectSymbols.g:230:5: ^( PLUS_ASSIGN id= ID e= . )
{
match(input,PLUS_ASSIGN,FOLLOW_PLUS_ASSIGN_in_labeledElement626); if (state.failed) return retval;
match(input,PLUS_ASSIGN,FOLLOW_PLUS_ASSIGN_in_labeledElement632); if (state.failed) return retval;
match(input, Token.DOWN, null); if (state.failed) return retval;
id=(GrammarAST)match(input,ID,FOLLOW_ID_in_labeledElement630); if (state.failed) return retval;
id=(GrammarAST)match(input,ID,FOLLOW_ID_in_labeledElement636); if (state.failed) return retval;
e=(GrammarAST)input.LT(1);
matchAny(input); if (state.failed) return retval;
@ -1181,8 +1190,8 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
if ( state.backtracking==1 ) {
LabelElementPair lp = new LabelElementPair(g, id, e, ((GrammarAST)retval.start).getType());
currentRule.labelDefs.map((id!=null?id.getText():null), lp);
currentRule.alt[currentAlt].labelDefs.map((id!=null?id.getText():null), id);
//currentRule.labelDefs.map((id!=null?id.getText():null), lp);
currentRule.alt[currentAlt].labelDefs.map((id!=null?id.getText():null), lp);
}
}
@ -1200,7 +1209,7 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
};
// $ANTLR start "terminal"
// CollectSymbols.g:217:1: terminal : ({...}? STRING_LITERAL | TOKEN_REF );
// CollectSymbols.g:234:1: terminal : ({...}? STRING_LITERAL | TOKEN_REF );
public final CollectSymbols.terminal_return terminal() throws RecognitionException {
CollectSymbols.terminal_return retval = new CollectSymbols.terminal_return();
retval.start = input.LT(1);
@ -1209,7 +1218,7 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
GrammarAST TOKEN_REF15=null;
try {
// CollectSymbols.g:218:5: ({...}? STRING_LITERAL | TOKEN_REF )
// CollectSymbols.g:235:5: ({...}? STRING_LITERAL | TOKEN_REF )
int alt8=2;
int LA8_0 = input.LA(1);
@ -1228,13 +1237,13 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
}
switch (alt8) {
case 1 :
// CollectSymbols.g:218:7: {...}? STRING_LITERAL
// CollectSymbols.g:235:7: {...}? STRING_LITERAL
{
if ( !((!inContext("TOKENS ASSIGN"))) ) {
if (state.backtracking>0) {state.failed=true; return retval;}
throw new FailedPredicateException(input, "terminal", "!inContext(\"TOKENS ASSIGN\")");
}
STRING_LITERAL14=(GrammarAST)match(input,STRING_LITERAL,FOLLOW_STRING_LITERAL_in_terminal656); if (state.failed) return retval;
STRING_LITERAL14=(GrammarAST)match(input,STRING_LITERAL,FOLLOW_STRING_LITERAL_in_terminal662); if (state.failed) return retval;
if ( state.backtracking==1 ) {
terminals.add(((GrammarAST)retval.start));
@ -1248,9 +1257,9 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
}
break;
case 2 :
// CollectSymbols.g:226:7: TOKEN_REF
// CollectSymbols.g:243:7: TOKEN_REF
{
TOKEN_REF15=(GrammarAST)match(input,TOKEN_REF,FOLLOW_TOKEN_REF_in_terminal671); if (state.failed) return retval;
TOKEN_REF15=(GrammarAST)match(input,TOKEN_REF,FOLLOW_TOKEN_REF_in_terminal677); if (state.failed) return retval;
if ( state.backtracking==1 ) {
terminals.add(TOKEN_REF15);
@ -1278,15 +1287,15 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
// $ANTLR start "ruleref"
// CollectSymbols.g:236:1: ruleref : RULE_REF ;
// CollectSymbols.g:253:1: ruleref : RULE_REF ;
public final void ruleref() throws RecognitionException {
GrammarAST RULE_REF16=null;
try {
// CollectSymbols.g:238:5: ( RULE_REF )
// CollectSymbols.g:238:7: RULE_REF
// CollectSymbols.g:255:5: ( RULE_REF )
// CollectSymbols.g:255:7: RULE_REF
{
RULE_REF16=(GrammarAST)match(input,RULE_REF,FOLLOW_RULE_REF_in_ruleref696); if (state.failed) return ;
RULE_REF16=(GrammarAST)match(input,RULE_REF,FOLLOW_RULE_REF_in_ruleref702); if (state.failed) return ;
if ( state.backtracking==1 ) {
rulerefs.add(RULE_REF16);
@ -1501,26 +1510,26 @@ public class CollectSymbols extends org.antlr.v4.runtime.tree.TreeFilter {
public static final BitSet FOLLOW_AT_in_rulelNamedAction408 = new BitSet(new long[]{0x0000000000000004L});
public static final BitSet FOLLOW_ID_in_rulelNamedAction410 = new BitSet(new long[]{0x0000000000010000L});
public static final BitSet FOLLOW_ACTION_in_rulelNamedAction412 = new BitSet(new long[]{0x0000000000000008L});
public static final BitSet FOLLOW_ACTION_in_ruleAction430 = new BitSet(new long[]{0x0000000000000002L});
public static final BitSet FOLLOW_CATCH_in_exceptionHandler444 = new BitSet(new long[]{0x0000000000000004L});
public static final BitSet FOLLOW_ARG_ACTION_in_exceptionHandler446 = new BitSet(new long[]{0x0000000000010000L});
public static final BitSet FOLLOW_ACTION_in_exceptionHandler448 = new BitSet(new long[]{0x0000000000000008L});
public static final BitSet FOLLOW_FINALLY_in_finallyClause463 = new BitSet(new long[]{0x0000000000000004L});
public static final BitSet FOLLOW_ACTION_in_finallyClause465 = new BitSet(new long[]{0x0000000000000008L});
public static final BitSet FOLLOW_ARG_ACTION_in_ruleArg485 = new BitSet(new long[]{0x0000000000000002L});
public static final BitSet FOLLOW_RETURNS_in_ruleReturns502 = new BitSet(new long[]{0x0000000000000004L});
public static final BitSet FOLLOW_ARG_ACTION_in_ruleReturns504 = new BitSet(new long[]{0x0000000000000008L});
public static final BitSet FOLLOW_SCOPE_in_ruleScopeSpec527 = new BitSet(new long[]{0x0000000000000004L});
public static final BitSet FOLLOW_ACTION_in_ruleScopeSpec529 = new BitSet(new long[]{0x0000000000000008L});
public static final BitSet FOLLOW_SCOPE_in_ruleScopeSpec542 = new BitSet(new long[]{0x0000000000000004L});
public static final BitSet FOLLOW_ID_in_ruleScopeSpec546 = new BitSet(new long[]{0x0000000000000008L,0x0000000000800000L});
public static final BitSet FOLLOW_set_in_rewriteElement574 = new BitSet(new long[]{0x0000000000000002L});
public static final BitSet FOLLOW_ASSIGN_in_labeledElement610 = new BitSet(new long[]{0x0000000000000004L});
public static final BitSet FOLLOW_ID_in_labeledElement614 = new BitSet(new long[]{0xFFFFFFFFFFFFFFF0L,0x0000003FFFFFFFFFL});
public static final BitSet FOLLOW_PLUS_ASSIGN_in_labeledElement626 = new BitSet(new long[]{0x0000000000000004L});
public static final BitSet FOLLOW_ID_in_labeledElement630 = new BitSet(new long[]{0xFFFFFFFFFFFFFFF0L,0x0000003FFFFFFFFFL});
public static final BitSet FOLLOW_STRING_LITERAL_in_terminal656 = new BitSet(new long[]{0x0000000000000002L});
public static final BitSet FOLLOW_TOKEN_REF_in_terminal671 = new BitSet(new long[]{0x0000000000000002L});
public static final BitSet FOLLOW_RULE_REF_in_ruleref696 = new BitSet(new long[]{0x0000000000000002L});
public static final BitSet FOLLOW_ACTION_in_ruleAction432 = new BitSet(new long[]{0x0000000000000002L});
public static final BitSet FOLLOW_CATCH_in_exceptionHandler448 = new BitSet(new long[]{0x0000000000000004L});
public static final BitSet FOLLOW_ARG_ACTION_in_exceptionHandler450 = new BitSet(new long[]{0x0000000000010000L});
public static final BitSet FOLLOW_ACTION_in_exceptionHandler452 = new BitSet(new long[]{0x0000000000000008L});
public static final BitSet FOLLOW_FINALLY_in_finallyClause469 = new BitSet(new long[]{0x0000000000000004L});
public static final BitSet FOLLOW_ACTION_in_finallyClause471 = new BitSet(new long[]{0x0000000000000008L});
public static final BitSet FOLLOW_ARG_ACTION_in_ruleArg491 = new BitSet(new long[]{0x0000000000000002L});
public static final BitSet FOLLOW_RETURNS_in_ruleReturns508 = new BitSet(new long[]{0x0000000000000004L});
public static final BitSet FOLLOW_ARG_ACTION_in_ruleReturns510 = new BitSet(new long[]{0x0000000000000008L});
public static final BitSet FOLLOW_SCOPE_in_ruleScopeSpec533 = new BitSet(new long[]{0x0000000000000004L});
public static final BitSet FOLLOW_ACTION_in_ruleScopeSpec535 = new BitSet(new long[]{0x0000000000000008L});
public static final BitSet FOLLOW_SCOPE_in_ruleScopeSpec548 = new BitSet(new long[]{0x0000000000000004L});
public static final BitSet FOLLOW_ID_in_ruleScopeSpec552 = new BitSet(new long[]{0x0000000000000008L,0x0000000000800000L});
public static final BitSet FOLLOW_set_in_rewriteElement580 = new BitSet(new long[]{0x0000000000000002L});
public static final BitSet FOLLOW_ASSIGN_in_labeledElement616 = new BitSet(new long[]{0x0000000000000004L});
public static final BitSet FOLLOW_ID_in_labeledElement620 = new BitSet(new long[]{0xFFFFFFFFFFFFFFF0L,0x0000003FFFFFFFFFL});
public static final BitSet FOLLOW_PLUS_ASSIGN_in_labeledElement632 = new BitSet(new long[]{0x0000000000000004L});
public static final BitSet FOLLOW_ID_in_labeledElement636 = new BitSet(new long[]{0xFFFFFFFFFFFFFFF0L,0x0000003FFFFFFFFFL});
public static final BitSet FOLLOW_STRING_LITERAL_in_terminal662 = new BitSet(new long[]{0x0000000000000002L});
public static final BitSet FOLLOW_TOKEN_REF_in_terminal677 = new BitSet(new long[]{0x0000000000000002L});
public static final BitSet FOLLOW_RULE_REF_in_ruleref702 = new BitSet(new long[]{0x0000000000000002L});
}

View File

@ -4,7 +4,9 @@ import org.antlr.runtime.RecognitionException;
import org.antlr.runtime.tree.BufferedTreeNodeStream;
import org.antlr.v4.parse.ASTVerifier;
import org.antlr.v4.parse.GrammarASTAdaptor;
import org.antlr.v4.tool.*;
import org.antlr.v4.tool.ErrorManager;
import org.antlr.v4.tool.Grammar;
import org.antlr.v4.tool.Rule;
/** */
public class SemanticPipeline {
@ -45,28 +47,14 @@ public class SemanticPipeline {
// CHECK FOR SYMBOL COLLISIONS
SymbolChecks symcheck = new SymbolChecks(g, collector);
symcheck.examine();
symcheck.examine(); // side-effect: strip away redef'd rules.
// STORE RULES IN GRAMMAR
for (Rule r : collector.rules) g.defineRule(r);
// CHECK ATTRIBUTE EXPRESSIONS FOR SEMANTIC VALIDITY
checkAttributeExpressions(g, collector);
AttributeChecks.checkAllAttributeExpressions(g, collector.rules);
// ASSIGN TOKEN TYPES
}
public void checkAttributeExpressions(Grammar g, CollectSymbols collector) {
for (Rule r : collector.rules) {
for (GrammarAST a : r.namedActions.values()) {
AttributeChecks checker = new AttributeChecks(g, r, null, a, a.getText());
checker.examine();
}
for (int i=1; i<=r.numberOfAlts; i++) {
Alternative alt = r.alt[i];
for (GrammarAST a : alt.actions) {
AttributeChecks checker =
new AttributeChecks(g, r, alt, a, a.getText());
checker.examine();
}
}
}
}
}

View File

@ -9,6 +9,8 @@ import java.util.*;
/** Check for symbol problems; no side-effects. Inefficient to walk rules
* and such multiple times, but I like isolating all error checking outside
* of code that actually defines symbols etc...
*
* Side-effect: strip away redef'd rules.
*/
public class SymbolChecks {
protected Grammar g;
@ -48,6 +50,8 @@ public class SymbolChecks {
public void checkForRuleConflicts(List<Rule> rules) {
if ( rules==null ) return;
int i = 0;
List<Integer> toRemove = new ArrayList<Integer>();
for (Rule r : collector.rules) {
if ( nameToRuleMap.get(r.name)==null ) {
nameToRuleMap.put(r.name, r);
@ -56,13 +60,16 @@ public class SymbolChecks {
GrammarAST idNode = (GrammarAST)r.ast.getChild(0);
ErrorManager.grammarError(ErrorType.RULE_REDEFINITION,
g.fileName, idNode.token, r.name);
toRemove.add(i);
}
if ( globalScopeNames.contains(r.name) ) {
GrammarAST idNode = (GrammarAST)r.ast.getChild(0);
ErrorManager.grammarError(ErrorType.SYMBOL_CONFLICTS_WITH_GLOBAL_SCOPE,
g.fileName, idNode.token, r.name);
}
i++;
}
collector.rules.removeAll(toRemove);
}
public void checkScopeRedefinitions(List<GrammarAST> scopes) {
@ -178,13 +185,16 @@ public class SymbolChecks {
checkForRuleScopeAttributeConflict(r);
Map<String, LabelElementPair> labelNameSpace =
new HashMap<String, LabelElementPair>();
for (List<LabelElementPair> pairs : r.labelDefs.values() ) {
for (LabelElementPair p : pairs) {
checkForLabelConflict(r, p.label);
String name = p.label.getText();
LabelElementPair prev = labelNameSpace.get(name);
if ( prev==null ) labelNameSpace.put(name, p);
else checkForTypeMismatch(prev, p);
for (int i=1; i<=r.numberOfAlts; i++) {
Alternative a = r.alt[i];
for (List<LabelElementPair> pairs : a.labelDefs.values() ) {
for (LabelElementPair p : pairs) {
checkForLabelConflict(r, p.label);
String name = p.label.getText();
LabelElementPair prev = labelNameSpace.get(name);
if ( prev==null ) labelNameSpace.put(name, p);
else checkForTypeMismatch(prev, p);
}
}
}
}

View File

@ -0,0 +1,11 @@
package org.antlr.v4.tool;
import org.antlr.runtime.Token;
public class ActionAST extends GrammarAST {
// Alt, rule, grammar space
public SymbolSpace space;
public ActionAST(Token t) { super(t); }
public ActionAST(int type) { super(type); }
public ActionAST(int type, Token t) { super(type, t); }
}

View File

@ -9,7 +9,9 @@ import java.util.List;
/** Record use/def information about an outermost alternative in a subrule
* or rule of a grammar.
*/
public class Alternative {
public class Alternative implements SymbolSpace {
Rule rule;
// token IDs, string literals in this alt
public MultiMap<String, GrammarAST> tokenRefs = new MultiMap<String, GrammarAST>();
@ -17,7 +19,7 @@ public class Alternative {
public MultiMap<String, GrammarAST> ruleRefs = new MultiMap<String, GrammarAST>();
/** A list of all LabelElementPair attached to tokens like id=ID, ids+=ID */
public MultiMap<String, GrammarAST> labelDefs = new MultiMap<String, GrammarAST>();
public MultiMap<String, LabelElementPair> labelDefs = new MultiMap<String, LabelElementPair>();
// track all token, rule, label refs in rewrite (right of ->)
public List<GrammarAST> rewriteElements = new ArrayList<GrammarAST>();
@ -27,8 +29,53 @@ public class Alternative {
* We need to examine these actions before code generation so
* that we can detect refs to $rule.attr etc...
*/
public List<GrammarAST> actions = new ArrayList<GrammarAST>();
public List<ActionAST> actions = new ArrayList<ActionAST>();
public Alternative() {
public Alternative(Rule r) { this.rule = r; }
public SymbolSpace getParent() {
return null;
}
/** Is isolated x a token/rule/label ref? */
public boolean resolves(String x, ActionAST node) {
boolean inAlt =
tokenRefs.get(x)!=null||
ruleRefs.get(x)!=null ||
labelDefs.get(x)!=null;
if ( inAlt ) return inAlt;
return rule.resolves(x, node);
}
/** Find x as token/rule/label ref then find y in properties list. */
public boolean resolves(String x, String y, ActionAST node) {
if ( tokenRefs.get(x)!=null ) { // token ref in this alt?
return rule.getPredefinedScope(LabelType.TOKEN_LABEL).get(y)!=null;
}
if ( ruleRefs.get(x)!=null ) { // rule ref in this alt?
// look up rule, ask it to resolve y (must be retval or predefined)
return rule.g.getRule(x).resolvesAsRetvalOrProperty(y);
}
List<LabelElementPair> labels = labelDefs.get(x); // label?
if ( labels!=null ) {
// it's a label ref, compute scope from label type and grammar type
LabelElementPair anyLabelDef = labels.get(0);
if ( rule.getPredefinedScope(anyLabelDef.type).get(y)!=null) return true;
if ( anyLabelDef.type==LabelType.RULE_LABEL ) {
Rule ref = rule.g.getRule(anyLabelDef.element.getText());
return ref.resolvesAsRetvalOrProperty(y);
}
}
return false;
}
public boolean resolveToRuleRef(String x, ActionAST node) {
if ( ruleRefs.get(x)!=null ) return true;
List<LabelElementPair> labels = labelDefs.get(x);
if ( labels!=null ) { // it's a label ref. is it a rule label?
LabelElementPair anyLabelDef = labels.get(0);
if ( anyLabelDef.type==LabelType.RULE_LABEL ) return true;
}
return false;
}
}

View File

@ -79,6 +79,7 @@ public enum ErrorType {
UNKNOWN_SIMPLE_ATTRIBUTE(ErrorSeverity.ERROR, true, true),
INVALID_RULE_PARAMETER_REF(ErrorSeverity.ERROR, true, true),
UNKNOWN_RULE_ATTRIBUTE(ErrorSeverity.ERROR, true, true),
UNKNOWN_ATTRIBUTE_IN_SCOPE(ErrorSeverity.ERROR, true, true),
ISOLATED_RULE_SCOPE(ErrorSeverity.ERROR, true, true),
SYMBOL_CONFLICTS_WITH_GLOBAL_SCOPE(ErrorSeverity.ERROR, true, true),
LABEL_CONFLICTS_WITH_RULE(ErrorSeverity.ERROR, true, true),

View File

@ -8,11 +8,10 @@ import org.antlr.v4.Tool;
import org.antlr.v4.parse.ANTLRLexer;
import org.antlr.v4.parse.ANTLRParser;
import org.antlr.v4.parse.GrammarASTAdaptor;
import org.stringtemplate.v4.misc.MultiMap;
import java.util.*;
public class Grammar {
public class Grammar implements SymbolSpace {
public static final Set doNotCopyOptionsToLexer =
new HashSet() {
{
@ -46,8 +45,8 @@ public class Grammar {
/** If we're imported, who imported us? If null, implies grammar is root */
public Grammar parent;
protected List<Grammar> importedGrammars;
protected Map<String, Rule> rules = new LinkedHashMap<String, Rule>();
public List<Grammar> importedGrammars;
public Map<String, Rule> rules = new LinkedHashMap<String, Rule>();
/** Map a scope to a map of name:action pairs.
* The code generator will use this to fill holes in the output files.
@ -122,7 +121,7 @@ public class Grammar {
}
public void defineRule(Rule r) { rules.put(r.name, r); }
public Rule getRule(String name) { return rules.get(name); }
/** Get list of all delegates from all grammars in the delegate subtree of g.
@ -211,6 +210,20 @@ public class Grammar {
return null;
}
public SymbolSpace getParent() { return null; }
public boolean resolves(String x, ActionAST node) {
return false;
}
public boolean resolves(String x, String y, ActionAST node) {
return false;
}
public boolean resolveToRuleRef(String x, ActionAST node) {
return false;
}
/** Given a grammar type, what should be the default action scope?
* If I say @members in a COMBINED grammar, for example, the
* default scope should be "parser".

View File

@ -1,15 +1,11 @@
package org.antlr.v4.tool;
import org.antlr.runtime.Token;
import org.antlr.v4.parse.ANTLRParser;
import org.stringtemplate.v4.misc.MultiMap;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.*;
public class Rule {
public class Rule implements SymbolSpace {
/** Rule refs have a predefined set of attributes as well as
* the return values and args.
*/
@ -57,20 +53,20 @@ public class Rule {
* I track the AST node for the action in case I need the line number
* for errors.
*/
public Map<String, GrammarAST> namedActions =
new HashMap<String, GrammarAST>();
public Map<String, ActionAST> namedActions =
new HashMap<String, ActionAST>();
/** Track exception handlers, finally action */
public List<GrammarAST> exceptionActions = new ArrayList<GrammarAST>();
public List<ActionAST> exceptionActions = new ArrayList<ActionAST>();
public int numberOfAlts;
/** Labels are visible to all alts in a rule. Record all defs here.
* We need to ensure labels are used to track same kind of symbols.
* Tracks all label defs for a label.
*/
public MultiMap<String, LabelElementPair> labelDefs =
new MultiMap<String, LabelElementPair>();
*/
public Alternative[] alt;
@ -80,61 +76,151 @@ public class Rule {
this.ast = ast;
this.numberOfAlts = numberOfAlts;
alt = new Alternative[numberOfAlts+1]; // 1..n
for (int i=1; i<=numberOfAlts; i++) alt[i] = new Alternative();
for (int i=1; i<=numberOfAlts; i++) alt[i] = new Alternative(this);
}
public boolean resolves(String name, Alternative alt) {
Attribute a = resolve(name);
if ( a!=null ) return true; // ok
if ( alt.tokenRefs.get(name)!=null||
alt.ruleRefs.get(name)!=null ||
alt.labelDefs.get(name)!=null )
{
return true;
}
return false;
public SymbolSpace getParent() { return g; }
/** Is isolated x an arg, retval, predefined prop? */
public boolean resolves(String x, ActionAST node) {
if ( resolvesAsRetvalOrProperty(x) ) return true;
if ( args.get(x)!=null ) return true;
// resolve outside of an alt?
if ( node.space instanceof Alternative ) return getParent().resolves(x, node);
return getLabelNames().contains(x); // can see all labels if not in alt
}
/** Look up name from context of this rule and an alternative.
* Find an arg, retval, predefined property, or label/rule/token ref.
/** For $x.y, is x an arg, retval, predefined prop, token/rule/label ref?
* If so, make sure y resolves within that perspective.
*/
public Attribute resolve(String name) {
Attribute a = args.get(name); if ( a!=null ) return a;
a = retvals.get(name); if ( a!=null ) return a;
String grammarLabelKey = g.getTypeString() + ":" + LabelType.RULE_LABEL;
AttributeScope properties =
Grammar.grammarAndLabelRefTypeToScope.get(grammarLabelKey);
a = properties.get(name);
if ( a!=null ) return a;
//alt[currentAlt].tokenRefs
// not here? look in grammar for global scope
return null;
}
public AttributeScope resolveScope(String name, Alternative alt) {
AttributeScope s = args; if ( s.get(name)!=null ) return s;
s = retvals; if ( s.get(name)!=null ) return s;
s = retvals; if ( s.get(name)!=null ) return s;
String grammarLabelKey = g.getTypeString() + ":" + LabelType.RULE_LABEL;
s = Grammar.grammarAndLabelRefTypeToScope.get(grammarLabelKey);
if ( s.get(name)!=null ) return s;
if ( alt.tokenRefs.get(name)!=null ) {
grammarLabelKey = g.getTypeString() + ":" + LabelType.TOKEN_LABEL;
return Grammar.grammarAndLabelRefTypeToScope.get(grammarLabelKey);
public boolean resolves(String x, String y, ActionAST node) {
if ( x.equals(this.name) ) { // $x.y ref in rule x is same as $y
return resolves(y, node);
}
if ( alt.ruleRefs.get(name)!=null ) {
grammarLabelKey = g.getTypeString() + ":" + LabelType.RULE_LABEL;
return Grammar.grammarAndLabelRefTypeToScope.get(grammarLabelKey);
MultiMap<String, LabelElementPair> labelDefs = null;
if ( node.space instanceof Alternative) {
labelDefs = ((Alternative)node.space).labelDefs;
}
List<LabelElementPair> labels = labelDefs.get(name);
else labelDefs = getLabelDefs();
List<LabelElementPair> labels = labelDefs.get(x); // label?
if ( labels!=null ) {
// it's a label ref, compute scope from label type and grammar type
LabelElementPair anyLabelDef = labels.get(0);
grammarLabelKey = g.getTypeString() + ":" + anyLabelDef.type;
return Grammar.grammarAndLabelRefTypeToScope.get(grammarLabelKey);
// predefined?
if ( getPredefinedScope(anyLabelDef.type).get(y)!=null) return true;
if ( anyLabelDef.type==LabelType.RULE_LABEL ) {
Rule ref = g.getRule(anyLabelDef.element.getText());
return ref.resolvesAsRetvalOrProperty(y);
}
}
return null;
return false;
}
public boolean resolveToRuleRef(String x, ActionAST node) {
if ( x.equals(this.name) ) return true;
MultiMap<String, LabelElementPair> labelDefs = null;
if ( node.space instanceof Alternative) {
labelDefs = ((Alternative)node.space).labelDefs;
}
else labelDefs = getLabelDefs();
List<LabelElementPair> labels = labelDefs.get(x);
if ( labels!=null ) { // it's a label ref. is it a rule label?
LabelElementPair anyLabelDef = labels.get(0);
if ( anyLabelDef.type==LabelType.RULE_LABEL ) return true;
}
return false;
}
public boolean resolvesAsRetvalOrProperty(String y) {
if ( retvals.get(y)!=null ) return true;
AttributeScope s = getPredefinedScope(LabelType.RULE_LABEL);
return s.get(y)!=null;
}
public Set<String> getRuleRefs() {
Set<String> refs = new HashSet<String>();
for (Alternative a : alt) refs.addAll(a.ruleRefs.keySet());
return refs;
}
public Set<String> getLabelNames() {
Set<String> refs = new HashSet<String>();
for (int i=1; i<=numberOfAlts; i++) {
refs.addAll(alt[i].labelDefs.keySet());
}
return refs;
}
public MultiMap<String, LabelElementPair> getLabelDefs() {
MultiMap<String, LabelElementPair> defs =
new MultiMap<String, LabelElementPair>();
for (int i=1; i<=numberOfAlts; i++) {
for (List<LabelElementPair> pairs : alt[i].labelDefs.values()) {
for (LabelElementPair p : pairs) {
defs.map(p.label.getText(), p);
}
}
}
return defs;
}
/** Look up name from context of this rule and an alternative.
* Find an arg, retval, predefined property, or label/rule/token ref.
*/
// public Attribute resolve(String name) {
// Attribute a = args.get(name); if ( a!=null ) return a;
// a = retvals.get(name); if ( a!=null ) return a;
// AttributeScope properties = getPredefinedScope(LabelType.RULE_LABEL);
// a = properties.get(name);
// if ( a!=null ) return a;
//
// //alt[currentAlt].tokenRefs
// // not here? look in grammar for global scope
// return null;
// }
/** Resolve x in $x.y to
*/
// public AttributeScope resolveScope(String name, Alternative alt) {
// AttributeScope s = null;
// if ( this.name.equals(name) ) { // $r ref in rule r
// s = resolveLocalAttributeScope(name);
// if ( s!=null ) return s;
// }
//
// if ( alt.tokenRefs.get(name)!=null ) { // token ref in this alt?
// return getPredefinedScope(LabelType.TOKEN_LABEL);
// }
// if ( alt.ruleRefs.get(name)!=null ) { // rule ref in this alt?
// s = getLocalAttributeScope(name);
// if ( s!=null ) return s;
// }
// List<GrammarAST> labels = alt.labelDefs.get(name); // label
// if ( labels!=null ) {
// // it's a label ref, compute scope from label type and grammar type
// LabelElementPair anyLabelDef = labels.get(0);
// return getPredefinedScope(anyLabelDef.type);
// }
// return null;
// }
//
// /** Look for name in the arg, return value, predefined property,
// * or dynamic scope attribute list for this rule.
// */
// public AttributeScope resolveLocalAttributeScope(String name) {
// if ( args.get(name)!=null ) return args;
// if ( retvals.get(name)!=null ) return retvals;
// AttributeScope s = getPredefinedScope(LabelType.RULE_LABEL);
// if ( s.get(name)!=null ) return s;
// if ( scope!=null && scope.get(name)!=null ) return scope;
// return null;
// }
public AttributeScope getPredefinedScope(LabelType ltype) {
String grammarLabelKey = g.getTypeString() + ":" + ltype;
return Grammar.grammarAndLabelRefTypeToScope.get(grammarLabelKey);
}
@Override
@ -143,7 +229,6 @@ public class Rule {
"name='" + name + '\'' +
", args=" + args +
", retvals=" + retvals +
", labels=" + labelDefs +
", scope=" + scope +
'}';
}

View File

@ -0,0 +1,13 @@
package org.antlr.v4.tool;
/** Grammars, rules, and alternatives all have symbols visible to
* actions. To evaluate attr exprs, ask action for its space
* then ask space to resolve. If not found in one space we look
* at parent. Alt's parent is rule; rule's parent is grammar.
*/
public interface SymbolSpace {
public SymbolSpace getParent();
public boolean resolves(String x, ActionAST node);
public boolean resolves(String x, String y, ActionAST node);
public boolean resolveToRuleRef(String x, ActionAST node);
}