提交 def58aa2 编写于 作者: M Manish Vasani

Add IOperation APIs for nameof and throw expressions

Fixes https://github.com/dotnet/roslyn/issues/19954 and https://github.com/dotnet/roslyn/issues/20125
上级 d2f94230
......@@ -107,6 +107,10 @@ private IOperation CreateInternal(BoundNode boundNode)
return CreateBoundArrayAccessOperation((BoundArrayAccess)boundNode);
case BoundKind.PointerIndirectionOperator:
return CreateBoundPointerIndirectionOperatorOperation((BoundPointerIndirectionOperator)boundNode);
case BoundKind.NameOfOperator:
return CreateBoundNameOfOperatorOperation((BoundNameOfOperator)boundNode);
case BoundKind.ThrowExpression:
return CreateBoundThrowExpressionOperation((BoundThrowExpression)boundNode);
case BoundKind.AddressOfOperator:
return CreateBoundAddressOfOperatorOperation((BoundAddressOfOperator)boundNode);
case BoundKind.ImplicitReceiver:
......@@ -704,6 +708,26 @@ private IPointerIndirectionReferenceExpression CreateBoundPointerIndirectionOper
return new LazyPointerIndirectionReferenceExpression(pointer, isInvalid, syntax, type, constantValue);
}
private INameOfExpression CreateBoundNameOfOperatorOperation(BoundNameOfOperator boundNameOfOperator)
{
Lazy<IOperation> argument = new Lazy<IOperation>(() => Create(boundNameOfOperator.Argument));
bool isInvalid = boundNameOfOperator.HasErrors;
SyntaxNode syntax = boundNameOfOperator.Syntax;
ITypeSymbol type = boundNameOfOperator.Type;
Optional<object> constantValue = ConvertToOptional(boundNameOfOperator.ConstantValue);
return new LazyNameOfExpression(argument, isInvalid, syntax, type, constantValue);
}
private IThrowExpression CreateBoundThrowExpressionOperation(BoundThrowExpression boundThrowExpression)
{
Lazy<IOperation> expression = new Lazy<IOperation>(() => Create(boundThrowExpression.Expression));
bool isInvalid = boundThrowExpression.HasErrors;
SyntaxNode syntax = boundThrowExpression.Syntax;
ITypeSymbol type = boundThrowExpression.Type;
Optional<object> constantValue = ConvertToOptional(boundThrowExpression.ConstantValue);
return new LazyThrowExpression(expression, isInvalid, syntax, type, constantValue);
}
private IAddressOfExpression CreateBoundAddressOfOperatorOperation(BoundAddressOfOperator boundAddressOfOperator)
{
Lazy<IOperation> reference = new Lazy<IOperation>(() => Create(boundAddressOfOperator.Operand));
......
......@@ -305,8 +305,8 @@ static void Main(string[] args)
Initializer: INullCoalescingExpression (OperationKind.NullCoalescingExpression, Type: System.Object) (Syntax: 'new object( ... Exception()')
Left: IObjectCreationExpression (Constructor: System.Object..ctor()) (OperationKind.ObjectCreationExpression, Type: System.Object) (Syntax: 'new object()')
Right: IConversionExpression (ConversionKind.CSharp, Implicit) (OperationKind.ConversionExpression, Type: System.Object) (Syntax: 'throw new Exception()')
IOperation: (OperationKind.None) (Syntax: 'throw new Exception()')
Children(1): IObjectCreationExpression (Constructor: System.Exception..ctor()) (OperationKind.ObjectCreationExpression, Type: System.Exception) (Syntax: 'new Exception()')
IThrowExpression (OperationKind.ThrowExpression, Type: null) (Syntax: 'throw new Exception()')
IObjectCreationExpression (Constructor: System.Exception..ctor()) (OperationKind.ObjectCreationExpression, Type: System.Exception) (Syntax: 'new Exception()')
";
var expectedDiagnostics = DiagnosticDescription.None;
......
......@@ -336,14 +336,41 @@ public string M(int x)
}
";
string expectedOperationTree = @"
IOperation: (OperationKind.None, Constant: ""x"") (Syntax: 'nameof(x)')
Children(1): IParameterReferenceExpression: x (OperationKind.ParameterReferenceExpression, Type: System.Int32) (Syntax: 'x')
INameOfExpression (OperationKind.NameOfExpression, Type: System.String, Constant: ""x"") (Syntax: 'nameof(x)')
IParameterReferenceExpression: x (OperationKind.ParameterReferenceExpression, Type: System.Int32) (Syntax: 'x')
";
var expectedDiagnostics = DiagnosticDescription.None;
VerifyOperationTreeAndDiagnosticsForTest<InvocationExpressionSyntax>(source, expectedOperationTree, expectedDiagnostics);
}
[Fact, WorkItem(8884, "https://github.com/dotnet/roslyn/issues/8884")]
public void ParameterReference_NameOfExpression_ErrorCase()
{
string source = @"
class Class1
{
public string M(int x, int y)
{
return /*<bind>*/nameof(x + y)/*</bind>*/;
}
}
";
string expectedOperationTree = @"
INameOfExpression (OperationKind.NameOfExpression, Type: System.String, Constant: """") (Syntax: 'nameof(x + y)')
IBinaryOperatorExpression (BinaryOperationKind.IntegerAdd) (OperationKind.BinaryOperatorExpression, Type: System.Int32) (Syntax: 'x + y')
Left: IParameterReferenceExpression: x (OperationKind.ParameterReferenceExpression, Type: System.Int32) (Syntax: 'x')
Right: IParameterReferenceExpression: y (OperationKind.ParameterReferenceExpression, Type: System.Int32) (Syntax: 'y')
";
var expectedDiagnostics = new DiagnosticDescription[] {
// CS8081: Expression does not have a name.
// return /*<bind>*/nameof(x + y)/*</bind>*/;
Diagnostic(ErrorCode.ERR_ExpressionHasNoName, "x + y").WithLocation(6, 33)
};
VerifyOperationTreeAndDiagnosticsForTest<InvocationExpressionSyntax>(source, expectedOperationTree, expectedDiagnostics);
}
[Fact, WorkItem(8884, "https://github.com/dotnet/roslyn/issues/8884")]
public void ParameterReference_PointerIndirectionExpression()
{
......@@ -637,17 +664,46 @@ public void M(string x)
}
";
string expectedOperationTree = @"
IOperation: (OperationKind.None) (Syntax: 'throw new A ... (nameof(x))')
Children(1): IObjectCreationExpression (Constructor: System.ArgumentNullException..ctor(System.String paramName)) (OperationKind.ObjectCreationExpression, Type: System.ArgumentNullException) (Syntax: 'new Argumen ... (nameof(x))')
Arguments(1): IArgument (ArgumentKind.Explicit, Matching Parameter: paramName) (OperationKind.Argument) (Syntax: 'nameof(x)')
IOperation: (OperationKind.None, Constant: ""x"") (Syntax: 'nameof(x)')
Children(1): IParameterReferenceExpression: x (OperationKind.ParameterReferenceExpression, Type: System.String) (Syntax: 'x')
IThrowExpression (OperationKind.ThrowExpression, Type: null) (Syntax: 'throw new A ... (nameof(x))')
IObjectCreationExpression (Constructor: System.ArgumentNullException..ctor(System.String paramName)) (OperationKind.ObjectCreationExpression, Type: System.ArgumentNullException) (Syntax: 'new Argumen ... (nameof(x))')
Arguments(1): IArgument (ArgumentKind.Explicit, Matching Parameter: paramName) (OperationKind.Argument) (Syntax: 'nameof(x)')
INameOfExpression (OperationKind.NameOfExpression, Type: System.String, Constant: ""x"") (Syntax: 'nameof(x)')
IParameterReferenceExpression: x (OperationKind.ParameterReferenceExpression, Type: System.String) (Syntax: 'x')
";
var expectedDiagnostics = DiagnosticDescription.None;
VerifyOperationTreeAndDiagnosticsForTest<ThrowExpressionSyntax>(source, expectedOperationTree, expectedDiagnostics);
}
[Fact, WorkItem(8884, "https://github.com/dotnet/roslyn/issues/8884")]
public void ParameterReference_ThrowExpression_ErrorCase()
{
string source = @"
using System;
internal class Class
{
public void M(string x, string y)
{
var z = x ?? /*<bind>*/throw x + y/*</bind>*/;
}
}
";
string expectedOperationTree = @"
IThrowExpression (OperationKind.ThrowExpression, Type: null, IsInvalid) (Syntax: 'throw x + y')
IBinaryOperatorExpression (BinaryOperationKind.StringConcatenate) (OperationKind.BinaryOperatorExpression, Type: System.String) (Syntax: 'x + y')
Left: IParameterReferenceExpression: x (OperationKind.ParameterReferenceExpression, Type: System.String) (Syntax: 'x')
Right: IParameterReferenceExpression: y (OperationKind.ParameterReferenceExpression, Type: System.String) (Syntax: 'y')
";
var expectedDiagnostics = new DiagnosticDescription[] {
// CS0155: The type caught or thrown must be derived from System.Exception
// var z = x ?? /*<bind>*/throw x + y/*</bind>*/;
Diagnostic(ErrorCode.ERR_BadExceptionType, "x + y").WithLocation(8, 38)
};
VerifyOperationTreeAndDiagnosticsForTest<ThrowExpressionSyntax>(source, expectedOperationTree, expectedDiagnostics);
}
[Fact, WorkItem(8884, "https://github.com/dotnet/roslyn/issues/8884")]
public void ParameterReference_PatternSwitchStatement()
{
......
......@@ -42,6 +42,8 @@
<Compile Include="Operations\BranchKind.cs" />
<Compile Include="Operations\CaseKind.cs" />
<Compile Include="Operations\ConversionKind.cs" />
<Compile Include="Operations\IThrowExpression.cs" />
<Compile Include="Operations\INameOfExpression.cs" />
<Compile Include="Operations\IAddressOfExpression.cs" />
<Compile Include="Operations\IArgument.cs" />
<Compile Include="Operations\IArrayCreationExpression.cs" />
......
......@@ -60,6 +60,114 @@ public LazyAddressOfExpression(Lazy<IOperation> reference, bool isInvalid, Synta
public override IOperation Reference => _lazyReference.Value;
}
/// <summary>
/// Represents C# nameof and VB NameOf expression.
/// </summary>
internal abstract partial class BaseNameOfExpression : Operation, INameOfExpression
{
protected BaseNameOfExpression(bool isInvalid, SyntaxNode syntax, ITypeSymbol type, Optional<object> constantValue) :
base(OperationKind.NameOfExpression, isInvalid, syntax, type, constantValue)
{
}
/// <summary>
/// Argument to name of expression.
/// </summary>
public abstract IOperation Argument { get; }
public override void Accept(OperationVisitor visitor)
{
visitor.VisitNameOfExpression(this);
}
public override TResult Accept<TArgument, TResult>(OperationVisitor<TArgument, TResult> visitor, TArgument argument)
{
return visitor.VisitNameOfExpression(this, argument);
}
}
/// <summary>
/// Represents C# nameof and VB NameOf expression.
/// </summary>
internal sealed partial class NameOfExpression : BaseNameOfExpression, INameOfExpression
{
public NameOfExpression(IOperation argument, bool isInvalid, SyntaxNode syntax, ITypeSymbol type, Optional<object> constantValue) :
base(isInvalid, syntax, type, constantValue)
{
Argument = argument;
}
/// <summary>
/// Argument to name of expression.
/// </summary>
public override IOperation Argument { get; }
}
/// <summary>
/// Represents C# nameof and VB NameOf expression.
/// </summary>
internal sealed partial class LazyNameOfExpression : BaseNameOfExpression, INameOfExpression
{
private readonly Lazy<IOperation> _lazyArgument;
public LazyNameOfExpression(Lazy<IOperation> argument, bool isInvalid, SyntaxNode syntax, ITypeSymbol type, Optional<object> constantValue) : base(isInvalid, syntax, type, constantValue)
{
_lazyArgument = argument ?? throw new System.ArgumentNullException(nameof(argument));
}
/// <summary>
/// Argument to name of expression.
/// </summary>
public override IOperation Argument => _lazyArgument.Value;
}
/// <summary>
/// Represents C# throw expression.
/// </summary>
internal abstract partial class BaseThrowExpression : Operation, IThrowExpression
{
protected BaseThrowExpression(bool isInvalid, SyntaxNode syntax, ITypeSymbol type, Optional<object> constantValue) :
base(OperationKind.ThrowExpression, isInvalid, syntax, type, constantValue)
{
}
/// <summary>
/// Expression.
/// </summary>
public abstract IOperation Expression { get; }
public override void Accept(OperationVisitor visitor)
{
visitor.VisitThrowExpression(this);
}
public override TResult Accept<TArgument, TResult>(OperationVisitor<TArgument, TResult> visitor, TArgument argument)
{
return visitor.VisitThrowExpression(this, argument);
}
}
/// <summary>
/// Represents C# throw expression.
/// </summary>
internal sealed partial class ThrowExpression : BaseThrowExpression, IThrowExpression
{
public ThrowExpression(IOperation expression, bool isInvalid, SyntaxNode syntax, ITypeSymbol type, Optional<object> constantValue) :
base(isInvalid, syntax, type, constantValue)
{
Expression = expression;
}
/// <summary>
/// Expression.
/// </summary>
public override IOperation Expression { get; }
}
/// <summary>
/// Represents C# throw expression.
/// </summary>
internal sealed partial class LazyThrowExpression : BaseThrowExpression, IThrowExpression
{
private readonly Lazy<IOperation> _lazyExpression;
public LazyThrowExpression(Lazy<IOperation> expression, bool isInvalid, SyntaxNode syntax, ITypeSymbol type, Optional<object> constantValue) : base(isInvalid, syntax, type, constantValue)
{
_lazyExpression = expression ?? throw new System.ArgumentNullException(nameof(expression));
}
/// <summary>
/// Expression.
/// </summary>
public override IOperation Expression => _lazyExpression.Value;
}
/// <summary>
/// Represents an argument in a method invocation.
/// </summary>
......
// Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Collections.Immutable;
namespace Microsoft.CodeAnalysis.Semantics
{
/// <summary>
/// Represents C# nameof and VB NameOf expression.
/// </summary>
/// <remarks>
/// This interface is reserved for implementation by its associated APIs. We reserve the right to
/// change it in the future.
/// </remarks>
public interface INameOfExpression : IOperation
{
/// <summary>
/// Argument to name of expression.
/// </summary>
IOperation Argument { get; }
}
}
// Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Collections.Immutable;
namespace Microsoft.CodeAnalysis.Semantics
{
/// <summary>
/// Represents C# throw expression.
/// </summary>
/// <remarks>
/// This interface is reserved for implementation by its associated APIs. We reserve the right to
/// change it in the future.
/// </remarks>
public interface IThrowExpression : IOperation
{
/// <summary>
/// Expression.
/// </summary>
IOperation Expression { get; }
}
}
......@@ -128,6 +128,8 @@ public enum OperationKind
InterpolatedStringExpression = 0x11e,
/// <summary>Indicates an <see cref="IAnonymousObjectCreationExpression"/>.</summary>
AnonymousObjectCreationExpression = 0x11f,
/// <summary>Indicates an <see cref="INameOfExpression"/>.</summary>
NameOfExpression = 0x123,
// Expressions that occur only in C#.
......@@ -145,7 +147,9 @@ public enum OperationKind
IsPatternExpression = 0x205,
/// <summary>Indicates an <see cref="IIncrementExpression"/>.</summary>
IncrementExpression = 0x206,
/// <summary>Indicates an <see cref="IThrowExpression"/>.</summary>
ThrowExpression = 0x207,
// Expressions that occur only in Visual Basic.
/// <summary>Indicates an <see cref="IOmittedArgumentExpression"/>.</summary>
......
......@@ -300,6 +300,16 @@ public virtual void VisitAwaitExpression(IAwaitExpression operation)
DefaultVisit(operation);
}
public virtual void VisitNameOfExpression(INameOfExpression operation)
{
DefaultVisit(operation);
}
public virtual void VisitThrowExpression(IThrowExpression operation)
{
DefaultVisit(operation);
}
public virtual void VisitAddressOfExpression(IAddressOfExpression operation)
{
DefaultVisit(operation);
......@@ -730,6 +740,16 @@ public virtual TResult VisitAwaitExpression(IAwaitExpression operation, TArgumen
return DefaultVisit(operation, argument);
}
public virtual TResult VisitNameOfExpression(INameOfExpression operation, TArgument argument)
{
return DefaultVisit(operation, argument);
}
public virtual TResult VisitThrowExpression(IThrowExpression operation, TArgument argument)
{
return DefaultVisit(operation, argument);
}
public virtual TResult VisitAddressOfExpression(IAddressOfExpression operation, TArgument argument)
{
return DefaultVisit(operation, argument);
......
......@@ -337,6 +337,16 @@ public override void VisitAwaitExpression(IAwaitExpression operation)
Visit(operation.AwaitedValue);
}
public override void VisitNameOfExpression(INameOfExpression operation)
{
Visit(operation.Argument);
}
public override void VisitThrowExpression(IThrowExpression operation)
{
Visit(operation.Expression);
}
public override void VisitAddressOfExpression(IAddressOfExpression operation)
{
Visit(operation.Reference);
......
......@@ -99,6 +99,7 @@ Microsoft.CodeAnalysis.OperationKind.LocalReferenceExpression = 261 -> Microsoft
Microsoft.CodeAnalysis.OperationKind.LockStatement = 13 -> Microsoft.CodeAnalysis.OperationKind
Microsoft.CodeAnalysis.OperationKind.LoopStatement = 6 -> Microsoft.CodeAnalysis.OperationKind
Microsoft.CodeAnalysis.OperationKind.MethodBindingExpression = 265 -> Microsoft.CodeAnalysis.OperationKind
Microsoft.CodeAnalysis.OperationKind.NameOfExpression = 291 -> Microsoft.CodeAnalysis.OperationKind
Microsoft.CodeAnalysis.OperationKind.None = 0 -> Microsoft.CodeAnalysis.OperationKind
Microsoft.CodeAnalysis.OperationKind.NullCoalescingExpression = 272 -> Microsoft.CodeAnalysis.OperationKind
Microsoft.CodeAnalysis.OperationKind.ObjectCreationExpression = 274 -> Microsoft.CodeAnalysis.OperationKind
......@@ -122,6 +123,7 @@ Microsoft.CodeAnalysis.OperationKind.StopStatement = 80 -> Microsoft.CodeAnalysi
Microsoft.CodeAnalysis.OperationKind.SwitchCase = 1033 -> Microsoft.CodeAnalysis.OperationKind
Microsoft.CodeAnalysis.OperationKind.SwitchStatement = 4 -> Microsoft.CodeAnalysis.OperationKind
Microsoft.CodeAnalysis.OperationKind.SyntheticLocalReferenceExpression = 263 -> Microsoft.CodeAnalysis.OperationKind
Microsoft.CodeAnalysis.OperationKind.ThrowExpression = 519 -> Microsoft.CodeAnalysis.OperationKind
Microsoft.CodeAnalysis.OperationKind.ThrowStatement = 10 -> Microsoft.CodeAnalysis.OperationKind
Microsoft.CodeAnalysis.OperationKind.TryStatement = 14 -> Microsoft.CodeAnalysis.OperationKind
Microsoft.CodeAnalysis.OperationKind.TypeOfExpression = 513 -> Microsoft.CodeAnalysis.OperationKind
......@@ -326,8 +328,8 @@ Microsoft.CodeAnalysis.Semantics.ConversionKind
Microsoft.CodeAnalysis.Semantics.ConversionKind.Basic = 3 -> Microsoft.CodeAnalysis.Semantics.ConversionKind
Microsoft.CodeAnalysis.Semantics.ConversionKind.CSharp = 4 -> Microsoft.CodeAnalysis.Semantics.ConversionKind
Microsoft.CodeAnalysis.Semantics.ConversionKind.Cast = 1 -> Microsoft.CodeAnalysis.Semantics.ConversionKind
Microsoft.CodeAnalysis.Semantics.ConversionKind.Invalid = 15 -> Microsoft.CodeAnalysis.Semantics.ConversionKind
Microsoft.CodeAnalysis.Semantics.ConversionKind.InterpolatedString = 6 -> Microsoft.CodeAnalysis.Semantics.ConversionKind
Microsoft.CodeAnalysis.Semantics.ConversionKind.Invalid = 15 -> Microsoft.CodeAnalysis.Semantics.ConversionKind
Microsoft.CodeAnalysis.Semantics.ConversionKind.None = 0 -> Microsoft.CodeAnalysis.Semantics.ConversionKind
Microsoft.CodeAnalysis.Semantics.ConversionKind.OperatorMethod = 5 -> Microsoft.CodeAnalysis.Semantics.ConversionKind
Microsoft.CodeAnalysis.Semantics.ConversionKind.TryCast = 2 -> Microsoft.CodeAnalysis.Semantics.ConversionKind
......@@ -483,6 +485,8 @@ Microsoft.CodeAnalysis.Semantics.IMemberReferenceExpression.Member.get -> Micros
Microsoft.CodeAnalysis.Semantics.IMethodBindingExpression
Microsoft.CodeAnalysis.Semantics.IMethodBindingExpression.IsVirtual.get -> bool
Microsoft.CodeAnalysis.Semantics.IMethodBindingExpression.Method.get -> Microsoft.CodeAnalysis.IMethodSymbol
Microsoft.CodeAnalysis.Semantics.INameOfExpression
Microsoft.CodeAnalysis.Semantics.INameOfExpression.Argument.get -> Microsoft.CodeAnalysis.IOperation
Microsoft.CodeAnalysis.Semantics.INullCoalescingExpression
Microsoft.CodeAnalysis.Semantics.INullCoalescingExpression.PrimaryOperand.get -> Microsoft.CodeAnalysis.IOperation
Microsoft.CodeAnalysis.Semantics.INullCoalescingExpression.SecondaryOperand.get -> Microsoft.CodeAnalysis.IOperation
......@@ -533,6 +537,8 @@ Microsoft.CodeAnalysis.Semantics.ISymbolInitializer.Value.get -> Microsoft.CodeA
Microsoft.CodeAnalysis.Semantics.ISyntheticLocalReferenceExpression
Microsoft.CodeAnalysis.Semantics.ISyntheticLocalReferenceExpression.ContainingStatement.get -> Microsoft.CodeAnalysis.IOperation
Microsoft.CodeAnalysis.Semantics.ISyntheticLocalReferenceExpression.SyntheticLocalKind.get -> Microsoft.CodeAnalysis.Semantics.SyntheticLocalKind
Microsoft.CodeAnalysis.Semantics.IThrowExpression
Microsoft.CodeAnalysis.Semantics.IThrowExpression.Expression.get -> Microsoft.CodeAnalysis.IOperation
Microsoft.CodeAnalysis.Semantics.IThrowStatement
Microsoft.CodeAnalysis.Semantics.IThrowStatement.ThrownObject.get -> Microsoft.CodeAnalysis.IOperation
Microsoft.CodeAnalysis.Semantics.ITryStatement
......@@ -761,6 +767,7 @@ override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitLocalFunctionStat
override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitLocalReferenceExpression(Microsoft.CodeAnalysis.Semantics.ILocalReferenceExpression operation) -> void
override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitLockStatement(Microsoft.CodeAnalysis.Semantics.ILockStatement operation) -> void
override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitMethodBindingExpression(Microsoft.CodeAnalysis.Semantics.IMethodBindingExpression operation) -> void
override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitNameOfExpression(Microsoft.CodeAnalysis.Semantics.INameOfExpression operation) -> void
override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitNullCoalescingExpression(Microsoft.CodeAnalysis.Semantics.INullCoalescingExpression operation) -> void
override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitObjectCreationExpression(Microsoft.CodeAnalysis.Semantics.IObjectCreationExpression operation) -> void
override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitOmittedArgumentExpression(Microsoft.CodeAnalysis.Semantics.IOmittedArgumentExpression operation) -> void
......@@ -782,6 +789,7 @@ override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitStopStatement(Mic
override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitSwitchCase(Microsoft.CodeAnalysis.Semantics.ISwitchCase operation) -> void
override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitSwitchStatement(Microsoft.CodeAnalysis.Semantics.ISwitchStatement operation) -> void
override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitSyntheticLocalReferenceExpression(Microsoft.CodeAnalysis.Semantics.ISyntheticLocalReferenceExpression operation) -> void
override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitThrowExpression(Microsoft.CodeAnalysis.Semantics.IThrowExpression operation) -> void
override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitThrowStatement(Microsoft.CodeAnalysis.Semantics.IThrowStatement operation) -> void
override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitTryStatement(Microsoft.CodeAnalysis.Semantics.ITryStatement operation) -> void
override Microsoft.CodeAnalysis.Semantics.OperationWalker.VisitTypeOfExpression(Microsoft.CodeAnalysis.Semantics.ITypeOfExpression operation) -> void
......@@ -866,6 +874,7 @@ virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitLocalFunctionStat
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitLocalReferenceExpression(Microsoft.CodeAnalysis.Semantics.ILocalReferenceExpression operation) -> void
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitLockStatement(Microsoft.CodeAnalysis.Semantics.ILockStatement operation) -> void
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitMethodBindingExpression(Microsoft.CodeAnalysis.Semantics.IMethodBindingExpression operation) -> void
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitNameOfExpression(Microsoft.CodeAnalysis.Semantics.INameOfExpression operation) -> void
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitNullCoalescingExpression(Microsoft.CodeAnalysis.Semantics.INullCoalescingExpression operation) -> void
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitObjectCreationExpression(Microsoft.CodeAnalysis.Semantics.IObjectCreationExpression operation) -> void
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitOmittedArgumentExpression(Microsoft.CodeAnalysis.Semantics.IOmittedArgumentExpression operation) -> void
......@@ -887,6 +896,7 @@ virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitStopStatement(Mic
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitSwitchCase(Microsoft.CodeAnalysis.Semantics.ISwitchCase operation) -> void
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitSwitchStatement(Microsoft.CodeAnalysis.Semantics.ISwitchStatement operation) -> void
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitSyntheticLocalReferenceExpression(Microsoft.CodeAnalysis.Semantics.ISyntheticLocalReferenceExpression operation) -> void
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitThrowExpression(Microsoft.CodeAnalysis.Semantics.IThrowExpression operation) -> void
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitThrowStatement(Microsoft.CodeAnalysis.Semantics.IThrowStatement operation) -> void
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitTryStatement(Microsoft.CodeAnalysis.Semantics.ITryStatement operation) -> void
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor.VisitTypeOfExpression(Microsoft.CodeAnalysis.Semantics.ITypeOfExpression operation) -> void
......@@ -948,6 +958,7 @@ virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.Vi
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.VisitLocalReferenceExpression(Microsoft.CodeAnalysis.Semantics.ILocalReferenceExpression operation, TArgument argument) -> TResult
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.VisitLockStatement(Microsoft.CodeAnalysis.Semantics.ILockStatement operation, TArgument argument) -> TResult
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.VisitMethodBindingExpression(Microsoft.CodeAnalysis.Semantics.IMethodBindingExpression operation, TArgument argument) -> TResult
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.VisitNameOfExpression(Microsoft.CodeAnalysis.Semantics.INameOfExpression operation, TArgument argument) -> TResult
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.VisitNullCoalescingExpression(Microsoft.CodeAnalysis.Semantics.INullCoalescingExpression operation, TArgument argument) -> TResult
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.VisitObjectCreationExpression(Microsoft.CodeAnalysis.Semantics.IObjectCreationExpression operation, TArgument argument) -> TResult
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.VisitOmittedArgumentExpression(Microsoft.CodeAnalysis.Semantics.IOmittedArgumentExpression operation, TArgument argument) -> TResult
......@@ -969,6 +980,7 @@ virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.Vi
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.VisitSwitchCase(Microsoft.CodeAnalysis.Semantics.ISwitchCase operation, TArgument argument) -> TResult
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.VisitSwitchStatement(Microsoft.CodeAnalysis.Semantics.ISwitchStatement operation, TArgument argument) -> TResult
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.VisitSyntheticLocalReferenceExpression(Microsoft.CodeAnalysis.Semantics.ISyntheticLocalReferenceExpression operation, TArgument argument) -> TResult
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.VisitThrowExpression(Microsoft.CodeAnalysis.Semantics.IThrowExpression operation, TArgument argument) -> TResult
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.VisitThrowStatement(Microsoft.CodeAnalysis.Semantics.IThrowStatement operation, TArgument argument) -> TResult
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.VisitTryStatement(Microsoft.CodeAnalysis.Semantics.ITryStatement operation, TArgument argument) -> TResult
virtual Microsoft.CodeAnalysis.Semantics.OperationVisitor<TArgument, TResult>.VisitTypeOfExpression(Microsoft.CodeAnalysis.Semantics.ITypeOfExpression operation, TArgument argument) -> TResult
......
' Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
' Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
Imports System.Collections.Concurrent
Imports System.Collections.Immutable
......@@ -33,6 +33,8 @@ Namespace Microsoft.CodeAnalysis.Semantics
Return CreateBoundLiteralOperation(DirectCast(boundNode, BoundLiteral))
Case BoundKind.AwaitOperator
Return CreateBoundAwaitOperatorOperation(DirectCast(boundNode, BoundAwaitOperator))
Case BoundKind.NameOfOperator
Return CreateBoundNameOfOperatorOperation(DirectCast(boundNode, BoundNameOfOperator))
Case BoundKind.Lambda
Return CreateBoundLambdaOperation(DirectCast(boundNode, BoundLambda))
Case BoundKind.Call
......@@ -263,6 +265,15 @@ Namespace Microsoft.CodeAnalysis.Semantics
Return New LazyAwaitExpression(awaitedValue, isInvalid, syntax, type, constantValue)
End Function
Private Function CreateBoundNameOfOperatorOperation(boundNameOfOperator As BoundNameOfOperator) As INameOfExpression
Dim argument As Lazy(Of IOperation) = New Lazy(Of IOperation)(Function() Create(boundNameOfOperator.Argument))
Dim isInvalid As Boolean = boundNameOfOperator.HasErrors
Dim syntax As SyntaxNode = boundNameOfOperator.Syntax
Dim type As ITypeSymbol = boundNameOfOperator.Type
Dim constantValue As [Optional](Of Object) = ConvertToOptional(boundNameOfOperator.ConstantValueOpt)
Return New LazyNameOfExpression(argument, isInvalid, syntax, type, constantValue)
End Function
Private Function CreateBoundLambdaOperation(boundLambda As BoundLambda) As ILambdaExpression
Dim signature As IMethodSymbol = boundLambda.LambdaSymbol
Dim body As Lazy(Of IBlockStatement) = New Lazy(Of IBlockStatement)(Function() DirectCast(Create(boundLambda.Body), IBlockStatement))
......
......@@ -378,8 +378,8 @@ Class Class1
End Class]]>.Value
Dim expectedOperationTree = <![CDATA[
IOperation: (OperationKind.None, Constant: "x") (Syntax: 'NameOf(x)')
Children(1): IParameterReferenceExpression: x (OperationKind.ParameterReferenceExpression, Type: System.Int32) (Syntax: 'x')
INameOfExpression (OperationKind.NameOfExpression, Type: System.String, Constant: "x") (Syntax: 'NameOf(x)')
IParameterReferenceExpression: x (OperationKind.ParameterReferenceExpression, Type: System.Int32) (Syntax: 'x')
]]>.Value
Dim expectedDiagnostics = String.Empty
......@@ -387,6 +387,31 @@ IOperation: (OperationKind.None, Constant: "x") (Syntax: 'NameOf(x)')
VerifyOperationTreeAndDiagnosticsForTest(Of NameOfExpressionSyntax)(source, expectedOperationTree, expectedDiagnostics)
End Sub
<Fact, WorkItem(8884, "https://github.com/dotnet/roslyn/issues/8884")>
Public Sub ParameterReference_NameOfExpression_ErrorCase()
Dim source = <![CDATA[
Class Class1
Public Function M(x As Integer, y As Integer) As String
Return NameOf(x + y)'BIND:"NameOf(x + y)"
End Function
End Class]]>.Value
Dim expectedOperationTree = <![CDATA[
INameOfExpression (OperationKind.NameOfExpression, Type: System.String, Constant: null) (Syntax: 'NameOf(x + y)')
IBinaryOperatorExpression (BinaryOperationKind.IntegerAdd) (OperationKind.BinaryOperatorExpression, Type: System.Int32) (Syntax: 'x + y')
Left: IParameterReferenceExpression: x (OperationKind.ParameterReferenceExpression, Type: System.Int32) (Syntax: 'x')
Right: IParameterReferenceExpression: y (OperationKind.ParameterReferenceExpression, Type: System.Int32) (Syntax: 'y')
]]>.Value
Dim expectedDiagnostics = <![CDATA[
BC37244: This expression does not have a name.
Return NameOf(x + y)'BIND:"NameOf(x + y)"
~~~~~
]]>.Value
VerifyOperationTreeAndDiagnosticsForTest(Of NameOfExpressionSyntax)(source, expectedOperationTree, expectedDiagnostics)
End Sub
<Fact, WorkItem(8884, "https://github.com/dotnet/roslyn/issues/8884")>
Public Sub ParameterReference_LateBoundIndexerAccess()
Dim source = <![CDATA[
......
......@@ -859,6 +859,22 @@ public override void VisitAwaitExpression(IAwaitExpression operation)
base.VisitAwaitExpression(operation);
}
public override void VisitNameOfExpression(INameOfExpression operation)
{
LogString(nameof(INameOfExpression));
LogCommonPropertiesAndNewLine(operation);
Visit(operation.Argument);
}
public override void VisitThrowExpression(IThrowExpression operation)
{
LogString(nameof(IThrowExpression));
LogCommonPropertiesAndNewLine(operation);
Visit(operation.Expression);
}
public override void VisitAddressOfExpression(IAddressOfExpression operation)
{
LogString(nameof(IAddressOfExpression));
......
......@@ -404,6 +404,16 @@ public override void VisitAwaitExpression(IAwaitExpression operation)
base.VisitAwaitExpression(operation);
}
public override void VisitNameOfExpression(INameOfExpression operation)
{
base.VisitNameOfExpression(operation);
}
public override void VisitThrowExpression(IThrowExpression operation)
{
base.VisitThrowExpression(operation);
}
public override void VisitAddressOfExpression(IAddressOfExpression operation)
{
base.VisitAddressOfExpression(operation);
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册