use of org.antlr.v4.runtime.misc.Nullable in project antlr4 by tunnelvisionlabs.
the class LexerATNFactory method createLexerAction.
@Nullable
private LexerAction createLexerAction(@NotNull GrammarAST ID, @Nullable GrammarAST arg) {
String command = ID.getText();
checkCommands(command, ID.getToken());
if ("skip".equals(command) && arg == null) {
return LexerSkipAction.INSTANCE;
} else if ("more".equals(command) && arg == null) {
return LexerMoreAction.INSTANCE;
} else if ("popMode".equals(command) && arg == null) {
return LexerPopModeAction.INSTANCE;
} else if ("mode".equals(command) && arg != null) {
String modeName = arg.getText();
Integer mode = getModeConstantValue(modeName, arg.getToken());
if (mode == null) {
return null;
}
return new LexerModeAction(mode);
} else if ("pushMode".equals(command) && arg != null) {
String modeName = arg.getText();
Integer mode = getModeConstantValue(modeName, arg.getToken());
if (mode == null) {
return null;
}
return new LexerPushModeAction(mode);
} else if ("type".equals(command) && arg != null) {
String typeName = arg.getText();
Integer type = getTokenConstantValue(typeName, arg.getToken());
if (type == null) {
return null;
}
return new LexerTypeAction(type);
} else if ("channel".equals(command) && arg != null) {
String channelName = arg.getText();
Integer channel = getChannelConstantValue(channelName, arg.getToken());
if (channel == null) {
return null;
}
return new LexerChannelAction(channel);
} else {
return null;
}
}
use of org.antlr.v4.runtime.misc.Nullable in project antlr4 by tunnelvisionlabs.
the class LeftRecursionDetector method check.
/**
* From state s, look for any transition to a rule that is currently
* being traced. When tracing r, visitedPerRuleCheck has r
* initially. If you reach a rule stop state, return but notify the
* invoking rule that the called rule is nullable. This implies that
* invoking rule must look at follow transition for that invoking state.
*
* The visitedStates tracks visited states within a single rule so
* we can avoid epsilon-loop-induced infinite recursion here. Keep
* filling the cycles in listOfRecursiveCycles and also, as a
* side-effect, set leftRecursiveRules.
*/
public boolean check(Rule enclosingRule, ATNState s, Set<ATNState> visitedStates) {
if (s instanceof RuleStopState)
return true;
if (visitedStates.contains(s))
return false;
visitedStates.add(s);
// System.out.println("visit "+s);
int n = s.getNumberOfTransitions();
boolean stateReachesStopState = false;
for (int i = 0; i < n; i++) {
Transition t = s.transition(i);
if (t instanceof RuleTransition) {
RuleTransition rt = (RuleTransition) t;
Rule r = g.getRule(rt.ruleIndex);
if (rulesVisitedPerRuleCheck.contains((RuleStartState) t.target)) {
addRulesToCycle(enclosingRule, r);
} else {
// must visit if not already visited; mark target, pop when done
rulesVisitedPerRuleCheck.add((RuleStartState) t.target);
// send new visitedStates set per rule invocation
boolean nullable = check(r, t.target, new HashSet<ATNState>());
// we're back from visiting that rule
rulesVisitedPerRuleCheck.remove((RuleStartState) t.target);
if (nullable) {
stateReachesStopState |= check(enclosingRule, rt.followState, visitedStates);
}
}
} else if (t.isEpsilon()) {
stateReachesStopState |= check(enclosingRule, t.target, visitedStates);
}
// else ignore non-epsilon transitions
}
return stateReachesStopState;
}
use of org.antlr.v4.runtime.misc.Nullable in project antlr4 by tunnelvisionlabs.
the class ParserATNSimulator method reportAttemptingFullContext.
protected void reportAttemptingFullContext(@NotNull DFA dfa, @Nullable BitSet conflictingAlts, @NotNull SimulatorState conflictState, int startIndex, int stopIndex) {
if (debug || retry_debug) {
Interval interval = Interval.of(startIndex, stopIndex);
System.out.println("reportAttemptingFullContext decision=" + dfa.decision + ":" + conflictState.s0.configs + ", input=" + parser.getInputStream().getText(interval));
}
if (parser != null)
parser.getErrorListenerDispatch().reportAttemptingFullContext(parser, dfa, startIndex, stopIndex, conflictingAlts, conflictState);
}
use of org.antlr.v4.runtime.misc.Nullable in project antlr4 by tunnelvisionlabs.
the class Trees method getRootOfSubtreeEnclosingRegion.
/**
* Find smallest subtree of t enclosing range startTokenIndex..stopTokenIndex
* inclusively using postorder traversal. Recursive depth-first-search.
*
* @since 4.5
*/
@Nullable
public static ParserRuleContext getRootOfSubtreeEnclosingRegion(@NotNull ParseTree t, // inclusive
int startTokenIndex, // inclusive
int stopTokenIndex) {
int n = t.getChildCount();
for (int i = 0; i < n; i++) {
ParseTree child = t.getChild(i);
ParserRuleContext r = getRootOfSubtreeEnclosingRegion(child, startTokenIndex, stopTokenIndex);
if (r != null)
return r;
}
if (t instanceof ParserRuleContext) {
ParserRuleContext r = (ParserRuleContext) t;
if (// is range fully contained in t?
startTokenIndex >= r.getStart().getTokenIndex() && (r.getStop() == null || stopTokenIndex <= r.getStop().getTokenIndex())) {
// note: r.getStop()==null likely implies that we bailed out of parser and there's nothing to the right
return r;
}
}
return null;
}
use of org.antlr.v4.runtime.misc.Nullable in project antlr4 by tunnelvisionlabs.
the class ParseTreePatternMatcher method matchImpl.
// ---- SUPPORT CODE ----
/**
* Recursively walk {@code tree} against {@code patternTree}, filling
* {@code match.}{@link ParseTreeMatch#labels labels}.
*
* @return the first node encountered in {@code tree} which does not match
* a corresponding node in {@code patternTree}, or {@code null} if the match
* was successful. The specific node returned depends on the matching
* algorithm used by the implementation, and may be overridden.
*/
@Nullable
protected ParseTree matchImpl(@NotNull ParseTree tree, @NotNull ParseTree patternTree, @NotNull MultiMap<String, ParseTree> labels) {
if (tree == null) {
throw new IllegalArgumentException("tree cannot be null");
}
if (patternTree == null) {
throw new IllegalArgumentException("patternTree cannot be null");
}
// x and <ID>, x and y, or x and x; or could be mismatched types
if (tree instanceof TerminalNode && patternTree instanceof TerminalNode) {
TerminalNode t1 = (TerminalNode) tree;
TerminalNode t2 = (TerminalNode) patternTree;
ParseTree mismatchedNode = null;
// both are tokens and they have same type
if (t1.getSymbol().getType() == t2.getSymbol().getType()) {
if (t2.getSymbol() instanceof TokenTagToken) {
// x and <ID>
TokenTagToken tokenTagToken = (TokenTagToken) t2.getSymbol();
// track label->list-of-nodes for both token name and label (if any)
labels.map(tokenTagToken.getTokenName(), tree);
if (tokenTagToken.getLabel() != null) {
labels.map(tokenTagToken.getLabel(), tree);
}
} else if (t1.getText().equals(t2.getText())) {
// x and x
} else {
// x and y
if (mismatchedNode == null) {
mismatchedNode = t1;
}
}
} else {
if (mismatchedNode == null) {
mismatchedNode = t1;
}
}
return mismatchedNode;
}
if (tree instanceof ParserRuleContext && patternTree instanceof ParserRuleContext) {
ParserRuleContext r1 = (ParserRuleContext) tree;
ParserRuleContext r2 = (ParserRuleContext) patternTree;
ParseTree mismatchedNode = null;
// (expr ...) and <expr>
RuleTagToken ruleTagToken = getRuleTagToken(r2);
if (ruleTagToken != null) {
ParseTreeMatch m = null;
if (r1.getRuleContext().getRuleIndex() == r2.getRuleContext().getRuleIndex()) {
// track label->list-of-nodes for both rule name and label (if any)
labels.map(ruleTagToken.getRuleName(), tree);
if (ruleTagToken.getLabel() != null) {
labels.map(ruleTagToken.getLabel(), tree);
}
} else {
if (mismatchedNode == null) {
mismatchedNode = r1;
}
}
return mismatchedNode;
}
// (expr ...) and (expr ...)
if (r1.getChildCount() != r2.getChildCount()) {
if (mismatchedNode == null) {
mismatchedNode = r1;
}
return mismatchedNode;
}
int n = r1.getChildCount();
for (int i = 0; i < n; i++) {
ParseTree childMatch = matchImpl(r1.getChild(i), patternTree.getChild(i), labels);
if (childMatch != null) {
return childMatch;
}
}
return mismatchedNode;
}
// if nodes aren't both tokens or both rule nodes, can't match
return tree;
}
Aggregations