private AstNode CreateNode(ActionRecord reduceAction, SourceSpan sourceSpan, AstNodeList childNodes) { IGrammarTerm nonTeminal = reduceAction.NonTerminal; AstNode result; AstNodeArgs args = new AstNodeArgs(nonTeminal, sourceSpan, childNodes); Type ntNodeType = nonTeminal.NodeType ?? typeof(AstNode); bool isList = nonTeminal.IsSet(TermOptions.IsList); if (isList && childNodes.Count > 1 && childNodes[0].Term == nonTeminal) { result = childNodes[0]; AstNode newChild = childNodes[childNodes.Count - 1]; newChild.Parent = result; result.ChildNodes.Add(newChild); return(result); } if (nonTeminal.IsSet(TermOptions.IsStarList) && childNodes.Count == 1) { childNodes = childNodes[0].ChildNodes; } if (!isList && !nonTeminal.IsSet(TermOptions.IsPunctuation) && childNodes.Count == 1) { Type childNodeType = childNodes[0].Term.NodeType ?? typeof(AstNode); if (childNodeType == ntNodeType || childNodeType.IsSubclassOf(ntNodeType)) { return(childNodes[0]); } } result = null; if (ntNodeType == typeof(AstNode)) { result = new AstNode(args); } else { ConstructorInfo ctor = ntNodeType.GetConstructor(new Type[] { typeof(AstNodeArgs) }); if (ctor == null) { throw new Exception("Failed to located constructor: " + ntNodeType.ToString() + "(AstNodeArgs args)"); } result = (AstNode)ctor.Invoke(new object[] { args }); } return(result); }
private ParserActionType GetActionTypeForOperation(TokenAst current) { ITerminal thisTerm = current.Terminal; for (int i = _stack.Count - 2; i >= 0; i--) { if (_stack[i].Node == null) { continue; } IGrammarTerm term = _stack[i].Node.Term; if (!term.IsSet(TermOptions.IsOperator)) { continue; } ITerminal prevTerm = term as ITerminal; if (prevTerm.Precedence == thisTerm.Precedence) { return(thisTerm.Associativity == Associativity.Left ? ParserActionType.Reduce : ParserActionType.Shift); } ParserActionType result = prevTerm.Precedence > thisTerm.Precedence ? ParserActionType.Reduce : ParserActionType.Shift; return(result); } return(ParserActionType.Shift); }