| File: Debugging\CSharpProximityExpressionsService.RelevantExpressionsCollector.cs | Web Access |
| Project: src\roslyn\src\Features\CSharp\Portable\Microsoft.CodeAnalysis.CSharp.Features.csproj (Microsoft.CodeAnalysis.CSharp.Features) |
// Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. // See the LICENSE file in the project root for more information. #nullable disable using System.Collections.Generic; using Microsoft.CodeAnalysis.CSharp.Syntax; using Roslyn.Utilities; namespace Microsoft.CodeAnalysis.CSharp.Debugging; internal sealed partial class CSharpProximityExpressionsService { private sealed class RelevantExpressionsCollector(bool includeDeclarations, IList<string> expressions) : CSharpSyntaxVisitor { private readonly bool _includeDeclarations = includeDeclarations; private readonly IList<string> _expressions = expressions; public override void VisitLabeledStatement(LabeledStatementSyntax node) => AddRelevantExpressions(node.Statement, _expressions, _includeDeclarations); public override void VisitExpressionStatement(ExpressionStatementSyntax node) => AddExpressionTerms(node.Expression, _expressions); public override void VisitReturnStatement(ReturnStatementSyntax node) => AddExpressionTerms(node.Expression, _expressions); public override void VisitThrowStatement(ThrowStatementSyntax node) => AddExpressionTerms(node.Expression, _expressions); public override void VisitLocalDeclarationStatement(LocalDeclarationStatementSyntax node) { // Here, we collect expression expressions from any/all initialization expressions AddVariableExpressions(node.Declaration.Variables, _expressions); } public override void VisitDoStatement(DoStatementSyntax node) => AddExpressionTerms(node.Condition, _expressions); public override void VisitLockStatement(LockStatementSyntax node) => AddExpressionTerms(node.Expression, _expressions); public override void VisitWhileStatement(WhileStatementSyntax node) => AddExpressionTerms(node.Condition, _expressions); public override void VisitIfStatement(IfStatementSyntax node) => AddExpressionTerms(node.Condition, _expressions); public override void VisitForStatement(ForStatementSyntax node) { if (node.Declaration != null) { AddVariableExpressions(node.Declaration.Variables, _expressions); } node.Initializers.Do(i => AddExpressionTerms(i, _expressions)); AddExpressionTerms(node.Condition, _expressions); node.Incrementors.Do(i => AddExpressionTerms(i, _expressions)); } public override void VisitForEachStatement(ForEachStatementSyntax node) { _expressions.Add(node.Identifier.ValueText); AddExpressionTerms(node.Expression, _expressions); } public override void VisitForEachVariableStatement(ForEachVariableStatementSyntax node) { AddVariableExpressions(node.Variable, _expressions); AddExpressionTerms(node.Expression, _expressions); } public override void VisitUsingStatement(UsingStatementSyntax node) { if (node.Declaration != null) { AddVariableExpressions(node.Declaration.Variables, _expressions); } AddExpressionTerms(node.Expression, _expressions); } public override void VisitSwitchStatement(SwitchStatementSyntax node) => AddExpressionTerms(node.Expression, _expressions); private void AddVariableExpressions( SeparatedSyntaxList<VariableDeclaratorSyntax> declarators, IList<string> expressions) { foreach (var declarator in declarators) { if (_includeDeclarations) { expressions.Add(declarator.Identifier.ValueText); } if (declarator.Initializer != null) { AddExpressionTerms(declarator.Initializer.Value, expressions); } } } private void AddVariableExpressions( ExpressionSyntax component, IList<string> expressions) { if (!_includeDeclarations) return; switch (component.Kind()) { case SyntaxKind.TupleExpression: { var t = (TupleExpressionSyntax)component; foreach (var a in t.Arguments) { AddVariableExpressions(a.Expression, expressions); } break; } case SyntaxKind.DeclarationExpression: { var t = (DeclarationExpressionSyntax)component; AddVariableExpressions(t.Designation, expressions); break; } } } private void AddVariableExpressions( VariableDesignationSyntax component, IList<string> expressions) { if (!_includeDeclarations) return; switch (component.Kind()) { case SyntaxKind.ParenthesizedVariableDesignation: { var t = (ParenthesizedVariableDesignationSyntax)component; foreach (var v in t.Variables) AddVariableExpressions(v, expressions); break; } case SyntaxKind.SingleVariableDesignation: { var t = (SingleVariableDesignationSyntax)component; expressions.Add(t.Identifier.ValueText); break; } } } } }