public override DefiniteAssignmentStatus VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression, DefiniteAssignmentStatus data) { BlockStatement body = anonymousMethodExpression.Body; analysis.ChangeNodeStatus(analysis.beginNodeDict[body], data); return(data); }
public AsLocalFunction(Location loc, string name, AnonymousMethodExpression methodExpr, BlockVariableDeclaration varDecl) { this.loc = loc; this.Name = name; this.MethodExpr = methodExpr; this.VarDecl = varDecl; }
public void EmptyAnonymousMethod() { AnonymousMethodExpression ame = Parse("delegate() {}"); Assert.AreEqual(0, ame.Parameters.Count); Assert.AreEqual(0, ame.Body.Children.Count); }
public override object VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression, object data) { base.VisitAnonymousMethodExpression(anonymousMethodExpression, data); LambdaExpression lambda = new LambdaExpression(); lambda.Parameters = anonymousMethodExpression.Parameters; if (anonymousMethodExpression.Body.Children.Count == 1) { ReturnStatement rs = anonymousMethodExpression.Body.Children[0] as ReturnStatement; if (rs != null) { lambda.ExpressionBody = rs.Expression; } else { lambda.StatementBody = anonymousMethodExpression.Body.Children[0] as Statement; lambda.ReturnType = new TypeReference("System.Void", true); } } else { var visitor = new ReturnStatementVisitor(); anonymousMethodExpression.AcceptVisitor(visitor, null); lambda.StatementBody = anonymousMethodExpression.Body; if (!visitor.HasReturn) { lambda.ReturnType = new TypeReference("System.Void", true); } } ReplaceCurrentNode(lambda); return(null); }
private Ust GetAnonymousMethod(LambdaExpressionSyntax node, ParameterDeclaration[] parameters) { var idNameSyntax = node.Body as IdentifierNameSyntax; Statement bodyStatement; if (idNameSyntax != null) { bodyStatement = new ReturnStatement((Expression)VisitIdentifierName(idNameSyntax), node.Body.GetTextSpan()); } else { var visited = base.Visit(node.Body); if (visited is Statement) { bodyStatement = (Statement)visited; } else { bodyStatement = new ExpressionStatement((Expression)visited, node.Body.GetTextSpan()); } } var body = new BlockStatement(new[] { bodyStatement }, node.Body.GetTextSpan()); var result = new AnonymousMethodExpression(parameters, body, node.GetTextSpan()); return(result); }
/// <returns><see cref="AnonymousMethodExpression"/></returns> public UstNode VisitFunctionExpression([NotNull] ECMAScriptParser.FunctionExpressionContext context) { var body = (BlockStatement)Visit(context.functionBody()); var result = new AnonymousMethodExpression(new ParameterDeclaration[0], body, context.GetTextSpan(), FileNode); return(result); }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { VisitBody("Delegate", anonymousMethodExpression.DelegateToken, anonymousMethodExpression.Body, null, null); base.VisitAnonymousMethodExpression(anonymousMethodExpression); }
public virtual void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { if (ThrowException) { throw (Exception)CreateException(anonymousMethodExpression); } }
public void AnonymousMethodWithoutParameterList() { AnonymousMethodExpression ame = Parse("delegate {}"); Assert.AreEqual(0, ame.Parameters.Count); Assert.AreEqual(0, ame.Body.Children.Count); }
public override void VisitMethodDeclaration(MethodDeclaration methodDeclaration) { Guard.AgainstNullArgument("methodDeclaration", methodDeclaration); IEnumerable<ParameterDeclaration> parameters = methodDeclaration .GetChildrenByRole(Roles.Parameter) .Select(x => (ParameterDeclaration)x.Clone()); var isVoid = false; var isAsync = methodDeclaration.Modifiers.HasFlag(Modifiers.Async); AstType returnType = methodDeclaration.GetChildByRole(Roles.Type).Clone(); var type = returnType as PrimitiveType; if (type != null) { isVoid = string.Compare( type.Keyword, "void", StringComparison.OrdinalIgnoreCase) == 0; } var methodType = new SimpleType(Identifier.Create(isVoid ? "Action" : "Func")); IEnumerable<AstType> types = parameters.Select( x => x.GetChildByRole(Roles.Type).Clone()); methodType .TypeArguments .AddRange(types); if (!isVoid) { methodType.TypeArguments.Add(returnType); } var methodName = GetIdentifierName(methodDeclaration); var methodBody = methodDeclaration .GetChildrenByRole(Roles.Body) .FirstOrDefault(); if (methodBody == null) { throw new NullReferenceException(string.Format("Method '{0}' has no method body", methodName)); } methodBody = (BlockStatement)methodBody.Clone(); var prototype = new VariableDeclarationStatement { Type = methodType }; prototype.Variables.Add(new VariableInitializer(methodName)); var anonymousMethod = new AnonymousMethodExpression(methodBody, parameters) { IsAsync = isAsync }; var expression = new ExpressionStatement { Expression = new AssignmentExpression( new IdentifierExpression(methodName), anonymousMethod) }; _methods.Add(new MethodVisitorResult { MethodDefinition = methodDeclaration, MethodPrototype = prototype, MethodExpression = expression }); }
public virtual void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { if (this.ThrowException) { throw (System.Exception) this.CreateException(anonymousMethodExpression); } }
protected override CodeAction GetAction(RefactoringContext context, LambdaExpression node) { if (context.Location < node.StartLocation || context.Location >= node.Body.StartLocation) { return(null); } var lambdaResolveResult = context.Resolve(node) as LambdaResolveResult; if (lambdaResolveResult == null) { return(null); } return(new CodeAction(context.TranslateString("Convert to anonymous delegate"), script => { BlockStatement newBody; if (node.Body is BlockStatement) { newBody = (BlockStatement)node.Body.Clone(); } else { newBody = new BlockStatement { Statements = { new ExpressionStatement((Expression)node.Body.Clone()) } }; } var method = new AnonymousMethodExpression(newBody, GetParameters(lambdaResolveResult.Parameters, context)); method.HasParameterList = true; script.Replace(node, method); })); }
public virtual void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { if (this.ThrowException) { throw (Exception)this.CreateException(anonymousMethodExpression); } }
void InsertAnonymousMethods(int insertPos, AstNode node, ControlFlowGraphBuilder cfgBuilder, CancellationToken cancellationToken) { // Ignore any statements, as those have their own ControlFlowNode and get handled separately if (node is Statement) { return; } AnonymousMethodExpression ame = node as AnonymousMethodExpression; if (ame != null) { allNodes.InsertRange(insertPos, cfgBuilder.BuildControlFlowGraph(ame.Body, resolver, cancellationToken).Cast <DefiniteAssignmentNode>()); return; } LambdaExpression lambda = node as LambdaExpression; if (lambda != null && lambda.Body is Statement) { allNodes.InsertRange(insertPos, cfgBuilder.BuildControlFlowGraph((Statement)lambda.Body, resolver, cancellationToken).Cast <DefiniteAssignmentNode>()); return; } // Descend into child expressions // Iterate backwards so that anonymous methods are inserted in the correct order for (AstNode child = node.LastChild; child != null; child = child.PrevSibling) { InsertAnonymousMethods(insertPos, child, cfgBuilder, cancellationToken); } }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression a) { // Replace properties. a.Body.AcceptVisitor(new FindPropertiesVisitor { Algorithm = Algorithm, ParameterContextName = ParameterContextName }); }
public override object VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression, object data) { foreach (ParameterDeclarationExpression p in anonymousMethodExpression.Parameters) { AddVariable(p.TypeReference, p.ParameterName, anonymousMethodExpression.StartLocation, anonymousMethodExpression.EndLocation, false); } return(base.VisitAnonymousMethodExpression(anonymousMethodExpression, data)); }
public void AnonymousMethodWithoutParameterList() { AnonymousMethodExpression ame = Parse("delegate {}"); Assert.AreEqual(0, ame.Parameters.Count()); Assert.AreEqual(0, ame.Body.Statements.Count()); Assert.IsFalse(ame.HasParameterList); }
public UnifiedElement VisitAnonymousMethodExpression( AnonymousMethodExpression expr, object data) { var parameters = expr.Parameters.AcceptVisitorAsParams(this, data); var body = expr.Body.TryAcceptForExpression(this).ToBlock(); return(UnifiedLambda.Create(parameters: parameters, body: body)); }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { bool old = skip; skip = AnonymousMethodMayReturnVoid(ctx, anonymousMethodExpression); base.VisitAnonymousMethodExpression(anonymousMethodExpression); skip = old; }
public void AnonymousMethodAfterCast() { CastExpression c = ParseUtilCSharp.ParseExpression <CastExpression>("(ThreadStart)delegate {}"); AnonymousMethodExpression ame = (AnonymousMethodExpression)c.Expression; Assert.AreEqual(0, ame.Parameters.Count()); Assert.AreEqual(0, ame.Body.Statements.Count()); }
public object VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression, object data) { B.BlockExpression cbe = new B.BlockExpression(GetLexicalInfo(anonymousMethodExpression)); cbe.EndSourceLocation = GetLocation(anonymousMethodExpression.EndLocation); cbe.Body = ConvertBlock(anonymousMethodExpression.Body); ConvertParameters(anonymousMethodExpression.Parameters, cbe.Parameters); return(cbe); }
public void EmptyAnonymousMethod() { AnonymousMethodExpression ame = Parse("delegate() {}"); Assert.AreEqual(0, ame.Parameters.Count()); Assert.AreEqual(0, ame.Body.Statements.Count()); Assert.IsTrue(ame.HasParameterList); }
public override IEnumerable <CodeAction> GetActions(RefactoringContext context) { Expression node = context.GetNode <IdentifierExpression>(); if (node == null) { var mr = context.GetNode <MemberReferenceExpression>(); if (mr == null || !mr.MemberNameToken.IsInside(context.Location)) { yield break; } node = mr; } if (node == null) { yield break; } var rr = context.Resolve(node) as MethodGroupResolveResult; if (rr == null || rr.IsError) { yield break; } var type = TypeGuessing.GetValidTypes(context.Resolver, node).FirstOrDefault(t => t.Kind == TypeKind.Delegate); if (type == null) { yield break; } var invocationMethod = type.GetDelegateInvokeMethod(); if (invocationMethod == null) { yield break; } yield return(new CodeAction( context.TranslateString("Convert to anonymous method"), script => { var expr = new InvocationExpression(node.Clone(), invocationMethod.Parameters.Select(p => new IdentifierExpression(context.GetNameProposal(p.Name)))); var stmt = invocationMethod.ReturnType.IsKnownType(KnownTypeCode.Void) ? (Statement)expr : new ReturnStatement(expr); var anonymousMethod = new AnonymousMethodExpression { Body = new BlockStatement { stmt } }; foreach (var p in invocationMethod.Parameters) { var decl = new ParameterDeclaration(context.CreateShortType(p.Type), context.GetNameProposal(p.Name)); anonymousMethod.Parameters.Add(decl); } script.Replace(node, anonymousMethod); }, node )); }
public void SimpleAnonymousMethod() { AnonymousMethodExpression ame = Parse("delegate(int a, int b) { return a + b; }"); Assert.IsTrue(ame.HasParameterList); Assert.AreEqual(2, ame.Parameters.Count()); Assert.AreEqual(1, ame.Body.Statements.Count()); Assert.IsTrue(ame.Body.Statements.First() is ReturnStatement); }
public void AsyncAnonymousMethod() { AnonymousMethodExpression ame = Parse("async delegate {}"); Assert.AreEqual(0, ame.Parameters.Count()); Assert.AreEqual(0, ame.Body.Statements.Count()); Assert.IsTrue(ame.IsAsync); Assert.IsFalse(ame.HasParameterList); }
public override object VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression, object data) { MethodDeclaration method = new MethodDeclaration(GetAnonymousMethodName(), Modifiers.Private, new TypeReference("System.Void"), anonymousMethodExpression.Parameters, null); method.Body = anonymousMethodExpression.Body; currentType.Children.Add(method); ReplaceCurrentNode(new AddressOfExpression(new IdentifierExpression(method.Name))); return(null); }
public JNode VisitAnonymousMethodExpression(AnonymousMethodExpression node) { return(Visit(node.Resolve())); //var func = new JsFunction(); //func.Parameters = node.Parameters.Select(t => t.Name).ToList(); //var body = Visit(node.Body); //func.Block = (JsBlock)body; //return CreateJsDelegateIfNeeded(func, node, true); }
public void SimpleAnonymousMethod() { AnonymousMethodExpression ame = Parse("delegate(int a, int b) { return a + b; }"); Assert.AreEqual(2, ame.Parameters.Count); // blocks can't be added without compilation unit -> anonymous method body // is always empty when using ParseExpression //Assert.AreEqual(1, ame.Body.Children.Count); //Assert.IsTrue(ame.Body.Children[0] is ReturnStatement); }
public void AnonymousMethodAfterCast() { CastExpression c = ParseUtilCSharp.ParseExpression <CastExpression>("(ThreadStart)delegate {}"); Assert.AreEqual("ThreadStart", c.CastTo.Type); AnonymousMethodExpression ame = (AnonymousMethodExpression)c.Expression; Assert.AreEqual(0, ame.Parameters.Count); Assert.AreEqual(0, ame.Body.Children.Count); }
public virtual object VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression, object data) { Debug.Assert((anonymousMethodExpression != null)); Debug.Assert((anonymousMethodExpression.Parameters != null)); Debug.Assert((anonymousMethodExpression.Body != null)); foreach (ParameterDeclarationExpression o in anonymousMethodExpression.Parameters) { Debug.Assert(o != null); o.AcceptVisitor(this, data); } return anonymousMethodExpression.Body.AcceptVisitor(this, data); }
public override object VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression, object data) { AnonymousMethodReturnType amrt = new AnonymousMethodReturnType(resolver.CompilationUnit); foreach (ParameterDeclarationExpression param in anonymousMethodExpression.Parameters) { amrt.MethodParameters.Add(NRefactoryASTConvertVisitor.CreateParameter(param, resolver.CallingMember as IMethod, resolver.CallingClass, resolver.CompilationUnit)); } return(amrt); }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { var capturedVariables = LambdaBlock.GetCapturedLoopVariables(Emitter, anonymousMethodExpression, anonymousMethodExpression.Parameters, true); if (capturedVariables != null) { DirectionVariables.AddRange(capturedVariables); } base.VisitAnonymousMethodExpression(anonymousMethodExpression); }
public override Ust VisitAnonymousMethodExpression(AnonymousMethodExpressionSyntax node) { var parameters = node.ParameterList == null ? new ParameterDeclaration[0] : node.ParameterList.Parameters.Select(p => (ParameterDeclaration)VisitAndReturnNullIfError(p)) .ToArray(); var body = (BlockStatement)VisitBlock(node.Block); var result = new AnonymousMethodExpression(parameters, body, node.GetTextSpan()); return(result); }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { if (!anonymousMethodExpression.Body.IsNull) { if (anonymousMethodExpression.Body.LBraceToken.GetNextNode(NoWhitespacePredicate) != anonymousMethodExpression.Body.RBraceToken) { FixOpenBrace(policy.AnonymousMethodBraceStyle, anonymousMethodExpression.Body.LBraceToken); VisitBlockWithoutFixingBraces(anonymousMethodExpression.Body, policy.IndentBlocks); FixClosingBrace(policy.AnonymousMethodBraceStyle, anonymousMethodExpression.Body.RBraceToken); } else { VisitBlockWithoutFixingBraces(anonymousMethodExpression.Body, policy.IndentBlocks); } return; } base.VisitAnonymousMethodExpression(anonymousMethodExpression); }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression lambdaExpression) { FormatArguments(lambdaExpression); if (!lambdaExpression.Body.IsNull) { var old = curIndent; this.curIndent = curIndent.GetIndentWithoutSpace (); FixOpenBrace(policy.AnonymousMethodBraceStyle, lambdaExpression.Body.LBraceToken); VisitBlockWithoutFixingBraces(lambdaExpression.Body, policy.IndentBlocks); FixClosingBrace(policy.AnonymousMethodBraceStyle, lambdaExpression.Body.RBraceToken); curIndent = old; } }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { AstNode oldMethod = _currentMethod; bool oldIsInsideLoop = _isInsideLoop; try { _currentMethod = anonymousMethodExpression; _isInsideLoop = false; foreach (var p in anonymousMethodExpression.Parameters) AddVariable(p, p.Name); base.VisitAnonymousMethodExpression(anonymousMethodExpression); } finally { _currentMethod = oldMethod; _isInsideLoop = oldIsInsideLoop; } }
public virtual object VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression, object data) { Debug.Assert((anonymousMethodExpression != null)); Debug.Assert((anonymousMethodExpression.Parameters != null)); Debug.Assert((anonymousMethodExpression.Body != null)); for (int i = 0; i < anonymousMethodExpression.Parameters.Count; i++) { ParameterDeclarationExpression o = anonymousMethodExpression.Parameters[i]; Debug.Assert(o != null); nodeStack.Push(o); o.AcceptVisitor(this, data); o = (ParameterDeclarationExpression)nodeStack.Pop(); if (o == null) anonymousMethodExpression.Parameters.RemoveAt(i--); else anonymousMethodExpression.Parameters[i] = o; } nodeStack.Push(anonymousMethodExpression.Body); anonymousMethodExpression.Body.AcceptVisitor(this, data); anonymousMethodExpression.Body = ((BlockStatement)(nodeStack.Pop())); return null; }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { statements.Add (anonymousMethodExpression.Body); base.VisitAnonymousMethodExpression (anonymousMethodExpression); }
public override void VisitAnonymousMethodExpression (AnonymousMethodExpression anonymousMethodExpression) { StatementIssueCollector.Collect (this, anonymousMethodExpression.Body); base.VisitAnonymousMethodExpression (anonymousMethodExpression); }
public void VisitAnonymousMethodExpression(AnonymousMethodExpression expression) { Formatter.StartNode(expression); Formatter.WriteKeyword("delegate"); if (expression.Parameters.Count > 0) { Formatter.WriteToken("("); WriteCommaSeparatedNodes(expression.Parameters); Formatter.WriteToken(")"); } expression.Body.AcceptVisitor(this); Formatter.EndNode(); }
public AsyncBlock(IEmitter emitter, AnonymousMethodExpression anonymousMethodExpression) : base(emitter, anonymousMethodExpression) { this.Emitter = emitter; this.AnonymousMethodExpression = anonymousMethodExpression; }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { new LambdaBlock(this, anonymousMethodExpression).Emit(); }
// IMPORTANT NOTE: // The grammar consists of a few LALR(1) conflicts. These issues are, however, correctly handled, due to the fact that the grammar // is defined in a specific order making the already added parser actions have precedence over the other. // // Known conflicts that are correctly handled: // // - ELSE: Shift/Reduce conflict Dangling ELSE problem. Lots of articles are around on the internet. // The shift action is taken here. // // - CLOSE_PARENS: Shift/Reduce conflict. This is due to the fact that the explicit cast expression is like the parenthesized // expression. The shift action is taken here. // // - STAR: Reduce/Reduce conflict, between VariableType -> TypeNameExpression and PrimaryExpression -> TypeNameExpression, // due to the fact variable types can have '*', and look therefore like a binary operator expression. // The first reduce action is taken here. public CSharpGrammar() { // Please let me know if there is a better way of tidying this :s TokenMapping.Add((int)ERROR, Error); #region Definitions to use later var statementList = new GrammarDefinition("StatementList"); var statementListOptional = new GrammarDefinition("StatementListOptional", rule: null | statementList); var blockStatement = new GrammarDefinition("BlockStatement"); var variableDeclarator = new GrammarDefinition("VariableDeclarator"); var variableDeclaratorList = new GrammarDefinition("VariableDeclaratorList"); variableDeclaratorList.Rule = variableDeclarator | variableDeclaratorList + ToElement(COMMA) + variableDeclarator; var variableDeclaration = new GrammarDefinition("VariableDeclaration"); var variableInitializer = new GrammarDefinition("VariableInitializer"); var arrayInitializer = new GrammarDefinition("ArrayInitializer"); var arrayInitializerOptional = new GrammarDefinition("ArrayInitializerOptional", rule: null | arrayInitializer); var identifierInsideBody = new GrammarDefinition("IdentifierInsideBody", rule: ToElement(IDENTIFIER), createNode: node => ToIdentifier(node.Children[0].Result)); var identifierInsideBodyOptional = new GrammarDefinition("IdentifierInsideBodyOptional", rule: null | identifierInsideBody); variableDeclarator.Rule = identifierInsideBody | identifierInsideBody + ToElement(EQUALS) + variableInitializer; variableDeclarator.ComputeResult = node => { var result = new VariableDeclarator((Identifier) node.Children[0].Result); if (node.Children.Count > 1) { result.OperatorToken = (AstToken) node.Children[1].Result; result.Value = (Expression) node.Children[2].Result; } return result; }; var typeReference = new GrammarDefinition("TypeReference"); var identifierExpression = new GrammarDefinition("IdentifierExpression", rule: identifierInsideBody, createNode: node => new IdentifierExpression((Identifier) node.Children[0].Result)); var usingDirectiveListOptional = new GrammarDefinition("UsingDirectiveListOptional"); #endregion #region Type References var namespaceOrTypeExpression = new GrammarDefinition("NamespaceOrTypeExpression"); namespaceOrTypeExpression.Rule = identifierExpression | namespaceOrTypeExpression + ToElement(DOT) + ToElement(IDENTIFIER); namespaceOrTypeExpression.ComputeResult = node => { if (node.Children.Count == 1) return ToTypeReference((IConvertibleToType) node.Children[0].Result); var result = new MemberTypeReference(); result.Target = (TypeReference) node.Children[0].Result; result.AddChild(AstNodeTitles.Accessor, node.Children[1].Result); result.Identifier = ToIdentifier(node.Children[2].Result); return result; }; ComputeResultDelegate createPrimitiveTypeExpression = node => { if (node.Children[0].Result is PrimitiveTypeReference) return node.Children[0].Result; return new PrimitiveTypeReference { Identifier = ToIdentifier(node.Children[0].Result), PrimitiveType = CSharpLanguage.PrimitiveTypeFromString(((AstToken) node.Children[0].Result).Value) }; }; var integralType = new GrammarDefinition("IntegralType", rule: ToElement(SBYTE) | ToElement(BYTE) | ToElement(SHORT) | ToElement(USHORT) | ToElement(INT) | ToElement(UINT) | ToElement(LONG) | ToElement(ULONG) | ToElement(CHAR), createNode: createPrimitiveTypeExpression); var primitiveType = new GrammarDefinition("PrimitiveTypeExpression", rule: ToElement(OBJECT) | ToElement(STRING) | ToElement(BOOL) | ToElement(DECIMAL) | ToElement(FLOAT) | ToElement(DOUBLE) | ToElement(VOID) | integralType, createNode: createPrimitiveTypeExpression); var dimensionSeparators = new GrammarDefinition("DimensionSeparators"); dimensionSeparators.Rule = ToElement(COMMA) | dimensionSeparators + ToElement(COMMA); var rankSpecifier = new GrammarDefinition("RankSpecifier", rule: ToElement(OPEN_BRACKET) + ToElement(CLOSE_BRACKET) | ToElement(OPEN_BRACKET) + dimensionSeparators + ToElement(CLOSE_BRACKET), createNode: node => { var result = new ArrayTypeRankSpecifier(); result.LeftBracket = (AstToken) node.Children[0].Result; if (node.Children.Count == 3) { foreach (var dimensionSeparator in node.Children[1].GetAllNodesFromListDefinition() .Select(x => x.Result)) { result.Dimensions++; result.AddChild(AstNodeTitles.ElementSeparator, dimensionSeparator); } } result.RightBracket = (AstToken) node.Children[node.Children.Count - 1].Result; return result; }); var arrayType = new GrammarDefinition("ArrayType", rule: typeReference + rankSpecifier, createNode: node => new ArrayTypeReference() { BaseType = (TypeReference) node.Children[0].Result, RankSpecifier = (ArrayTypeRankSpecifier) node.Children[1].Result }); var pointerType = new GrammarDefinition("PointerType", rule: typeReference + ToElement(STAR), createNode: node => new PointerTypeReference() { BaseType = (TypeReference) node.Children[0].Result, PointerToken = (AstToken) node.Children[1].Result }); var typeExpression = new GrammarDefinition("TypeExpression", rule: namespaceOrTypeExpression | primitiveType); typeReference.Rule = typeExpression | arrayType | pointerType ; #endregion #region Expressions ComputeResultDelegate createBinaryOperatorExpression = node => { if (node.Children.Count == 1) return node.Children[0].Result; var result = new BinaryOperatorExpression(); result.Left = (Expression) node.Children[0].Result; var operatorToken = (AstToken) (node.Children[1].Result ?? node.Children[1].Children[0].Result); result.Operator = CSharpLanguage.BinaryOperatorFromString(operatorToken.Value); result.OperatorToken = (AstToken) operatorToken; result.Right = (Expression) node.Children[2].Result; return result; }; var expression = new GrammarDefinition("Expression"); var expressionOptional = new GrammarDefinition("ExpressionOptional", rule: null | expression); var primaryExpression = new GrammarDefinition("PrimaryExpression"); var primitiveExpression = new GrammarDefinition("PrimitiveExpression", rule: ToElement(LITERAL) | ToElement(TRUE) | ToElement(FALSE) | ToElement(NULL), createNode: node => { object interpretedValue; node.Children[0].Result.UserData.TryGetValue("InterpretedValue", out interpretedValue); var result = new PrimitiveExpression(interpretedValue, ((AstToken) node.Children[0].Result).Value, node.Children[0].Range); return result; }); var parenthesizedExpression = new GrammarDefinition("ParenthesizedExpression", rule: ToElement(OPEN_PARENS) + expression + ToElement(CLOSE_PARENS) | ToElement(OPEN_PARENS) + Error + ToElement(CLOSE_PARENS), createNode: node => new ParenthesizedExpression { LeftParenthese = (AstToken) node.Children[0].Result, Expression = (Expression) node.Children[1].Result, RightParenthese = (AstToken) node.Children[2].Result, }); var memberAccessorOperator = new GrammarDefinition("MemberAccessorOperator", rule: ToElement(DOT) | ToElement(OP_PTR) | ToElement(INTERR_OPERATOR)); var memberReferenceExpression = new GrammarDefinition("MemberReferenceExpression", rule: primaryExpression + memberAccessorOperator + identifierInsideBody | primaryExpression + memberAccessorOperator + Error, createNode: node => new MemberReferenceExpression { Target = (Expression) ((IConvertibleToExpression) node.Children[0].Result).ToExpression().Remove(), Accessor = CSharpLanguage.AccessorFromString(((AstToken) node.Children[1].Children[0].Result).Value), AccessorToken = (AstToken) node.Children[1].Children[0].Result, Identifier = (Identifier) node.Children[2].Result }); var argument = new GrammarDefinition("Argument", rule: expression | ToElement(REF) + expression | ToElement(OUT) + expression, createNode: node => { if (node.Children.Count > 1) { return new DirectionExpression() { DirectionToken = (AstToken) node.Children[0].Result, Direction = CSharpLanguage.DirectionFromString(((AstToken) node.Children[0].Result).Value), Expression = (Expression) node.Children[1].Result }; } return node.Children[0].Result; }); var argumentList = new GrammarDefinition("ArgumentList"); argumentList.Rule = argument | argumentList + ToElement(COMMA) + argument; var argumentListOptional = new GrammarDefinition("ArgumentListOptional", rule: null | argumentList); var invocationExpression = new GrammarDefinition("InvocationExpression", rule: primaryExpression + ToElement(OPEN_PARENS) + argumentListOptional + ToElement(CLOSE_PARENS), createNode: node => { var result = new InvocationExpression() { Target = (Expression) node.Children[0].Result, LeftParenthese = (AstToken) node.Children[1].Result, }; if (node.Children[2].HasChildren) { foreach (var subNode in node.Children[2].Children[0].GetAllListAstNodes()) { if (subNode is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, subNode); else result.Arguments.Add((Expression) subNode); } } result.RightParenthese = (AstToken) node.Children[3].Result; return result; }); var indexerExpression = new GrammarDefinition("IndexerExpression", rule: primaryExpression + ToElement(OPEN_BRACKET_EXPR) + argumentList + ToElement(CLOSE_BRACKET), createNode: node => { var result = new IndexerExpression() { Target = (Expression) node.Children[0].Result, LeftBracket = (AstToken) node.Children[1].Result, }; foreach (var subNode in node.Children[2].GetAllListAstNodes()) { if (subNode is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, subNode); else result.Indices.Add((Expression) subNode); } result.RightBracket = (AstToken) node.Children[3].Result; return result; }); var createObjectExpression = new GrammarDefinition("CreateObjectExpression", rule: ToElement(NEW) + typeReference + ToElement(OPEN_PARENS) + argumentListOptional + ToElement(CLOSE_PARENS) + arrayInitializerOptional | ToElement(NEW) + namespaceOrTypeExpression + arrayInitializer, createNode: node => { var result = new CreateObjectExpression(); result.NewKeyword = (AstToken) node.Children[0].Result; result.Type = (TypeReference) node.Children[1].Result; if (node.Children.Count == 6) { result.LeftParenthese = (AstToken) node.Children[2].Result; if (node.Children[3].HasChildren) { foreach (var subNode in node.Children[3].Children[0].GetAllListAstNodes()) { if (subNode is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, subNode); else result.Arguments.Add((Expression) subNode); } } result.RightParenthese = (AstToken) node.Children[4].Result; } var initializerNode = node.Children[node.Children.Count - 1]; if (initializerNode.HasChildren) result.Initializer = (ArrayInitializer) initializerNode.Result; return result; }); var createArrayExpression = new GrammarDefinition("CreateArrayExpression", rule: ToElement(NEW) + rankSpecifier + arrayInitializer | ToElement(NEW) + typeReference + rankSpecifier + arrayInitializer | ToElement(NEW) + typeReference + ToElement(OPEN_BRACKET_EXPR) + argumentList + ToElement(CLOSE_BRACKET) + arrayInitializerOptional , createNode: node => { var result = new CreateArrayExpression(); result.NewKeyword = (AstToken) node.Children[0].Result; switch (node.Children.Count) { case 3: { var rankSpecifierNode = (ArrayTypeRankSpecifier) node.Children[1].Result; result.LeftBracket = (AstToken) rankSpecifierNode.LeftBracket.Remove(); result.RightBracket = (AstToken) rankSpecifierNode.RightBracket.Remove(); break; } case 4: { result.Type = (TypeReference) node.Children[1].Result; var rankSpecifierNode = (ArrayTypeRankSpecifier) node.Children[2].Result; result.LeftBracket = (AstToken) rankSpecifierNode.LeftBracket.Remove(); result.RightBracket = (AstToken) rankSpecifierNode.RightBracket.Remove(); break; } case 6: { result.Type = (TypeReference) node.Children[1].Result; result.LeftBracket = (AstToken) node.Children[2].Result; if (node.Children[3].HasChildren) { foreach (var subNode in node.Children[3].Children[0].GetAllListAstNodes()) { if (subNode is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, subNode); else result.Arguments.Add((Expression) subNode); } } result.RightBracket = (AstToken) node.Children[4].Result; break; } } var initializerNode = node.Children[node.Children.Count - 1]; if (initializerNode.HasChildren) result.Initializer = (ArrayInitializer) initializerNode.Result; return result; }); var primitiveTypeExpression = new GrammarDefinition("PrimitiveTypeExpression", rule: primitiveType, createNode: node => ((IConvertibleToExpression) node.Children[0].Result).ToExpression()); var typeNameExpression = new GrammarDefinition("TypeNameExpression", rule: identifierExpression | memberReferenceExpression | primitiveTypeExpression); var thisExpression = new GrammarDefinition("ThisExpression", rule: ToElement(THIS), createNode: node => new ThisReferenceExpression() { ThisKeywordToken = (AstToken) node.Children[0].Result, }); var baseExpression = new GrammarDefinition("BaseExpression", rule: ToElement(BASE), createNode: node => new BaseReferenceExpression() { BaseKeywordToken = (AstToken) node.Children[0].Result, }); var typeofExpression = new GrammarDefinition("TypeOfExpression", rule: ToElement(TYPEOF) + ToElement(OPEN_PARENS) + typeReference + ToElement(CLOSE_PARENS), createNode: node => new GetTypeExpression() { GetTypeKeywordToken = (AstToken) node.Children[0].Result, LeftParenthese = (AstToken) node.Children[1].Result, TargetType = (TypeReference) node.Children[2].Result, RightParenthese = (AstToken) node.Children[3].Result, }); var defaultExpression = new GrammarDefinition("DefaultExpression", rule: ToElement(DEFAULT) + ToElement(OPEN_PARENS) + typeReference + ToElement(CLOSE_PARENS), createNode: node => new DefaultExpression() { KeywordToken = (AstToken) node.Children[0].Result, LeftParenthese = (AstToken) node.Children[1].Result, TargetType = (TypeReference) node.Children[2].Result, RightParenthese = (AstToken) node.Children[3].Result, }); var sizeofExpression = new GrammarDefinition("SizeOfExpression", rule: ToElement(SIZEOF) + ToElement(OPEN_PARENS) + typeReference + ToElement(CLOSE_PARENS), createNode: node => new SizeOfExpression() { SizeofKeyword = (AstToken) node.Children[0].Result, LeftParenthese = (AstToken) node.Children[1].Result, TargetType = (TypeReference) node.Children[2].Result, RightParenthese = (AstToken) node.Children[3].Result, }); var checkedExpression = new GrammarDefinition("CheckedExpression", rule: ToElement(CHECKED) + ToElement(OPEN_PARENS) + expression + ToElement(CLOSE_PARENS), createNode: node => new CheckedExpression() { CheckedKeyword = (AstToken) node.Children[0].Result, LeftParenthese = (AstToken) node.Children[1].Result, TargetExpression = (Expression) node.Children[2].Result, RightParenthese = (AstToken) node.Children[3].Result, }); var uncheckedExpression = new GrammarDefinition("UncheckedExpression", rule: ToElement(UNCHECKED) + ToElement(OPEN_PARENS) + expression + ToElement(CLOSE_PARENS), createNode: node => new UncheckedExpression() { UncheckedKeyword = (AstToken) node.Children[0].Result, LeftParenthese = (AstToken) node.Children[1].Result, TargetExpression = (Expression) node.Children[2].Result, RightParenthese = (AstToken) node.Children[3].Result, }); var stackAllocExpression = new GrammarDefinition("StackAllocExpression", rule: ToElement(STACKALLOC) + typeReference + ToElement(OPEN_BRACKET_EXPR) + expression + ToElement(CLOSE_BRACKET), createNode: node => new StackAllocExpression() { StackAllocKeyword = (AstToken) node.Children[0].Result, Type = (TypeReference) node.Children[1].Result, LeftBracket = (AstToken) node.Children[2].Result, Counter = (Expression) node.Children[3].Result, RightBracket = (AstToken) node.Children[4].Result, }); var explicitAnonymousMethodParameter = new GrammarDefinition("ExplicitAnonymousMethodParameter", rule: typeReference + ToElement(IDENTIFIER), createNode: node => new ParameterDeclaration { ParameterType = (TypeReference)node.Children[0].Result, Declarator = new VariableDeclarator(ToIdentifier(node.Children[1].Result)) }); var explicitAnonymousMethodParameterList = new GrammarDefinition("ExplicitAnonymousMethodParameterList"); explicitAnonymousMethodParameterList.Rule = explicitAnonymousMethodParameter | explicitAnonymousMethodParameterList + ToElement(COMMA) + explicitAnonymousMethodParameter; var explicitAnonymousMethodParameterListOptional = new GrammarDefinition("ExplicitAnonymousMethodParameterListOptional", rule: null | explicitAnonymousMethodParameterList); var explicitAnonymousMethodSignature = new GrammarDefinition("ExplicitAnonymousMethodSignature", rule: ToElement(OPEN_PARENS) + explicitAnonymousMethodParameterListOptional + ToElement(CLOSE_PARENS)); var explicitAnonymousMethodSignatureOptional = new GrammarDefinition("ExplicitAnonymousMethodSignatureOptional", rule: null | explicitAnonymousMethodSignature); var anonymousMethodExpression = new GrammarDefinition("AnonymousMethodExpression", rule: ToElement(DELEGATE) + explicitAnonymousMethodSignatureOptional + blockStatement, createNode: node => { var result = new AnonymousMethodExpression(); result.DelegateKeyword = (AstToken) node.Children[0].Result; if (node.Children[1].HasChildren) { var signature = node.Children[1].Children[0]; result.LeftParenthese = (AstToken) signature.Children[0].Result; if (signature.Children[1].HasChildren) { foreach (var child in signature.Children[1].Children[0].GetAllListAstNodes()) { if (child is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, child); else result.Parameters.Add((ParameterDeclaration) child); } } result.RightParenthese = (AstToken)signature.Children[2].Result; } result.Body = (BlockStatement) node.Children[2].Result; return result; }); var implicitAnonymousMethodParameter = new GrammarDefinition("ImplicitAnonymousMethodParameter", rule: ToElement(IDENTIFIER), createNode: node => new ParameterDeclaration { Declarator = new VariableDeclarator(ToIdentifier(node.Children[0].Result)) }); var implicitAnonymousMethodParameterList = new GrammarDefinition("ImplicitAnonymousMethodParameterList"); implicitAnonymousMethodParameterList.Rule = implicitAnonymousMethodParameter | implicitAnonymousMethodParameterList + ToElement(COMMA) + implicitAnonymousMethodParameter; var implicitAnonymousMethodParameterListOptional = new GrammarDefinition("ImplicitAnonymousMethodParameterListOptional", rule: null | implicitAnonymousMethodParameterList); var implicitAnonymousMethodSignature = new GrammarDefinition("implicitAnonymousMethodSignature", rule: implicitAnonymousMethodParameter | ToElement(OPEN_PARENS_LAMBDA) + implicitAnonymousMethodParameterList + ToElement(CLOSE_PARENS)); var anonymousMethodSignature = new GrammarDefinition("AnonymousMethodSignature", rule: implicitAnonymousMethodSignature); var anonymousFunctionBody = new GrammarDefinition("AnonymousFunctionBody", rule: expression | blockStatement); var lambdaExpression = new GrammarDefinition("LambdaExpression", rule: anonymousMethodSignature + ToElement(ARROW) + anonymousFunctionBody, createNode: node => { var result = new LambdaExpression(); result.Arrow = (AstToken)node.Children[1].Result; result.Body = node.Children[2].Result; return result; }); primaryExpression.Rule = typeNameExpression | primitiveExpression | parenthesizedExpression | invocationExpression | indexerExpression | thisExpression | baseExpression | createObjectExpression | createArrayExpression | typeofExpression | defaultExpression | sizeofExpression | checkedExpression | uncheckedExpression | stackAllocExpression | anonymousMethodExpression ; var preFixUnaryOperator = new GrammarDefinition("PreFixUnaryOperator", rule: ToElement(PLUS) | ToElement(MINUS) | ToElement(STAR) | ToElement(BANG) | ToElement(OP_INC) | ToElement(OP_DEC) | ToElement(BITWISE_AND) | ToElement(TILDE) | ToElement(AWAIT)); var postFixUnaryOperator = new GrammarDefinition("PostFixUnaryOperator", rule: ToElement(OP_INC) | ToElement(OP_DEC)); var castExpression = new GrammarDefinition("CastExpression"); var unaryOperatorExpression = new GrammarDefinition("UnaryOperatorExpression", rule: primaryExpression | castExpression | (preFixUnaryOperator + primaryExpression) | (primaryExpression + postFixUnaryOperator), createNode: node => { if (node.Children.Count == 1) return node.Children[0].Result; var result = new UnaryOperatorExpression(); var isPrefix = node.Children[0].GrammarElement == preFixUnaryOperator; if (isPrefix) { var operatorToken = ((AstToken) node.Children[0].Children[0].Result); result.Operator = CSharpLanguage.UnaryOperatorFromString(operatorToken.Value); result.OperatorToken = operatorToken; } result.Expression = (Expression) node.Children[isPrefix ? 1 : 0].Result; if (!isPrefix) { var operatorToken = (AstToken) node.Children[1].Children[0].Result; result.Operator = CSharpLanguage.UnaryOperatorFromString(operatorToken.Value, false); result.OperatorToken = operatorToken; } return result; }); castExpression.Rule = ToElement(OPEN_PARENS) + typeNameExpression + ToElement(CLOSE_PARENS) + unaryOperatorExpression; castExpression.ComputeResult = node => new ExplicitCastExpression { LeftParenthese = (AstToken) node.Children[0].Result, TargetType = ToTypeReference((IConvertibleToType) node.Children[1].Result), RightParenthese = (AstToken) node.Children[2].Result, TargetExpression = (Expression) node.Children[3].Result }; var multiplicativeOperator = new GrammarDefinition("MultiplicativeOperator", rule: ToElement(STAR) | ToElement(DIV) | ToElement(PERCENT)); var multiplicativeExpression = new GrammarDefinition("MultiplicativeExpression"); multiplicativeExpression.Rule = unaryOperatorExpression | multiplicativeExpression + multiplicativeOperator + unaryOperatorExpression; multiplicativeExpression.ComputeResult = createBinaryOperatorExpression; var additiveOperator = new GrammarDefinition("AdditiveOperator", rule: ToElement(PLUS) | ToElement(MINUS)); var additiveExpression = new GrammarDefinition("AdditiveExpression"); additiveExpression.Rule = multiplicativeExpression | additiveExpression + additiveOperator + multiplicativeExpression; additiveExpression.ComputeResult = createBinaryOperatorExpression; var shiftOperator = new GrammarDefinition("ShiftOperator", rule: ToElement(OP_SHIFT_LEFT) | ToElement(OP_SHIFT_RIGHT)); var shiftExpression = new GrammarDefinition("ShiftExpression"); shiftExpression.Rule = additiveExpression | shiftExpression + shiftOperator + additiveExpression; shiftExpression.ComputeResult = createBinaryOperatorExpression; var relationalOperator = new GrammarDefinition("RelationalOperator", rule: ToElement(OP_GT) | ToElement(OP_GE) | ToElement(OP_LT) | ToElement(OP_LE) | ToElement(IS) | ToElement(AS)); var relationalExpression = new GrammarDefinition("RelationalExpression"); relationalExpression.Rule = shiftExpression | relationalExpression + relationalOperator + shiftExpression; relationalExpression.ComputeResult = node => { if (node.Children.Count == 1) return node.Children[0].Result; var operatorToken = (CSharpAstToken) node.Children[1].Children[0].Result; switch (operatorToken.Code) { case IS: return new TypeCheckExpression() { TargetExpression = (Expression) node.Children[0].Result, IsKeyword = operatorToken, TargetType = ToTypeReference((IConvertibleToType) node.Children[2].Result) }; case AS: return new SafeCastExpression() { TargetExpression = (Expression) node.Children[0].Result, CastKeyword = operatorToken, TargetType = ToTypeReference((IConvertibleToType) node.Children[2].Result) }; default: return createBinaryOperatorExpression(node); } }; var equalityOperator = new GrammarDefinition("equalityOperator", rule: ToElement(OP_EQUALS) | ToElement(OP_NOTEQUALS)); var equalityExpression = new GrammarDefinition("EqualityExpression"); equalityExpression.Rule = relationalExpression | equalityExpression + equalityOperator + relationalExpression; equalityExpression.ComputeResult = createBinaryOperatorExpression; var logicalAndExpression = new GrammarDefinition("LogicalAndExpression"); logicalAndExpression.Rule = equalityExpression | logicalAndExpression + ToElement(BITWISE_AND) + equalityExpression; logicalAndExpression.ComputeResult = createBinaryOperatorExpression; var logicalXorExpression = new GrammarDefinition("LogicalOrExpression"); logicalXorExpression.Rule = logicalAndExpression | logicalXorExpression + ToElement(CARRET) + logicalAndExpression; logicalXorExpression.ComputeResult = createBinaryOperatorExpression; var logicalOrExpression = new GrammarDefinition("LogicalOrExpression"); logicalOrExpression.Rule = logicalXorExpression | logicalOrExpression + ToElement(BITWISE_OR) + logicalXorExpression; logicalOrExpression.ComputeResult = createBinaryOperatorExpression; var conditionalAndExpression = new GrammarDefinition("ConditionalAndExpression"); conditionalAndExpression.Rule = logicalOrExpression | conditionalAndExpression + ToElement(OP_AND) + logicalOrExpression; conditionalAndExpression.ComputeResult = createBinaryOperatorExpression; var conditionalOrExpression = new GrammarDefinition("ConditionalOrExpression"); conditionalOrExpression.Rule = conditionalAndExpression | conditionalOrExpression + ToElement(OP_OR) + conditionalAndExpression; conditionalOrExpression.ComputeResult = createBinaryOperatorExpression; var nullCoalescingExpression = new GrammarDefinition("NullCoalescingExpression"); nullCoalescingExpression.Rule = conditionalOrExpression | nullCoalescingExpression + ToElement(OP_COALESCING) + conditionalOrExpression; nullCoalescingExpression.ComputeResult = createBinaryOperatorExpression; var conditionalExpression = new GrammarDefinition("ConditionalExpression", rule: nullCoalescingExpression | nullCoalescingExpression + ToElement(INTERR) + expression + ToElement(COLON) + expression, createNode: node => node.Children.Count == 1 ? node.Children[0].Result : new ConditionalExpression { Condition = (Expression) node.Children[0].Result, OperatorToken = (AstToken) node.Children[1].Result, TrueExpression = (Expression) node.Children[2].Result, ColonToken = (AstToken) node.Children[3].Result, FalseExpression = (Expression) node.Children[4].Result }); var assignmentOperator = new GrammarDefinition("AssignmentOperator", rule: ToElement(EQUALS) | ToElement(OP_ADD_ASSIGN) | ToElement(OP_SUB_ASSIGN) | ToElement(OP_MULT_ASSIGN) | ToElement(OP_DIV_ASSIGN) | ToElement(OP_AND_ASSIGN) | ToElement(OP_OR_ASSIGN) | ToElement(OP_XOR_ASSIGN) | ToElement(OP_SHIFT_LEFT_ASSIGN) | ToElement(OP_SHIFT_RIGHT_ASSIGN)); var assignmentExpression = new GrammarDefinition("AssignmentExpression", rule: unaryOperatorExpression + assignmentOperator + expression, createNode: node => new AssignmentExpression { Target = (Expression) node.Children[0].Result, Operator = CSharpLanguage.AssignmentOperatorFromString(((AstToken) node.Children[1].Children[0].Result).Value), OperatorToken = (AstToken) node.Children[1].Children[0].Result, Value = (Expression) node.Children[2].Result, }); var fromClause = new GrammarDefinition("FromClause", rule: ToElement(FROM) + identifierInsideBody + ToElement(IN) + expression, createNode: node => new LinqFromClause { FromKeyword = (AstToken) node.Children[0].Result, VariableName = (Identifier) node.Children[1].Result, InKeyword = (AstToken) node.Children[2].Result, DataSource = (Expression) node.Children[3].Result }); var letClause = new GrammarDefinition("LetClause", rule: ToElement(LET) + variableDeclarator, createNode: node => new LinqLetClause() { LetKeyword = (AstToken) node.Children[0].Result, Variable = (VariableDeclarator) node.Children[1].Result }); var whereClause = new GrammarDefinition("WhereClause", rule: ToElement(WHERE) + expression, createNode: node => new LinqWhereClause() { WhereKeyword = (AstToken) node.Children[0].Result, Condition = (Expression) node.Children[1].Result }); var orderingDirection = new GrammarDefinition("OrderingDirection", rule: null | ToElement(ASCENDING) | ToElement(DESCENDING)); var ordering = new GrammarDefinition("Ordering", rule: expression + orderingDirection, createNode: node => { var result = new LinqOrdering(); result.Expression = (Expression) node.Children[0].Result; if (node.Children[1].HasChildren) { var directionNode = node.Children[1].Children[0]; result.DirectionKeyword = (AstToken) directionNode.Result; result.Direction = directionNode.Result != null ? CSharpLanguage.OrderningDirectionFromString(result.DirectionKeyword.Value) : LinqOrderingDirection.None; } return result; }); var orderings = new GrammarDefinition("Orderings"); orderings.Rule = ordering | orderings + ToElement(COMMA) + ordering; var orderByClause = new GrammarDefinition("OrderByClause", rule: ToElement(ORDERBY) + orderings, createNode: node => { var result = new LinqOrderByClause(); result.OrderByKeyword = (AstToken) node.Children[0].Result; foreach (var subNode in node.Children[1].GetAllListAstNodes()) { if (subNode is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, subNode); else result.Ordernings.Add((LinqOrdering) subNode); } return result; }); var groupByClause = new GrammarDefinition("GroupByClause", rule: ToElement(GROUP) + expression + ToElement(BY) + expression, createNode: node => new LinqGroupByClause() { GroupKeyword = (AstToken) node.Children[0].Result, Expression = (Expression) node.Children[1].Result, ByKeyword = (AstToken) node.Children[2].Result, KeyExpression = (Expression) node.Children[3].Result }); var selectClause = new GrammarDefinition("SelectClause", rule: ToElement(SELECT) + expression, createNode: node => new LinqSelectClause() { SelectKeyword = (AstToken) node.Children[0].Result, Target = (Expression) node.Children[1].Result }); var queryBodyClause = new GrammarDefinition("QueryBodyClause", rule: fromClause | letClause | groupByClause | whereClause | orderByClause ); var queryBodyClauses = new GrammarDefinition("QueryBodyClauses"); queryBodyClauses.Rule = queryBodyClause | queryBodyClauses + queryBodyClause; var queryBodyClausesOptional = new GrammarDefinition("QueryBodyClausesOptional", rule: null | queryBodyClauses); var linqExpression = new GrammarDefinition("LinqExpression", rule: fromClause + queryBodyClausesOptional + selectClause, createNode: node => { var result = new LinqExpression(); result.Clauses.Add((LinqClause) node.Children[0].Result); if (node.Children[1].HasChildren) { result.Clauses.AddRange(node.Children[1].Children[0].GetAllListAstNodes().Cast<LinqClause>()); } result.Clauses.Add((LinqClause) node.Children[2].Result); return result; }); expression.Rule = conditionalExpression | linqExpression | lambdaExpression | assignmentExpression; #endregion #region Statements var statement = new GrammarDefinition("Statement"); var embeddedStatement = new GrammarDefinition("EmbeddedStatement"); var emptyStatement = new GrammarDefinition("EmptyStatement", rule: ToElement(SEMICOLON), createNode: node => { var result = new EmptyStatement(); result.AddChild(AstNodeTitles.Semicolon, node.Children[0].Result); return result; }); var labelStatement = new GrammarDefinition("LabelStatement", rule: identifierInsideBody + ToElement(COLON), createNode: node => new LabelStatement((Identifier) node.Children[0].Result) { Colon = (AstToken) node.Children[1].Result }); var expressionStatement = new GrammarDefinition("ExpressionStatement", rule: expression + ToElement(SEMICOLON) | Error + ToElement(SEMICOLON) | Error + ToElement(CLOSE_BRACE) | expression + ToElement(CLOSE_BRACE), // Common mistake in C# is to forget the semicolon at the end of a statement. createNode: node => { var result = new ExpressionStatement(node.Children[0].Result as Expression); var endingToken = (AstToken) node.Children[1].Result; if (endingToken.GetTokenCode() == (int) SEMICOLON) { result.AddChild(AstNodeTitles.Semicolon, node.Children[1].Result); } else { node.Context.SyntaxErrors.Add(new SyntaxError( node.Children[1].Range.End, "';' expected.", MessageSeverity.Error)); node.Context.Lexer.PutBack((AstToken) endingToken); } return result; }); blockStatement.Rule = ToElement(OPEN_BRACE) + statementListOptional + ToElement(CLOSE_BRACE); blockStatement.ComputeResult = node => { var result = new BlockStatement(); result.StartScope = node.Children[0].Result; if (node.Children[1].HasChildren) { result.Statements.AddRange(node.Children[1].Children[0].GetAllListAstNodes<Statement>()); } result.EndScope = node.Children[2].Result; return result; }; var variableDeclarationStatement = new GrammarDefinition("VariableDeclarationStatement", rule: variableDeclaration + ToElement(SEMICOLON), createNode: node => { var result = node.Children[0].Result; result.AddChild(AstNodeTitles.Semicolon, node.Children[1].Result); return result; }); var ifElseStatement = new GrammarDefinition("IfElseStatement", rule: ToElement(IF) + parenthesizedExpression + embeddedStatement | ToElement(IF) + parenthesizedExpression + embeddedStatement + ToElement(ELSE) + embeddedStatement , createNode: node => { var result = new IfElseStatement(); result.IfKeyword = (AstToken) node.Children[0].Result; var parenthesized = (ParenthesizedExpression) node.Children[1].Result; result.LeftParenthese = (AstToken) parenthesized.LeftParenthese.Remove(); result.Condition = (Expression) parenthesized.Expression?.Remove(); result.RightParenthese = (AstToken) parenthesized.RightParenthese.Remove(); result.TrueBlock = (Statement) node.Children[2].Result; if (node.Children.Count > 3) { result.ElseKeyword = (AstToken) node.Children[3].Result; result.FalseBlock = (Statement) node.Children[4].Result; CheckForPossibleMistakenEmptyStatement(node.Children[4]); } else { CheckForPossibleMistakenEmptyStatement(node.Children[2]); } return result; }); var switchLabel = new GrammarDefinition("SwitchLabel", rule: ToElement(CASE) + expression + ToElement(COLON) | ToElement(DEFAULT_COLON) + ToElement(COLON), createNode: node => { var result = new SwitchCaseLabel(); result.CaseKeyword = (AstToken) node.Children[0].Result; if (node.Children.Count > 2) result.Condition = (Expression) node.Children[1].Result; result.Colon = (AstToken) node.Children[node.Children.Count - 1].Result; return result; }); var switchLabels = new GrammarDefinition("SwitchLabels"); switchLabels.Rule = switchLabel | switchLabels + switchLabel; var switchSection = new GrammarDefinition("SwitchSection", rule: switchLabels + statementList, createNode: node => { var result = new SwitchSection(); result.Labels.AddRange(node.Children[0].GetAllListAstNodes<SwitchCaseLabel>()); result.Statements.AddRange(node.Children[1].GetAllListAstNodes<Statement>()); return result; }); var switchSections = new GrammarDefinition("SwitchSections"); switchSections.Rule = switchSection | switchSections + switchSection; var switchBlock = new GrammarDefinition("SwitchBlock", rule: ToElement(OPEN_BRACE) + switchSections + ToElement(CLOSE_BRACE)); var switchStatement = new GrammarDefinition("SwitchStatement", rule: ToElement(SWITCH) + ToElement(OPEN_PARENS) + expression + ToElement(CLOSE_PARENS) + switchBlock, createNode: node => { var result = new SwitchStatement(); result.SwitchKeyword = (AstToken) node.Children[0].Result; result.LeftParenthese = (AstToken) node.Children[1].Result; result.Condition = (Expression) node.Children[2].Result; result.RightParenthese = (AstToken) node.Children[3].Result; var switchBlockNode = node.Children[4]; result.StartScope = switchBlockNode.Children[0].Result; result.Sections.AddRange(switchBlockNode.Children[1].GetAllListAstNodes<SwitchSection>()); result.EndScope = switchBlockNode.Children[2].Result; return result; }); var selectionStatement = new GrammarDefinition("SelectionStatement", rule: ifElseStatement | switchStatement); var whileLoopStatement = new GrammarDefinition("WhileLoopStatement", rule: ToElement(WHILE) + parenthesizedExpression + embeddedStatement, createNode: node => { var bodyNode = node.Children[2]; CheckForPossibleMistakenEmptyStatement(bodyNode); var conditionExpr = (ParenthesizedExpression) node.Children[1].Result; return new WhileLoopStatement { WhileKeyword = (AstToken) node.Children[0].Result, LeftParenthese = (AstToken) conditionExpr.LeftParenthese.Remove(), Condition = (Expression) conditionExpr.Expression.Remove(), RightParenthese = (AstToken) conditionExpr.RightParenthese.Remove(), Body = (Statement) bodyNode.Result }; }); var doLoopStatement = new GrammarDefinition("DoLoopStatement", rule: ToElement(DO) + embeddedStatement + ToElement(WHILE) + parenthesizedExpression + ToElement(SEMICOLON), createNode: node => { var conditionExpr = (ParenthesizedExpression) node.Children[3].Result; return new DoLoopStatement { DoKeyword = (AstToken) node.Children[0].Result, Body = (Statement) node.Children[1].Result, WhileKeyword = (AstToken) node.Children[2].Result, LeftParenthese = (AstToken) conditionExpr.LeftParenthese.Remove(), Condition = (Expression) conditionExpr.Expression.Remove(), RightParenthese = (AstToken) conditionExpr.RightParenthese.Remove(), Semicolon = (AstToken) node.Children[4].Result }; }); var forLoopInitializer = new GrammarDefinition("ForLoopInitializer", rule: variableDeclaration | null // TODO: statement-expression-list ); var forLoopCondition = new GrammarDefinition("ForLoopCondition", rule: expression | null); var forLoopStatement = new GrammarDefinition("ForLoopStatement", rule: ToElement(FOR) + ToElement(OPEN_PARENS) + forLoopInitializer + ToElement(SEMICOLON) + expressionOptional + ToElement(SEMICOLON) + expressionOptional // TODO: statement-expression-list + ToElement(CLOSE_PARENS) + embeddedStatement, createNode: node => { var result = new ForLoopStatement(); result.ForKeyword = (AstToken) node.Children[0].Result; result.LeftParenthese = (AstToken) node.Children[1].Result; if (node.Children[2].HasChildren) { var declaration = node.Children[2].Children[0].Result as VariableDeclarationStatement; if (declaration != null) { result.Initializers.Add(declaration); } else { result.Initializers.AddRange(node.Children[2].GetAllListAstNodes<Expression>() .Select(x => new ExpressionStatement(x))); } } result.AddChild(AstNodeTitles.Semicolon, node.Children[3].Result); if (node.Children[4].HasChildren) result.Condition = (Expression) node.Children[4].Result; result.AddChild(AstNodeTitles.Semicolon, node.Children[5].Result); if (node.Children[6].HasChildren) { result.Iterators.AddRange(node.Children[6].Children[0].GetAllListAstNodes<Expression>() .Select(x => new ExpressionStatement(x))); } result.RightParenthese = (AstToken) node.Children[7].Result; var bodyNode = node.Children[8]; CheckForPossibleMistakenEmptyStatement(bodyNode); result.Body = (Statement) bodyNode.Result; return result; }); var foreachLoopStatement = new GrammarDefinition("ForEachLoopStatement", rule: ToElement(FOREACH) + ToElement(OPEN_PARENS) + typeReference + identifierInsideBody + ToElement(IN) + expression + ToElement(CLOSE_PARENS) + embeddedStatement, createNode: node => { var bodyNode = node.Children[7]; CheckForPossibleMistakenEmptyStatement(bodyNode); return new ForeachLoopStatement { ForeachKeyword = (AstToken) node.Children[0].Result, LeftParenthese = (AstToken) node.Children[1].Result, Type = (TypeReference) node.Children[2].Result, Identifier = (Identifier) node.Children[3].Result, InKeyword = (AstToken) node.Children[4].Result, Target = (Expression) node.Children[5].Result, RightParenthese = (AstToken) node.Children[6].Result, Body = (Statement) bodyNode.Result }; }); var loopStatement = new GrammarDefinition("LoopStatement", rule: whileLoopStatement | doLoopStatement | forLoopStatement | foreachLoopStatement); var lockStatement = new GrammarDefinition("LockStatement", rule: ToElement(LOCK) + ToElement(OPEN_PARENS) + expression + ToElement(CLOSE_PARENS) + statement, createNode: node => { var bodyNode = node.Children[4]; CheckForPossibleMistakenEmptyStatement(bodyNode); return new LockStatement { LockKeyword = (AstToken) node.Children[0].Result, LeftParenthese = (AstToken) node.Children[1].Result, LockObject = (Expression) node.Children[2].Result, RightParenthese = (AstToken) node.Children[3].Result, Body = (Statement) bodyNode.Result }; }); var resourceAcquisition = new GrammarDefinition("ResourceAcquisition", rule: variableDeclaration | expression); var usingStatement = new GrammarDefinition("UsingStatement", rule: ToElement(USING) + ToElement(OPEN_PARENS) + resourceAcquisition + ToElement(CLOSE_PARENS) + statement, createNode: node => { var bodyNode = node.Children[4]; CheckForPossibleMistakenEmptyStatement(bodyNode); return new UsingStatement() { UsingKeyword = (AstToken) node.Children[0].Result, LeftParenthese = (AstToken) node.Children[1].Result, DisposableObject = node.Children[2].Result, RightParenthese = (AstToken) node.Children[3].Result, Body = (Statement) bodyNode.Result }; }); var breakStatement = new GrammarDefinition("BreakStatement", rule: ToElement(BREAK) + ToElement(SEMICOLON), createNode: node => new BreakStatement() { Keyword = (AstToken) node.Children[0].Result, Semicolon = (AstToken) node.Children[1].Result }); var continueStatement = new GrammarDefinition("ContinueStatement", rule: ToElement(CONTINUE) + ToElement(SEMICOLON), createNode: node => new BreakStatement() { Keyword = (AstToken) node.Children[0].Result, Semicolon = (AstToken) node.Children[1].Result }); var returnStatement = new GrammarDefinition("ReturnStatement", rule: ToElement(RETURN) + expressionOptional + ToElement(SEMICOLON), createNode: node => { var result = new ReturnStatement(); result.ReturnKeyword = (AstToken) node.Children[0].Result; if (node.Children[1].HasChildren) result.Value = (Expression) node.Children[1].Result; result.AddChild(AstNodeTitles.Semicolon, node.Children[2].Result); return result; }); var throwStatement = new GrammarDefinition("ThrowStatement", rule: ToElement(THROW) + expressionOptional + ToElement(SEMICOLON), createNode: node => { var result = new ThrowStatement(); result.ThrowKeyword = (AstToken) node.Children[0].Result; if (node.Children[1].HasChildren) result.Expression = (Expression) node.Children[1].Result; result.AddChild(AstNodeTitles.Semicolon, node.Children[2].Result); return result; }); var gotoStatement = new GrammarDefinition("GotoStatement", rule: ToElement(GOTO) + identifierInsideBody + ToElement(SEMICOLON), // TODO: goto case and goto default statements. createNode: node => { var result = new GotoStatement(); result.GotoKeyword = (AstToken) node.Children[0].Result; result.LabelIdentifier = (Identifier) node.Children[1].Result; result.AddChild(AstNodeTitles.Semicolon, node.Children[2].Result); return result; }); var jumpStatement = new GrammarDefinition("JumpStatement", rule: breakStatement | continueStatement | gotoStatement | returnStatement | throwStatement); var yieldStatement = new GrammarDefinition("YieldStatement", rule: ToElement(YIELD) + ToElement(RETURN) + expression + ToElement(SEMICOLON), createNode: node => new YieldStatement() { YieldKeyword = (AstToken) node.Children[0].Result, ReturnKeyword = (AstToken) node.Children[1].Result, Value = (Expression) node.Children[2].Result }); var yieldBreakStatement = new GrammarDefinition("YieldBreakStatement", rule: ToElement(YIELD) + ToElement(BREAK) + ToElement(SEMICOLON), createNode: node => new YieldBreakStatement() { Keyword = (AstToken) node.Children[0].Result, BreakKeyword = (AstToken) node.Children[1].Result }); var specificCatchClause = new GrammarDefinition("SpecificCatchClause", rule: ToElement(CATCH) + ToElement(OPEN_PARENS) + namespaceOrTypeExpression + identifierInsideBodyOptional + ToElement(CLOSE_PARENS) + blockStatement, createNode: node => { var result = new CatchClause(); result.CatchKeyword = (AstToken) node.Children[0].Result; result.LeftParenthese = (AstToken) node.Children[1].Result; result.ExceptionType = (TypeReference) node.Children[2].Result; if (node.Children[3].HasChildren) result.ExceptionIdentifier = (Identifier) node.Children[3].Result; result.RightParenthese = (AstToken) node.Children[4].Result; result.Body = (BlockStatement) node.Children[5].Result; return result; }); var generalCatchClause = new GrammarDefinition("GeneralCatchClause", rule: ToElement(CATCH) + blockStatement, createNode: node => new CatchClause { CatchKeyword = (AstToken) node.Children[0].Result, Body = (BlockStatement) node.Children[1].Result }); var catchClause = new GrammarDefinition("CatchClause", rule: specificCatchClause | generalCatchClause); var catchClauses = new GrammarDefinition("CatchClauses"); catchClauses.Rule = catchClause | catchClauses + catchClause; var finallyClause = new GrammarDefinition("FinallyClause", rule: ToElement(FINALLY) + blockStatement); var tryCatchStatement = new GrammarDefinition("TryCatchStatement", rule: ToElement(TRY) + blockStatement + catchClauses | ToElement(TRY) + blockStatement + finallyClause | ToElement(TRY) + blockStatement + catchClauses + finallyClause, createNode: node => { var result = new TryCatchStatement(); result.TryKeyword = (AstToken) node.Children[0].Result; result.TryBlock = (BlockStatement) node.Children[1].Result; ParserNode finallyClauseNode = null; if (node.Children[2].GrammarElement == finallyClause) { finallyClauseNode = node.Children[2]; } else { result.CatchClauses.AddRange(node.Children[2].GetAllListAstNodes<CatchClause>()); } if (node.Children.Count == 4) finallyClauseNode = node.Children[3]; if (finallyClauseNode != null) { result.FinallyKeyword = (AstToken) finallyClauseNode.Children[0].Result; result.FinallyBlock = (BlockStatement) finallyClauseNode.Children[1].Result; } return result; }); var unsafeStatement = new GrammarDefinition("UnsafeStatement", rule: ToElement(UNSAFE) + blockStatement, createNode: node => new UnsafeStatement() { Keyword = (AstToken) node.Children[0].Result, Body = (BlockStatement) node.Children[1].Result }); var fixedStatement = new GrammarDefinition("FixedStatement", rule: ToElement(FIXED) + ToElement(OPEN_PARENS) + variableDeclaration + ToElement(CLOSE_PARENS) + embeddedStatement, createNode: node => { var result = new FixedStatement(); result.Keyword = (AstToken) node.Children[0].Result; result.LeftParenthese = (AstToken) node.Children[1].Result; result.VariableDeclaration = (VariableDeclarationStatement) node.Children[2].Result; result.RightParenthese = (AstToken) node.Children[3].Result; var bodyNode = node.Children[4]; result.Body = (Statement) bodyNode.Result; CheckForPossibleMistakenEmptyStatement(bodyNode); return result; }); embeddedStatement.Rule = emptyStatement | expressionStatement | blockStatement | selectionStatement | loopStatement | jumpStatement | lockStatement | usingStatement | yieldStatement | yieldBreakStatement | tryCatchStatement | unsafeStatement | fixedStatement ; statement.Rule = variableDeclarationStatement | labelStatement | embeddedStatement; ; #endregion #region Members var customAttribute = new GrammarDefinition("CustomAttribute", rule: namespaceOrTypeExpression | namespaceOrTypeExpression + ToElement(OPEN_PARENS) + argumentListOptional + ToElement(CLOSE_PARENS), createNode: node => { var result = new CustomAttribute(); result.Type = ((IConvertibleToType) node.Children[0].Result).ToTypeReference(); if (node.Children.Count > 1) { result.LeftParenthese = (AstToken) node.Children[1].Result; if (node.Children[2].HasChildren) { foreach (var child in node.Children[2].Children[0].GetAllListAstNodes()) { if (child is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, child); else result.Arguments.Add((Expression) child); } } result.RightParenthese = (AstToken) node.Children[3].Result; } return result; }); var customAttributeList = new GrammarDefinition("CustomAttributeList"); customAttributeList.Rule = customAttribute | customAttributeList + ToElement(COMMA) + customAttribute; var customAttributePrefix = new GrammarDefinition("CustomAttributePrefix", rule: ToElement(ASSEMBLY) | ToElement(MODULE)); var customAttributePrefixOptional = new GrammarDefinition("CustomAttributePrefixOptional", rule: null | customAttributePrefix + ToElement(COLON)); var customAttributeSection = new GrammarDefinition("CustomAttributeSection", rule: ToElement(OPEN_BRACKET_EXPR) // HACK: use expression brackets instead to avoid conflicts. + customAttributePrefixOptional + customAttributeList + ToElement(CLOSE_BRACKET), createNode: node => { var result = new CustomAttributeSection(); result.LeftBracket = (AstToken) node.Children[0].Result; if (node.Children[1].Result != null) { result.VariantKeyword = (AstToken) node.Children[1].Result; result.Variant = CSharpLanguage.SectionVariantFromString(result.VariantKeyword.Value); } foreach (var child in node.Children[2].GetAllListAstNodes()) { if (child is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, child); else result.Attributes.Add((CustomAttribute) child); } result.RightBracket = (AstToken) node.Children[3].Result; return result; }); var customAttributeSectionList = new GrammarDefinition("CustomAttributeSectionList"); customAttributeSectionList.Rule = customAttributeSection | customAttributeSectionList + customAttributeSection; var customAttributeSectionListOptional = new GrammarDefinition("CustomAttributeSectionListOptional", rule: null | customAttributeSectionList); var modifier = new GrammarDefinition("Modifier", rule: ToElement(PRIVATE) | ToElement(PROTECTED) | ToElement(INTERNAL) | ToElement(PUBLIC) | ToElement(STATIC) | ToElement(ABSTRACT) | ToElement(OVERRIDE) | ToElement(PARTIAL) | ToElement(CONST) | ToElement(READONLY) | ToElement(VIRTUAL) | ToElement(SEALED) | ToElement(UNSAFE) | ToElement(FIXED) | ToElement(ASYNC) | ToElement(EXTERN), createNode: node => new ModifierElement(((AstToken) node.Children[0].Result).Value, node.Children[0].Range) { Modifier = CSharpLanguage.ModifierFromString(((AstToken) node.Children[0].Result).Value) }); var modifierList = new GrammarDefinition("ModifierList"); modifierList.Rule = modifier | modifierList + modifier; var modifierListOptional = new GrammarDefinition("ModifierListOptional", rule: null | modifierList); var fieldDeclaration = new GrammarDefinition("FieldDeclaration", rule: customAttributeSectionListOptional + modifierListOptional + typeReference + variableDeclaratorList + ToElement(SEMICOLON), createNode: node => { var result = new FieldDeclaration(); if (node.Children[0].HasChildren) result.CustomAttributeSections.AddRange(node.Children[0].Children[0].GetAllListAstNodes<CustomAttributeSection>()); if (node.Children[1].HasChildren) result.ModifierElements.AddRange(node.Children[1].Children[0].GetAllListAstNodes<ModifierElement>()); result.FieldType = (TypeReference) node.Children[2].Result; foreach (var subNode in node.Children[3].GetAllListAstNodes()) { if (subNode is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, subNode); else result.Declarators.Add((VariableDeclarator) subNode); } result.AddChild(AstNodeTitles.Semicolon, node.Children[4].Result); return result; }); var parameterModifier = new GrammarDefinition("ParameterModifier", rule: null | ToElement(THIS) | ToElement(REF) | ToElement(OUT) | ToElement(PARAMS)); var parameterDeclaration = new GrammarDefinition("ParameterDeclaration", rule: customAttributeSectionListOptional + parameterModifier + typeReference + variableDeclarator, createNode: node => { var result = new ParameterDeclaration(); if (node.Children[0].HasChildren) { result.CustomAttributeSections.AddRange( node.Children[0].Children[0].GetAllListAstNodes<CustomAttributeSection>()); } result.ParameterModifierToken = (AstToken) (node.Children[1].HasChildren ? node.Children[1].Children[0].Result : null); result.ParameterType = (TypeReference) node.Children[2].Result; result.Declarator = (VariableDeclarator) node.Children[3].Result; return result; }); var parameterDeclarationList = new GrammarDefinition("ParameterDeclarationList"); parameterDeclarationList.Rule = parameterDeclaration | parameterDeclarationList + ToElement(COMMA) + parameterDeclaration; var optionalParameterDeclarationList = new GrammarDefinition("OptionalParameterDeclarationList", rule: null | parameterDeclarationList); var constructorInitializerVariant = new GrammarDefinition("ConstructorInitializerVariant", rule: ToElement(THIS) | ToElement(BASE)); var constructorInitializer = new GrammarDefinition("ConstructorInitializer", rule: constructorInitializerVariant + ToElement(OPEN_PARENS) + argumentListOptional + ToElement(CLOSE_PARENS), createNode: node => { var result = new Members.ConstructorInitializer(); result.VariantToken = (AstToken) node.Children[0].Children[0].Result; result.LeftParenthese = (AstToken) node.Children[1].Result; if (node.Children[2].HasChildren) { foreach (var subNode in node.Children[2].Children[0].GetAllListAstNodes()) { if (subNode is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, subNode); else result.Arguments.Add((Expression) subNode); } } result.RightParenthese = (AstToken) node.Children[3].Result; return result; }); var optionalConstructorInitializerList = new GrammarDefinition("OptionalConstructorInitializer", rule: null | ToElement(COLON) + constructorInitializer); var constructorDeclaration = new GrammarDefinition("ConstructorDeclaration", rule: customAttributeSectionListOptional + modifierListOptional + ToElement(IDENTIFIER) + ToElement(OPEN_PARENS) + optionalParameterDeclarationList + ToElement(CLOSE_PARENS) + optionalConstructorInitializerList + blockStatement, createNode: node => { var result = new Members.ConstructorDeclaration(); if (node.Children[0].HasChildren) result.CustomAttributeSections.AddRange(node.Children[0].Children[0].GetAllListAstNodes<CustomAttributeSection>()); if (node.Children[1].HasChildren) result.ModifierElements.AddRange(node.Children[1].Children[0].GetAllListAstNodes<ModifierElement>()); result.Identifier = ToIdentifier(node.Children[2].Result); result.LeftParenthese = (AstToken) node.Children[3].Result; if (node.Children[4].HasChildren) { foreach (var subNode in node.Children[4].Children[0].GetAllListAstNodes()) { if (subNode is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, subNode); else result.Parameters.Add((ParameterDeclaration) subNode); } } result.RightParenthese = (AstToken) node.Children[5].Result; if (node.Children[6].HasChildren) { result.Colon = (AstToken) node.Children[6].Children[0].Result; result.Initializer = (Members.ConstructorInitializer) node.Children[6].Children[1].Result; } result.Body = (BlockStatement) node.Children[7].Result; return result; }); var conversionOperator = new GrammarDefinition("ConversionOperator", rule: ToElement(IMPLICIT) | ToElement(EXPLICIT)); var conversionOperatorDeclaration = new GrammarDefinition("ConversionOperatorDeclaration", rule: customAttributeSectionListOptional + modifierListOptional + conversionOperator + ToElement(OPERATOR) + ToElement(IDENTIFIER) + ToElement(OPEN_PARENS) + optionalParameterDeclarationList + ToElement(CLOSE_PARENS) + blockStatement, createNode: node => { var result = new OperatorDeclaration(); if (node.Children[0].HasChildren) result.CustomAttributeSections.AddRange(node.Children[0].Children[0].GetAllListAstNodes<CustomAttributeSection>()); if (node.Children[1].HasChildren) result.ModifierElements.AddRange(node.Children[1].Children[0].GetAllListAstNodes<ModifierElement>()); result.Identifier = ToIdentifier(node.Children[2].Result); result.OperatorType = CSharpLanguage.OperatorDeclarationTypeFromString(result.Identifier.Name); result.OperatorKeyword = (AstToken) node.Children[3].Result; result.ReturnType = ToTypeReference(ToIdentifier(node.Children[4].Result)); result.LeftParenthese = (AstToken)node.Children[5].Result; if (node.Children[6].HasChildren) { foreach (var subNode in node.Children[6].Children[0].GetAllListAstNodes()) { if (subNode is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, subNode); else result.Parameters.Add((ParameterDeclaration)subNode); } } result.RightParenthese = (AstToken) node.Children[7].Result; result.Body = (BlockStatement) node.Children[8].Result; return result; }); var overloadableOperator = new GrammarDefinition("OverloadableOperator", rule: ToElement(PLUS) | ToElement(MINUS) | ToElement(STAR) | ToElement(DIV) | ToElement(PERCENT) | ToElement(BITWISE_AND) | ToElement(BITWISE_OR) | ToElement(CARRET) | ToElement(OP_EQUALS) | ToElement(OP_NOTEQUALS) | ToElement(OP_GT) | ToElement(OP_GE) | ToElement(OP_LT) | ToElement(OP_LE) | ToElement(OP_SHIFT_LEFT) | ToElement(OP_SHIFT_RIGHT) | ToElement(TRUE) | ToElement(FALSE) | ToElement(BANG) | ToElement(TILDE) | ToElement(OP_INC) | ToElement(OP_DEC)); var arithmeticOperatorDeclaration = new GrammarDefinition("ArithmeticOperatorDeclaration", rule: customAttributeSectionListOptional + modifierListOptional + typeReference + ToElement(OPERATOR) + overloadableOperator + ToElement(OPEN_PARENS) + optionalParameterDeclarationList + ToElement(CLOSE_PARENS) + blockStatement, createNode: node => { var result = new OperatorDeclaration(); if (node.Children[0].HasChildren) result.CustomAttributeSections.AddRange(node.Children[0].Children[0].GetAllListAstNodes<CustomAttributeSection>()); if (node.Children[1].HasChildren) result.ModifierElements.AddRange(node.Children[1].Children[0].GetAllListAstNodes<ModifierElement>()); result.ReturnType = (TypeReference) node.Children[2].Result; result.OperatorKeyword = (AstToken)node.Children[3].Result; result.Identifier = ToIdentifier(node.Children[4].Result); result.LeftParenthese = (AstToken)node.Children[5].Result; if (node.Children[6].HasChildren) { foreach (var subNode in node.Children[6].Children[0].GetAllListAstNodes()) { if (subNode is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, subNode); else result.Parameters.Add((ParameterDeclaration)subNode); } } result.RightParenthese = (AstToken)node.Children[7].Result; result.OperatorType = CSharpLanguage.OperatorDeclarationTypeFromString(result.Identifier.Name); if (result.Parameters.Count == 2) { if (result.OperatorType == OperatorDeclarationType.Positive) result.OperatorType = OperatorDeclarationType.Add; else if (result.OperatorType == OperatorDeclarationType.Negative) result.OperatorType = OperatorDeclarationType.Subtract; } result.Body = (BlockStatement)node.Children[8].Result; return result; }); var operatorDeclaration = new GrammarDefinition("OperatorDeclaration", rule: conversionOperatorDeclaration | arithmeticOperatorDeclaration); var methodDeclarationBody = new GrammarDefinition("MethodDeclarationBody", rule: ToElement(SEMICOLON) | blockStatement); var methodDeclaration = new GrammarDefinition("MethodDeclaration", rule: customAttributeSectionListOptional + modifierListOptional + typeReference + ToElement(IDENTIFIER) + ToElement(OPEN_PARENS) + optionalParameterDeclarationList + ToElement(CLOSE_PARENS) + methodDeclarationBody, createNode: node => { var result = new MethodDeclaration(); if (node.Children[0].HasChildren) result.CustomAttributeSections.AddRange(node.Children[0].Children[0].GetAllListAstNodes<CustomAttributeSection>()); if (node.Children[1].HasChildren) result.ModifierElements.AddRange(node.Children[1].Children[0].GetAllListAstNodes<ModifierElement>()); result.ReturnType = (TypeReference) node.Children[2].Result; result.Identifier = ToIdentifier(node.Children[3].Result); result.LeftParenthese = (AstToken) node.Children[4].Result; if (node.Children[5].HasChildren) { foreach (var subNode in node.Children[5].Children[0].GetAllListAstNodes()) { if (subNode is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, subNode); else result.Parameters.Add((ParameterDeclaration) subNode); } } result.RightParenthese = (AstToken) node.Children[6].Result; var body = node.Children[7].Result; if (body is AstToken) result.AddChild(AstNodeTitles.Semicolon, (AstToken) body); else result.Body = (BlockStatement) body; return result; }); var eventDeclaration = new GrammarDefinition("EventDeclaration", rule: customAttributeSectionListOptional + modifierListOptional + ToElement(EVENT) + typeReference + variableDeclaratorList + ToElement(SEMICOLON), createNode: node => { var result = new EventDeclaration(); if (node.Children[0].HasChildren) result.CustomAttributeSections.AddRange(node.Children[0].Children[0].GetAllListAstNodes<CustomAttributeSection>()); if (node.Children[1].HasChildren) result.ModifierElements.AddRange(node.Children[1].Children[0].GetAllListAstNodes<ModifierElement>()); result.EventKeyword = (AstToken) node.Children[2].Result; result.EventType = (TypeReference) node.Children[3].Result; foreach (var subNode in node.Children[4].GetAllListAstNodes()) { if (subNode is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, subNode); else result.Declarators.Add((VariableDeclarator) subNode); } result.AddChild(AstNodeTitles.Semicolon, node.Children[5].Result); return result; }); var accessorKeyword = new GrammarDefinition("AccessorKeyword", rule: ToElement(GET) | ToElement(SET)); var accessorBody = new GrammarDefinition("AccessorBody", rule: ToElement(SEMICOLON) | blockStatement); var accessorDeclaration = new GrammarDefinition("AccessorDeclaration", rule: customAttributeSectionListOptional + modifierListOptional + accessorKeyword + accessorBody, createNode: node => { var result = new AccessorDeclaration(); if (node.Children[0].HasChildren) result.CustomAttributeSections.AddRange(node.Children[0].Children[0].GetAllListAstNodes<CustomAttributeSection>()); if (node.Children[1].HasChildren) result.ModifierElements.AddRange(node.Children[1].Children[0].GetAllListAstNodes<ModifierElement>()); result.AccessorKeyword = (AstToken) node.Children[2].Children[0].Result; var bodyNode = node.Children[3].Children[0].Result; if (bodyNode is AstToken) result.AddChild(AstNodeTitles.Semicolon, bodyNode); else result.Body = (BlockStatement) bodyNode; return result; }); var accessorDeclarationList = new GrammarDefinition("AccessorDeclarationList"); accessorDeclarationList.Rule = accessorDeclaration | accessorDeclaration + accessorDeclaration; var propertyDeclaration = new GrammarDefinition("PropertyDeclaration", rule: customAttributeSectionListOptional + modifierListOptional + typeReference + ToElement(IDENTIFIER) + ToElement(OPEN_BRACE) + accessorDeclarationList + ToElement(CLOSE_BRACE), createNode: node => { var result = new PropertyDeclaration(); if (node.Children[0].HasChildren) result.CustomAttributeSections.AddRange(node.Children[0].Children[0].GetAllListAstNodes<CustomAttributeSection>()); if (node.Children[1].HasChildren) result.ModifierElements.AddRange(node.Children[1].Children[0].GetAllListAstNodes<ModifierElement>()); result.PropertyType = (TypeReference) node.Children[2].Result; result.Identifier = ToIdentifier(node.Children[3].Result); result.StartScope = node.Children[4].Result; foreach (var accessor in node.Children[5].Children) { var declaration = (AccessorDeclaration) accessor.Result; // TODO: detect duplicate accessor declarations. switch (declaration.AccessorKeyword.Value) { case "get": result.Getter = declaration; break; case "set": result.Setter = declaration; break; } } result.EndScope = node.Children[6].Result; return result; }); var memberDeclaration = new GrammarDefinition("MemberDeclaration"); var memberDeclarationList = new GrammarDefinition("MemberDeclarationList"); memberDeclarationList.Rule = memberDeclaration | memberDeclarationList + memberDeclaration; var memberDeclarationListOptional = new GrammarDefinition("MemberDeclarationListOptional"); memberDeclarationListOptional.Rule = null | memberDeclarationList; var baseTypeList = new GrammarDefinition("BaseTypeList"); baseTypeList.Rule = typeReference | baseTypeList + ToElement(COMMA) + typeReference; var optionalBaseTypeList = new GrammarDefinition("OptionalBaseTypeList"); optionalBaseTypeList.Rule = null | ToElement(COLON) + baseTypeList; var typeVariantKeyword = new GrammarDefinition("TypeVariantKeyword", rule: ToElement(CLASS) | ToElement(STRUCT) | ToElement(INTERFACE) | ToElement(ENUM)); var typeDeclaration = new GrammarDefinition("TypeDeclaration", rule: customAttributeSectionListOptional + modifierListOptional + typeVariantKeyword + ToElement(IDENTIFIER) + optionalBaseTypeList + ToElement(OPEN_BRACE) + memberDeclarationListOptional + ToElement(CLOSE_BRACE), createNode: node => { var result = new TypeDeclaration(); if (node.Children[0].HasChildren) result.CustomAttributeSections.AddRange(node.Children[0].Children[0].GetAllListAstNodes<CustomAttributeSection>()); if (node.Children[1].HasChildren) result.ModifierElements.AddRange(node.Children[1].Children[0].GetAllListAstNodes<ModifierElement>()); var variantToken = (AstToken) node.Children[2].Children[0].Result; result.TypeVariant = CSharpLanguage.TypeVariantFromString(variantToken.Value); result.TypeVariantToken = variantToken; result.Identifier = ToIdentifier(node.Children[3].Result); if (node.Children[4].HasChildren) { result.AddChild(AstNodeTitles.Colon, node.Children[4].Children[0].Result); foreach (var child in node.Children[4].Children[1].GetAllListAstNodes()) { if (child is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, child); else result.BaseTypes.Add((TypeReference) child); } } result.StartScope = node.Children[5].Result; if (node.Children[6].HasChildren) { result.Members.AddRange(node.Children[6].Children[0].GetAllListAstNodes<MemberDeclaration>()); } result.EndScope = node.Children[7].Result; return result; }); memberDeclaration.Rule = methodDeclaration | constructorDeclaration | operatorDeclaration | propertyDeclaration | eventDeclaration | fieldDeclaration | typeDeclaration ; var typeOrNamespaceDeclarationList = new GrammarDefinition("TypeOrNamespaceDeclarationList"); var typeOrNamespaceDeclarationListOptional = new GrammarDefinition("TypeOrNamespaceDeclarationListOptional", rule: null | typeOrNamespaceDeclarationList); var namespaceDeclaration = new GrammarDefinition("NamespaceDeclaration", rule: ToElement(NAMESPACE) + typeNameExpression + ToElement(OPEN_BRACE) + usingDirectiveListOptional + typeOrNamespaceDeclarationListOptional + ToElement(CLOSE_BRACE), createNode: node => { var result = new NamespaceDeclaration(); result.Keyword = (AstToken) node.Children[0].Result; result.Identifier = ((IConvertibleToIdentifier) node.Children[1].Result).ToIdentifier(); result.StartScope = node.Children[2].Result; if (node.Children[3].HasChildren) { result.UsingDirectives.AddRange(node.Children[3].Children[0].GetAllListAstNodes<UsingDirective>()); } if (node.Children[4].HasChildren) { foreach (var subNode in node.Children[4].Children[0].GetAllListAstNodes()) { var type = subNode as TypeDeclaration; if (type != null) result.Types.Add(type); else result.Namespaces.Add((NamespaceDeclaration) subNode); } } result.EndScope = node.Children[5].Result; return result; }); var typeOrNamespaceDeclaration = new GrammarDefinition("TypeOrNamespaceDeclaration", rule: namespaceDeclaration | typeDeclaration); typeOrNamespaceDeclarationList.Rule = typeOrNamespaceDeclaration | typeOrNamespaceDeclarationList + typeOrNamespaceDeclaration; #endregion #region Initialize definitions var variableInitializerList = new GrammarDefinition("VariableInitializerList"); variableInitializerList.Rule = variableInitializer | variableInitializerList + ToElement(COMMA) + variableInitializer; var variableInitializerListOptional = new GrammarDefinition("VariableInitializerListOptional", rule: null | variableInitializerList); arrayInitializer.Rule = ToElement(OPEN_BRACE) + variableInitializerListOptional + ToElement(CLOSE_BRACE) | ToElement(OPEN_BRACE) + variableInitializerList + ToElement(COMMA) + ToElement(CLOSE_BRACE); arrayInitializer.ComputeResult = node => { var result = new ArrayInitializer(); result.OpeningBrace = node.Children[0].Result; ParserNode initializersNode = null; if (node.Children.Count == 4) { initializersNode = node.Children[1]; } else { if (node.Children[1].HasChildren) initializersNode = node.Children[1].Children[0]; } if (initializersNode != null) { foreach (var element in initializersNode.GetAllListAstNodes()) { if (element is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, element); else result.Elements.Add((Expression) element); } } if (node.Children.Count == 4) result.AddChild(AstNodeTitles.ElementSeparator, node.Children[2].Result); result.ClosingBrace = node.Children[node.Children.Count - 1].Result; return result; }; variableInitializer.Rule = expression | arrayInitializer ; var variableType = new GrammarDefinition("VariableType"); variableType.Rule = typeNameExpression | variableType + rankSpecifier | variableType + ToElement(STAR); variableType.ComputeResult = node => { var type = ToTypeReference((IConvertibleToType) node.Children[0].Result); if (node.Children.Count > 1) { var specifier = node.Children[1].Result as ArrayTypeRankSpecifier; if (specifier != null) { type = new ArrayTypeReference(type, specifier); } else { type = new PointerTypeReference(type) { PointerToken = (AstToken) node.Children[1].Result }; } } return type; }; // Types are recognized as expressions to prevent a conflict in the grammar. // TODO: also support array and pointer types. variableDeclaration.Rule = variableType + variableDeclaratorList; variableDeclaration.ComputeResult = node => { var result = new VariableDeclarationStatement(); result.VariableType = ToTypeReference((IConvertibleToType)node.Children[0].Result); foreach (var subNode in node.Children[1].GetAllListAstNodes()) { if (subNode is AstToken) result.AddChild(AstNodeTitles.ElementSeparator, subNode); else result.Declarators.Add((VariableDeclarator) subNode); } return result; }; statementList.Rule = statement | statementList + statement; #endregion #region Root compilation unit var usingNamespaceDirective = new GrammarDefinition("UsingNamespaceDirective", rule: ToElement(USING) + namespaceOrTypeExpression + ToElement(SEMICOLON), createNode: node => { var result = new UsingNamespaceDirective(); result.UsingKeyword = (AstToken) node.Children[0].Result; result.NamespaceIdentifier = ((IConvertibleToIdentifier) node.Children[1].Result).ToIdentifier(); result.AddChild(AstNodeTitles.Semicolon, node.Children[2].Result); return result; }); var usingAliasDirective = new GrammarDefinition("UsingAliasDirective", rule: ToElement(USING) + ToElement(IDENTIFIER) + ToElement(EQUALS) + typeReference + ToElement(SEMICOLON), createNode: node => { var result = new UsingAliasDirective { UsingKeyword = (AstToken) node.Children[0].Result, AliasIdentifier = ToIdentifier(node.Children[1].Result), OperatorToken = (AstToken) node.Children[2].Result, TypeImport = (TypeReference) node.Children[3].Result }; result.AddChild(AstNodeTitles.Semicolon, node.Children[4].Result); return result; }); var usingDirective = new GrammarDefinition("UsingNamespaceDirective", rule: usingNamespaceDirective | usingAliasDirective); var usingDirectiveList = new GrammarDefinition("UsingDirectiveList"); usingDirectiveList.Rule = usingDirective | usingDirectiveList + usingDirective; usingDirectiveListOptional.Rule = null | usingDirectiveList; var compilationUnit = new GrammarDefinition("CompilationUnit", rule: usingDirectiveListOptional + typeOrNamespaceDeclarationListOptional, createNode: node => { var result = new CompilationUnit(); if (node.Children[0].HasChildren) { result.UsingDirectives.AddRange(node.Children[0].Children[0].GetAllListAstNodes<UsingDirective>()); } if (node.Children[1].HasChildren) { foreach (var subNode in node.Children[1].Children[0].GetAllListAstNodes()) { var typeDecl = subNode as TypeDeclaration; if (typeDecl == null) result.Namespaces.Add((NamespaceDeclaration) subNode); else result.Types.Add(typeDecl); } } return result; }); #endregion RootDefinitions.Add(DefaultRoot = compilationUnit); RootDefinitions.Add(MemberDeclarationRule = memberDeclaration); RootDefinitions.Add(StatementRule = statement); }
bool HandleAnonymousMethod(ObjectCreateExpression objectCreateExpression, Expression target, MethodReference methodRef) { // Anonymous methods are defined in the same assembly, so there's no need to Resolve(). MethodDefinition method = methodRef as MethodDefinition; if (method == null || !method.Name.StartsWith("<", StringComparison.Ordinal)) return false; if (!(method.IsCompilerGenerated() || IsPotentialClosure(method.DeclaringType))) return false; // Decompile the anonymous method: DecompilerContext subContext = context.Clone(); subContext.CurrentMethod = method; BlockStatement body = AstMethodBodyBuilder.CreateMethodBody(method, subContext); TransformationPipeline.RunTransformationsUntil(body, v => v is DelegateConstruction, subContext); body.AcceptVisitor(this, null); AnonymousMethodExpression ame = new AnonymousMethodExpression(); bool isLambda = false; if (method.Parameters.All(p => string.IsNullOrEmpty(p.Name))) { ame.HasParameterList = false; } else { ame.HasParameterList = true; ame.Parameters.AddRange(AstBuilder.MakeParameters(method.Parameters)); if (ame.Parameters.All(p => p.ParameterModifier == ParameterModifier.None)) { isLambda = (body.Statements.Count == 1 && body.Statements.Single() is ReturnStatement); } } // Replace all occurrences of 'this' in the method body with the delegate's target: foreach (AstNode node in body.Descendants) { if (node is ThisReferenceExpression) node.ReplaceWith(target.Clone()); } if (isLambda) { LambdaExpression lambda = new LambdaExpression(); ame.Parameters.MoveTo(lambda.Parameters); Expression returnExpr = ((ReturnStatement)body.Statements.Single()).Expression; returnExpr.Remove(); lambda.Body = returnExpr; objectCreateExpression.ReplaceWith(lambda); } else { ame.Body = body; objectCreateExpression.ReplaceWith(ame); } return true; }
public virtual void VisitAnonymousMethodExpression (AnonymousMethodExpression anonymousMethodExpression) { VisitChildren (anonymousMethodExpression); }
public override object VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression, object data) { foreach (ParameterDeclarationExpression p in anonymousMethodExpression.Parameters) { AddVariable(p.TypeReference, p.ParameterName, anonymousMethodExpression.StartLocation, anonymousMethodExpression.EndLocation, false, false, null, null); } return base.VisitAnonymousMethodExpression(anonymousMethodExpression, data); }
/// <summary> /// Reads an anonymous method from the code. /// </summary> /// <param name="unsafeCode">Indicates whether the code being parsed resides in an unsafe code block.</param> /// <returns>Returns the expression.</returns> private AnonymousMethodExpression GetAnonymousMethodExpression(bool unsafeCode) { Param.Ignore(unsafeCode); // Get the delegate keyword. Node<CsToken> firstTokenNode = this.tokens.InsertLast(this.GetToken(CsTokenType.Delegate, SymbolType.Delegate)); // Check whether the next symbol is an opening parenthesis. Symbol symbol = this.GetNextSymbol(); ICollection<Parameter> parameters = null; if (symbol.SymbolType == SymbolType.OpenParenthesis) { parameters = this.ParseAnonymousMethodParameterList(unsafeCode); } // Create the anonymous method object now. AnonymousMethodExpression anonymousMethod = new AnonymousMethodExpression(); // The next symbol must be an opening curly bracket. Bracket openingBracket = this.GetBracketToken(CsTokenType.OpenCurlyBracket, SymbolType.OpenCurlyBracket); Node<CsToken> openingBracketNode = this.tokens.InsertLast(openingBracket); // Read the child statements. Node<CsToken> closingBracketNode = this.ParseStatementScope(anonymousMethod, unsafeCode); if (closingBracketNode == null) { // If we failed to get a closing bracket back, then there is a syntax // error in the document since there is an opening bracket with no matching // closing bracket. throw this.CreateSyntaxException(); } openingBracket.MatchingBracketNode = closingBracketNode; ((Bracket)closingBracketNode.Value).MatchingBracketNode = openingBracketNode; // Create the token list for the anonymous method expression. anonymousMethod.Tokens = new CsTokenList(this.tokens, firstTokenNode, this.tokens.Last); // Get the item's argument list if necessary. if (parameters != null && parameters.Count > 0) { anonymousMethod.AddParameters(parameters); } // Add a variable for each of the parameters. if (anonymousMethod.Parameters != null && anonymousMethod.Parameters.Count > 0) { // Add a variable for each of the parameters. foreach (Parameter parameter in anonymousMethod.Parameters) { anonymousMethod.Variables.Add(new Variable( parameter.Type, parameter.Name, VariableModifiers.None, parameter.Location.StartPoint)); } } // Return the expression. return anonymousMethod; }
/// <summary> /// Checks that parenthesis are used correctly within an anonymous method. /// </summary> /// <param name="element">The parent element.</param> /// <param name="expression">The expression to check.</param> private void CheckAnonymousMethodParenthesis(Element element, AnonymousMethodExpression expression) { Param.AssertNotNull(element, "element"); Param.AssertNotNull(expression, "expression"); if (expression.ParameterList == null || expression.ParameterList.Count == 0) { // Check for parenthesis. for (Token token = expression.FindFirstChildToken(); token != null; token = token.FindNextSiblingToken()) { if (token.TokenType == TokenType.OpenCurlyBracket) { break; } else if (token.TokenType == TokenType.OpenParenthesis) { this.AddViolation(element, token.LineNumber, Rules.RemoveDelegateParenthesisWhenPossible); break; } } } }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression a) { base.VisitAnonymousMethodExpression(a); // Replace properties. a.Body.AcceptVisitor(new FindPropertiesVisitor { Algorithm = Algorithm, ParameterContextName = ParameterContextName }); }
public LambdaBlock(IEmitter emitter, AnonymousMethodExpression anonymousMethodExpression) : this(emitter, anonymousMethodExpression.Parameters, anonymousMethodExpression.Body, anonymousMethodExpression, anonymousMethodExpression.IsAsync) { }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { if (!anonymousMethodExpression.Body.IsNull) { EnforceBraceStyle(policy.AnonymousMethodBraceStyle, anonymousMethodExpression.Body.LBraceToken, anonymousMethodExpression.Body.RBraceToken); } base.VisitAnonymousMethodExpression(anonymousMethodExpression); }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { VisitNestedFunction(anonymousMethodExpression, anonymousMethodExpression.Body); }
private void Format_Anonymous_Method_Expression(StringBuilder sb, AnonymousMethodExpression expression) { sb.Append("delegate"); List<string> parameters = new List<string>(); foreach (IAstNode child in expression.ChildNodes) { if (child is ParameterDeclaration) { parameters.Add(FormatterUtility.FormatParameter((ParameterDeclaration)child, document, controller)); } } if (parameters.Count > 0) { sb.Append("("); sb.Append(string.Join(", ", parameters.ToArray())); sb.Append(")"); } indentLevel++; sb.Append(ProcessStatement(expression.BlockStatement).TrimEnd(Environment.NewLine.ToCharArray())); indentLevel--; }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { if (!anonymousMethodExpression.Body.IsNull) { if (anonymousMethodExpression.Body.LBraceToken.GetNextNode () != anonymousMethodExpression.Body.RBraceToken) { EnforceBraceStyle(policy.AnonymousMethodBraceStyle, anonymousMethodExpression.Body.LBraceToken, anonymousMethodExpression.Body.RBraceToken); } VisitBlockWithoutFixingBraces(anonymousMethodExpression.Body, policy.IndentBlocks); return; } base.VisitAnonymousMethodExpression(anonymousMethodExpression); }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { foreach (var param in anonymousMethodExpression.Parameters) { var result = context.Resolve(param); var local = result as LocalResolveResult; anonymousParameters.Add(local.Variable); } base.VisitAnonymousMethodExpression(anonymousMethodExpression); foreach (var param in anonymousMethodExpression.Parameters) { var result = context.Resolve(param); var local = result as LocalResolveResult; anonymousParameters.Remove(local.Variable); } }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { base.VisitAnonymousMethodExpression(anonymousMethodExpression); AnalyzeExpression(anonymousMethodExpression, anonymousMethodExpression.Body, anonymousMethodExpression.Parameters); }
public override void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { this.LambdaExpression.Add(anonymousMethodExpression); base.VisitAnonymousMethodExpression(anonymousMethodExpression); }
public void VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression) { StartNode(anonymousMethodExpression); if (anonymousMethodExpression.IsAsync) { WriteKeyword(AnonymousMethodExpression.AsyncModifierRole); Space(); } WriteKeyword(AnonymousMethodExpression.DelegateKeywordRole); if (anonymousMethodExpression.HasParameterList) { Space(policy.SpaceBeforeMethodDeclarationParentheses); WriteCommaSeparatedListInParenthesis(anonymousMethodExpression.Parameters, policy.SpaceWithinMethodDeclarationParentheses); } anonymousMethodExpression.Body.AcceptVisitor(this); EndNode(anonymousMethodExpression); }
public StringBuilder VisitAnonymousMethodExpression(AnonymousMethodExpression anonymousMethodExpression, int data) { throw new SLSharpException("SL# does not understand anonymous methods."); }