public virtual void TranslateLeftRecursiveRules()
{
string language = g.GetOptionString("language");
// translate all recursive rules
IList <string> leftRecursiveRuleNames = new List <string>();
foreach (Rule r in rules)
{
if (!Grammar.IsTokenName(r.name))
{
if (LeftRecursiveRuleAnalyzer.HasImmediateRecursiveRuleRefs(r.ast, r.name))
{
bool fitsPattern = TranslateLeftRecursiveRule(ast, (LeftRecursiveRule)r, language);
if (fitsPattern)
{
leftRecursiveRuleNames.Add(r.name);
}
else
{
// Suppressed since this build has secondary support for left recursive rules that don't
// match the patterns for precedence rules.
// better given an error that non-conforming left-recursion exists
//tool.errMgr.grammarError(ErrorType.NONCONFORMING_LR_RULE, g.fileName, ((GrammarAST)r.ast.GetChild(0)).Token, r.name);
}
}
}
}
// update all refs to recursive rules to have [0] argument
foreach (GrammarAST r in ast.GetNodesWithType(ANTLRParser.RULE_REF))
{
if (r.Parent.Type == ANTLRParser.RULE)
{
continue; // must be rule def
}
if (((GrammarASTWithOptions)r).GetOptionString(PRECEDENCE_OPTION_NAME) != null)
{
continue; // already has arg; must be in rewritten rule
}
if (leftRecursiveRuleNames.Contains(r.Text))
{
// found ref to recursive rule not already rewritten with arg
((GrammarASTWithOptions)r).SetOption(PRECEDENCE_OPTION_NAME, (GrammarAST) new GrammarASTAdaptor().Create(ANTLRParser.INT, "0"));
}
}
}