提交 db84e6e6 编写于 作者: A AlekseyTs

Remove explicit syntax reference to body from SourceMemberMethodSymbol.

上级 c5c551c0
......@@ -520,7 +520,7 @@ private BoundStatement BindLocalFunctionStatement(LocalFunctionStatementSyntax n
{
if (ImplicitReturnIsOkay(localSymbol))
{
block = FlowAnalysisPass.AppendImplicitReturn(block, localSymbol, node.Body);
block = FlowAnalysisPass.AppendImplicitReturn(block, localSymbol);
}
else
{
......
......@@ -129,7 +129,9 @@ private enum IndirectReturnState : byte
_boundBody = boundBody;
}
_methodBodySyntaxOpt = (method as SourceMemberMethodSymbol)?.BodySyntax;
var sourceMethod = method as SourceMemberMethodSymbol;
(BlockSyntax, ArrowExpressionClauseSyntax) bodies = sourceMethod?.Bodies ?? default;
_methodBodySyntaxOpt = (SyntaxNode)bodies.Item1 ?? bodies.Item2 ?? sourceMethod?.SyntaxNode;
}
private bool IsDebugPlus()
......
......@@ -1564,6 +1564,8 @@ private static BoundBlock BindMethodBody(MethodSymbol method, TypeCompilationSta
if ((object)sourceMethod != null)
{
var constructorSyntax = sourceMethod.SyntaxNode as ConstructorDeclarationSyntax;
(BlockSyntax, ArrowExpressionClauseSyntax) bodies = sourceMethod.Bodies;
var bodySyntax = (SyntaxNode)bodies.Item1 ?? bodies.Item2;
// Static constructor can't have any this/base call
if (method.MethodKind == MethodKind.StaticConstructor &&
......@@ -1577,7 +1579,7 @@ private static BoundBlock BindMethodBody(MethodSymbol method, TypeCompilationSta
if (sourceMethod.IsExtern)
{
if (sourceMethod.BodySyntax == null && constructorSyntax?.Initializer == null)
if (bodySyntax == null && constructorSyntax?.Initializer == null)
{
// Generate warnings only if we are not generating ERR_ExternHasBody or ERR_ExternHasConstructorInitializer errors
GenerateExternalMethodWarnings(sourceMethod, diagnostics);
......@@ -1595,8 +1597,6 @@ private static BoundBlock BindMethodBody(MethodSymbol method, TypeCompilationSta
var compilation = method.DeclaringCompilation;
var factory = compilation.GetBinderFactory(sourceMethod.SyntaxTree);
var bodySyntax = sourceMethod.BodySyntax;
if (bodySyntax != null)
{
var inMethodBinder = factory.GetBinder(bodySyntax);
......
......@@ -41,7 +41,7 @@ internal class FlowAnalysisPass
// we don't analyze synthesized void methods.
if ((method.IsImplicitlyDeclared && !method.IsScriptInitializer) || Analyze(compilation, method, block, diagnostics))
{
block = AppendImplicitReturn(block, method, (CSharpSyntaxNode)(method as SourceMemberMethodSymbol)?.BodySyntax, originalBodyNested);
block = AppendImplicitReturn(block, method, originalBodyNested);
}
}
else if (Analyze(compilation, method, block, diagnostics))
......@@ -80,7 +80,7 @@ internal class FlowAnalysisPass
return block;
}
private static BoundBlock AppendImplicitReturn(BoundBlock body, MethodSymbol method, CSharpSyntaxNode syntax, bool originalBodyNested)
private static BoundBlock AppendImplicitReturn(BoundBlock body, MethodSymbol method, bool originalBodyNested)
{
if (originalBodyNested)
{
......@@ -89,28 +89,25 @@ private static BoundBlock AppendImplicitReturn(BoundBlock body, MethodSymbol met
var builder = ArrayBuilder<BoundStatement>.GetInstance(n);
builder.AddRange(statements, n - 1);
builder.Add(AppendImplicitReturn((BoundBlock)statements[n - 1], method, syntax));
builder.Add(AppendImplicitReturn((BoundBlock)statements[n - 1], method));
return body.Update(body.Locals, ImmutableArray<LocalFunctionSymbol>.Empty, builder.ToImmutableAndFree());
}
else
{
return AppendImplicitReturn(body, method, syntax);
return AppendImplicitReturn(body, method);
}
}
// insert the implicit "return" statement at the end of the method body
// Normally, we wouldn't bother attaching syntax trees to compiler-generated nodes, but these
// ones are going to have sequence points.
internal static BoundBlock AppendImplicitReturn(BoundBlock body, MethodSymbol method, SyntaxNode syntax = null)
internal static BoundBlock AppendImplicitReturn(BoundBlock body, MethodSymbol method)
{
Debug.Assert(body != null);
Debug.Assert(method != null);
if (syntax == null)
{
syntax = body.Syntax;
}
SyntaxNode syntax = body.Syntax;
Debug.Assert(body.WasCompilerGenerated || syntax.IsKind(SyntaxKind.Block) || syntax.IsKind(SyntaxKind.ArrowExpressionClause));
......
......@@ -30,7 +30,6 @@ internal sealed class SynthesizedClosureMethod : SynthesizedMethodBaseSymbol, IS
DebugId lambdaId)
: base(containingType,
originalMethod,
null,
blockSyntax,
originalMethod.DeclaringSyntaxReferences[0].GetLocation(),
originalMethod is LocalFunctionSymbol
......
......@@ -644,7 +644,7 @@ private static bool BaseReferenceInReceiverWasRewritten(BoundExpression original
private sealed partial class BaseMethodWrapperSymbol : SynthesizedMethodBaseSymbol
{
internal BaseMethodWrapperSymbol(NamedTypeSymbol containingType, MethodSymbol methodBeingWrapped, SyntaxNode syntax, string name)
: base(containingType, methodBeingWrapped, syntax.SyntaxTree.GetReference(syntax), null, syntax.GetLocation(), name, DeclarationModifiers.Private)
: base(containingType, methodBeingWrapped, syntax.SyntaxTree.GetReference(syntax), syntax.GetLocation(), name, DeclarationModifiers.Private)
{
Debug.Assert(containingType.ContainingModule is SourceModuleSymbol);
Debug.Assert(ReferenceEquals(methodBeingWrapped, methodBeingWrapped.ConstructedFrom));
......
......@@ -24,11 +24,10 @@ internal abstract class SynthesizedMethodBaseSymbol : SourceMemberMethodSymbol
protected SynthesizedMethodBaseSymbol(NamedTypeSymbol containingType,
MethodSymbol baseMethod,
SyntaxReference syntaxReference,
SyntaxReference blockSyntaxReference,
Location location,
string name,
DeclarationModifiers declarationModifiers)
: base(containingType, syntaxReference, blockSyntaxReference, location)
: base(containingType, syntaxReference, location)
{
Debug.Assert((object)containingType != null);
Debug.Assert((object)baseMethod != null);
......
......@@ -30,7 +30,7 @@ internal sealed class SourceConstructorSymbol : SourceMemberMethodSymbol
ConstructorDeclarationSyntax syntax,
MethodKind methodKind,
DiagnosticBag diagnostics) :
base(containingType, syntax.GetReference(), syntax.Body?.GetReference() ?? syntax.ExpressionBody?.GetReference(), ImmutableArray.Create(location))
base(containingType, syntax.GetReference(), ImmutableArray.Create(location))
{
bool modifierErrors;
var declarationModifiers = this.MakeModifiers(syntax.Modifiers, methodKind, location, diagnostics, out modifierErrors);
......@@ -66,7 +66,7 @@ internal sealed class SourceConstructorSymbol : SourceMemberMethodSymbol
if (!modifierErrors)
{
this.CheckModifiers(methodKind, location, diagnostics);
this.CheckModifiers(methodKind, hasBlockBody || _isExpressionBodied, location, diagnostics);
}
CheckForBlockAndExpressionBody(
......@@ -213,9 +213,9 @@ private DeclarationModifiers MakeModifiers(SyntaxTokenList modifiers, MethodKind
return mods;
}
private void CheckModifiers(MethodKind methodKind, Location location, DiagnosticBag diagnostics)
private void CheckModifiers(MethodKind methodKind, bool hasBody, Location location, DiagnosticBag diagnostics)
{
if (bodySyntaxReferenceOpt == null && !IsExtern)
if (!hasBody && !IsExtern)
{
diagnostics.Add(ErrorCode.ERR_ConcreteMissingBody, location, this);
}
......@@ -273,17 +273,19 @@ internal override int CalculateLocalSyntaxOffset(int position, SyntaxTree tree)
TextSpan span;
// local/lambda/closure defined within the body of the constructor:
if (tree == bodySyntaxReferenceOpt?.SyntaxTree)
ConstructorDeclarationSyntax ctorSyntax = GetSyntax();
if (tree == ctorSyntax.SyntaxTree)
{
span = bodySyntaxReferenceOpt.Span;
if (span.Contains(position))
if (ctorSyntax.Body?.Span.Contains(position) == true)
{
return position - ctorSyntax.Body.Span.Start;
}
else if (ctorSyntax.ExpressionBody?.Span.Contains(position) == true)
{
return position - span.Start;
return position - ctorSyntax.ExpressionBody.Span.Start;
}
}
var ctorSyntax = GetSyntax();
// closure in ctor initializer lifting its parameter(s) spans the constructor declaration:
if (position == ctorSyntax.SpanStart)
{
......
......@@ -29,7 +29,6 @@ internal sealed class SourceCustomEventAccessorSymbol : SourceEventAccessorSymbo
DiagnosticBag diagnostics)
: base(@event,
syntax.GetReference(),
((SyntaxNode)syntax.Body ?? syntax.ExpressionBody)?.GetReference(),
ImmutableArray.Create(syntax.Keyword.GetLocation()))
{
Debug.Assert(syntax != null);
......
......@@ -24,7 +24,7 @@ internal abstract class SourceDelegateMethodSymbol : SourceMemberMethodSymbol
DelegateDeclarationSyntax syntax,
MethodKind methodKind,
DeclarationModifiers declarationModifiers)
: base(delegateType, syntax.GetReference(), bodySyntaxReferenceOpt: null, location: syntax.Identifier.GetLocation())
: base(delegateType, syntax.GetReference(), location: syntax.Identifier.GetLocation())
{
_returnType = returnType;
this.MakeFlags(methodKind, declarationModifiers, _returnType.SpecialType == SpecialType.System_Void, isExtensionMethod: false);
......
......@@ -16,7 +16,7 @@ internal sealed class SourceDestructorSymbol : SourceMemberMethodSymbol
SourceMemberContainerTypeSymbol containingType,
DestructorDeclarationSyntax syntax,
DiagnosticBag diagnostics) :
base(containingType, syntax.GetReference(), syntax.Body?.GetReference() ?? syntax.ExpressionBody?.GetReference() , syntax.Identifier.GetLocation())
base(containingType, syntax.GetReference(), syntax.Identifier.GetLocation())
{
const MethodKind methodKind = MethodKind.Destructor;
Location location = this.Locations[0];
......@@ -41,7 +41,7 @@ internal sealed class SourceDestructorSymbol : SourceMemberMethodSymbol
}
}
if (!modifierErrors && bodySyntaxReferenceOpt == null && !IsExtern)
if (!modifierErrors && !hasBlockBody && !_isExpressionBodied && !IsExtern)
{
diagnostics.Add(ErrorCode.ERR_ConcreteMissingBody, location, this);
}
......
......@@ -22,9 +22,8 @@ internal abstract class SourceEventAccessorSymbol : SourceMemberMethodSymbol
public SourceEventAccessorSymbol(
SourceEventSymbol @event,
SyntaxReference syntaxReference,
SyntaxReference blockSyntaxReference,
ImmutableArray<Location> locations)
: base(@event.containingType, syntaxReference, blockSyntaxReference, locations)
: base(@event.containingType, syntaxReference, locations)
{
_event = @event;
}
......
......@@ -169,9 +169,6 @@ public void EnsureMetadataVirtual()
// some symbols may not have a syntax (e.g. lambdas, synthesized event accessors)
protected readonly SyntaxReference syntaxReferenceOpt;
// some symbols may not have a body syntax (e.g. abstract and extern members, primary constructors, synthesized event accessors, etc.)
protected readonly SyntaxReference bodySyntaxReferenceOpt;
protected ImmutableArray<Location> locations;
protected string lazyDocComment;
......@@ -191,19 +188,18 @@ internal ImmutableArray<Diagnostic> SetDiagnostics(ImmutableArray<Diagnostic> ne
return _cachedDiagnostics;
}
protected SourceMemberMethodSymbol(NamedTypeSymbol containingType, SyntaxReference syntaxReferenceOpt, SyntaxReference bodySyntaxReferenceOpt, Location location)
: this(containingType, syntaxReferenceOpt, bodySyntaxReferenceOpt, ImmutableArray.Create(location))
protected SourceMemberMethodSymbol(NamedTypeSymbol containingType, SyntaxReference syntaxReferenceOpt, Location location)
: this(containingType, syntaxReferenceOpt, ImmutableArray.Create(location))
{
}
protected SourceMemberMethodSymbol(NamedTypeSymbol containingType, SyntaxReference syntaxReferenceOpt, SyntaxReference bodySyntaxReferenceOpt, ImmutableArray<Location> locations)
protected SourceMemberMethodSymbol(NamedTypeSymbol containingType, SyntaxReference syntaxReferenceOpt, ImmutableArray<Location> locations)
{
Debug.Assert((object)containingType != null);
Debug.Assert(!locations.IsEmpty);
_containingType = containingType;
this.syntaxReferenceOpt = syntaxReferenceOpt;
this.bodySyntaxReferenceOpt = bodySyntaxReferenceOpt;
this.locations = locations;
}
......@@ -537,11 +533,31 @@ internal sealed override Cci.CallingConvention CallingConvention
#region Syntax
internal SyntaxNode BodySyntax
internal (BlockSyntax, ArrowExpressionClauseSyntax) Bodies
{
get
{
return (this.bodySyntaxReferenceOpt == null) ? null : this.bodySyntaxReferenceOpt.GetSyntax();
switch (SyntaxNode)
{
case BaseMethodDeclarationSyntax method:
return (method.Body, method.ExpressionBody);
case AccessorDeclarationSyntax accessor:
return (accessor.Body, accessor.ExpressionBody);
case ArrowExpressionClauseSyntax arrowExpression:
Debug.Assert(arrowExpression.Parent.Kind() == SyntaxKind.PropertyDeclaration ||
arrowExpression.Parent.Kind() == SyntaxKind.IndexerDeclaration ||
this is SynthesizedClosureMethod);
return (null, arrowExpression);
case BlockSyntax block:
Debug.Assert(this is SynthesizedClosureMethod);
return (block, null);
default:
return (null, null);
}
}
}
......@@ -1594,14 +1610,28 @@ protected void CheckModifiersForBody(Location location, DiagnosticBag diagnostic
internal override int CalculateLocalSyntaxOffset(int localPosition, SyntaxTree localTree)
{
// Method without body doesn't declare locals.
Debug.Assert(this.BodySyntax != null);
Debug.Assert(this.BodySyntax.SyntaxTree == localTree);
Debug.Assert(this.SyntaxNode.SyntaxTree == localTree);
(BlockSyntax, ArrowExpressionClauseSyntax) bodies = Bodies;
CSharpSyntaxNode bodySyntax = null;
// All locals are declared within the body of the method.
Debug.Assert(this.BodySyntax.Span.Contains(localPosition));
if (bodies.Item1?.Span.Contains(localPosition) == true)
{
bodySyntax = bodies.Item1;
}
else if (bodies.Item2?.Span.Contains(localPosition) == true)
{
bodySyntax = bodies.Item2;
}
else
{
// Method without body doesn't declare locals.
Debug.Assert(bodySyntax != null);
return -1;
}
return localPosition - this.BodySyntax.SpanStart;
return localPosition - bodySyntax.SpanStart;
}
}
}
......@@ -72,8 +72,6 @@ internal sealed class SourceOrdinaryMethodSymbol : SourceMemberMethodSymbol
DiagnosticBag diagnostics) :
base(containingType,
syntax.GetReference(),
// Prefer a block body if both exist
syntax.Body?.GetReference() ?? syntax.ExpressionBody?.GetReference(),
location)
{
_name = name;
......@@ -367,7 +365,7 @@ private void MethodChecks(MethodDeclarationSyntax syntax, Binder withTypeParamsB
}
}
CheckModifiers(location, diagnostics);
CheckModifiers((syntax.Body ?? (SyntaxNode)syntax.ExpressionBody) != null, location, diagnostics);
}
// This is also used for async lambdas. Probably not the best place to locate this method, but where else could it go?
......@@ -590,8 +588,9 @@ internal bool IsPartialDefinition
{
get
{
MethodDeclarationSyntax declaration;
return this.IsPartial
&& this.BodySyntax == null;
&& (declaration = GetSyntax()).Body == null && declaration.ExpressionBody == null;
}
}
......@@ -602,8 +601,9 @@ internal bool IsPartialImplementation
{
get
{
MethodDeclarationSyntax declaration;
return this.IsPartial
&& this.BodySyntax != null;
&& ((declaration = GetSyntax()).Body ?? (SyntaxNode)declaration.ExpressionBody) != null;
}
}
......@@ -866,7 +866,7 @@ private ImmutableArray<TypeParameterSymbol> MakeTypeParameters(MethodDeclaration
return result.ToImmutableAndFree();
}
private void CheckModifiers(Location location, DiagnosticBag diagnostics)
private void CheckModifiers(bool hasBody, Location location, DiagnosticBag diagnostics)
{
const DeclarationModifiers partialMethodInvalidModifierMask = (DeclarationModifiers.AccessibilityMask & ~DeclarationModifiers.Private) |
DeclarationModifiers.Virtual |
......@@ -945,11 +945,11 @@ private void CheckModifiers(Location location, DiagnosticBag diagnostics)
// '{0}' is a new virtual member in sealed class '{1}'
diagnostics.Add(ErrorCode.ERR_NewVirtualInSealed, location, this, ContainingType);
}
else if (bodySyntaxReferenceOpt == null && IsAsync)
else if (!hasBody && IsAsync)
{
diagnostics.Add(ErrorCode.ERR_BadAsyncLacksBody, location);
}
else if (bodySyntaxReferenceOpt == null && !IsExtern && !IsAbstract && !IsPartial && !IsExpressionBodied)
else if (!hasBody && !IsExtern && !IsAbstract && !IsPartial && !IsExpressionBodied)
{
diagnostics.Add(ErrorCode.ERR_ConcreteMissingBody, location, this);
}
......
......@@ -144,7 +144,7 @@ internal override bool IsExpressionBodied
Location location,
ArrowExpressionClauseSyntax syntax,
DiagnosticBag diagnostics) :
base(containingType, syntax.GetReference(), syntax.GetReference(), location)
base(containingType, syntax.GetReference(), location)
{
_property = property;
_explicitInterfaceImplementations = explicitInterfaceImplementations;
......@@ -169,7 +169,7 @@ internal override bool IsExpressionBodied
diagnostics.Add(info, location);
}
this.CheckModifiers(location, isAutoPropertyOrExpressionBodied: true, diagnostics: diagnostics);
this.CheckModifiers(location, hasBody: true, isAutoPropertyOrExpressionBodied: true, diagnostics: diagnostics);
if (this.IsOverride)
{
......@@ -197,7 +197,6 @@ internal override bool IsExpressionBodied
DiagnosticBag diagnostics)
: base(containingType,
syntax.GetReference(),
((SyntaxNode)syntax.Body ?? syntax.ExpressionBody)?.GetReference(),
location)
{
_property = property;
......@@ -239,7 +238,7 @@ internal override bool IsExpressionBodied
if (!modifierErrors)
{
this.CheckModifiers(location, isAutoPropertyAccessor, diagnostics);
this.CheckModifiers(location, hasBody || hasExpressionBody, isAutoPropertyAccessor, diagnostics);
}
if (this.IsOverride)
......@@ -435,7 +434,7 @@ private DeclarationModifiers MakeModifiers(AccessorDeclarationSyntax syntax, Loc
return mods;
}
private void CheckModifiers(Location location, bool isAutoPropertyOrExpressionBodied, DiagnosticBag diagnostics)
private void CheckModifiers(Location location, bool hasBody, bool isAutoPropertyOrExpressionBodied, DiagnosticBag diagnostics)
{
// Check accessibility against the accessibility declared on the accessor not the property.
var localAccessibility = this.LocalAccessibility;
......@@ -450,7 +449,7 @@ private void CheckModifiers(Location location, bool isAutoPropertyOrExpressionBo
// '{0}' is a new virtual member in sealed class '{1}'
diagnostics.Add(ErrorCode.ERR_NewVirtualInSealed, location, this, ContainingType);
}
else if (bodySyntaxReferenceOpt == null && !IsExtern && !IsAbstract && !isAutoPropertyOrExpressionBodied)
else if (!hasBody && !IsExtern && !IsAbstract && !isAutoPropertyOrExpressionBodied)
{
diagnostics.Add(ErrorCode.ERR_ConcreteMissingBody, location, this);
}
......
......@@ -23,8 +23,7 @@ internal sealed class SourceUserDefinedConversionSymbol : SourceUserDefinedOpera
: WellKnownMemberNames.ExplicitConversionName;
return new SourceUserDefinedConversionSymbol(
containingType, name, location, syntax, diagnostics,
syntax.Body == null && syntax.ExpressionBody != null);
containingType, name, location, syntax, diagnostics);
}
// NOTE: no need to call WithUnsafeRegionIfNecessary, since the signature
......@@ -35,18 +34,14 @@ internal sealed class SourceUserDefinedConversionSymbol : SourceUserDefinedOpera
string name,
Location location,
ConversionOperatorDeclarationSyntax syntax,
DiagnosticBag diagnostics,
bool isExpressionBodied) :
DiagnosticBag diagnostics) :
base(
MethodKind.Conversion,
name,
containingType,
location,
syntax.GetReference(),
syntax.Body?.GetReference() ?? syntax.ExpressionBody?.GetReference(),
syntax.Modifiers,
diagnostics,
isExpressionBodied)
syntax,
diagnostics)
{
CheckForBlockAndExpressionBody(
syntax.Body, syntax.ExpressionBody, syntax, diagnostics);
......
......@@ -37,11 +37,8 @@ internal sealed class SourceUserDefinedOperatorSymbol : SourceUserDefinedOperato
name,
containingType,
location,
syntax.GetReference(),
syntax.Body?.GetReference() ?? syntax.ExpressionBody?.GetReference(),
syntax.Modifiers,
diagnostics,
isExpressionBodied)
syntax,
diagnostics)
{
CheckForBlockAndExpressionBody(
syntax.Body, syntax.ExpressionBody, syntax, diagnostics);
......
......@@ -23,15 +23,12 @@ internal abstract class SourceUserDefinedOperatorSymbolBase : SourceMemberMethod
string name,
SourceMemberContainerTypeSymbol containingType,
Location location,
SyntaxReference syntaxReference,
SyntaxReference bodySyntaxReference,
SyntaxTokenList modifiersSyntax,
DiagnosticBag diagnostics,
bool isExpressionBodied) :
base(containingType, syntaxReference, bodySyntaxReference, location)
BaseMethodDeclarationSyntax syntax,
DiagnosticBag diagnostics) :
base(containingType, syntax.GetReference(), location)
{
_name = name;
_isExpressionBodied = isExpressionBodied;
_isExpressionBodied = syntax.Body == null && syntax.ExpressionBody != null;
var defaultAccess = DeclarationModifiers.Private;
var allowedModifiers =
......@@ -42,7 +39,7 @@ internal abstract class SourceUserDefinedOperatorSymbolBase : SourceMemberMethod
bool modifierErrors;
var declarationModifiers = ModifierUtils.MakeAndCheckNontypeMemberModifiers(
modifiersSyntax, defaultAccess, allowedModifiers, location, diagnostics, out modifierErrors);
syntax.Modifiers, defaultAccess, allowedModifiers, location, diagnostics, out modifierErrors);
this.CheckUnsafeModifier(declarationModifiers, diagnostics);
......@@ -80,11 +77,12 @@ internal abstract class SourceUserDefinedOperatorSymbolBase : SourceMemberMethod
// SPEC: its operator body consists of a semicolon. For expression-bodied
// SPEC: operators, the body is an expression. For all other operators,
// SPEC: the operator body consists of a block...
if (bodySyntaxReference != null && IsExtern)
bool hasBody = (syntax.Body ?? (SyntaxNode)syntax.ExpressionBody) != null;
if (hasBody && IsExtern)
{
diagnostics.Add(ErrorCode.ERR_ExternHasBody, location, this);
}
else if (bodySyntaxReference == null && !IsExtern && !IsAbstract && !IsPartial)
else if (!hasBody && !IsExtern && !IsAbstract && !IsPartial)
{
// Do not report that the body is missing if the operator is marked as
// partial or abstract; we will already have given an error for that so
......
......@@ -24,7 +24,7 @@ internal sealed class SynthesizedFieldLikeEventAccessorSymbol : SourceEventAcces
private readonly string _name;
internal SynthesizedFieldLikeEventAccessorSymbol(SourceFieldLikeEventSymbol @event, bool isAdder)
: base(@event, null, null, @event.Locations)
: base(@event, null, @event.Locations)
{
this.MakeFlags(
isAdder ? MethodKind.EventAdd : MethodKind.EventRemove,
......
......@@ -61,36 +61,6 @@ public void TestAllErrors(string code, params string[] errors)
AssertEx.SetEqual(errors, diagnostics.Select(DumpDiagnostic));
}
// Tests just the errors found while binding method M in class C.
[Obsolete("Use VerifyDiagnostics", true)]
public void TestErrors(string code, params string[] errors)
{
var compilation = CreateStandardCompilation(code);
var method = (SourceMemberMethodSymbol)compilation.GlobalNamespace.GetTypeMembers("C").Single().GetMembers("M").Single();
var factory = compilation.GetBinderFactory(method.SyntaxTree);
var bodyBlock = (BlockSyntax)method.BodySyntax;
var parameterBinderContext = factory.GetBinder(bodyBlock);
var binder = new ExecutableCodeBinder(bodyBlock.Parent, method, parameterBinderContext);
var diagnostics = new DiagnosticBag();
var block = binder.BindEmbeddedBlock(bodyBlock, diagnostics);
AssertEx.SetEqual(errors, diagnostics.AsEnumerable().Select(DumpDiagnostic));
}
[Obsolete("Use VerifyDiagnostics", true)]
public void TestWarnings(string code, params string[] expectedWarnings)
{
var compilation = CreateStandardCompilation(code);
var method = (SourceMemberMethodSymbol)compilation.GlobalNamespace.GetTypeMembers("C").Single().GetMembers("M").Single();
var factory = compilation.GetBinderFactory(method.SyntaxTree);
var bodyBlock = (BlockSyntax)method.BodySyntax;
var parameterBinderContext = factory.GetBinder(bodyBlock);
var binder = new ExecutableCodeBinder(bodyBlock.Parent, method, parameterBinderContext);
var block = binder.BindEmbeddedBlock(bodyBlock, new DiagnosticBag());
var actualWarnings = new DiagnosticBag();
DiagnosticsPass.IssueDiagnostics(compilation, block, actualWarnings, method);
AssertEx.SetEqual(expectedWarnings, actualWarnings.AsEnumerable().Select(DumpDiagnostic));
}
public const string LINQ =
#region the string LINQ defines a complete LINQ API called List1<T> (for instance method) and List2<T> (for extension methods)
@"using System;
......
......@@ -20,7 +20,8 @@ internal static ImmutableArray<SyntaxNode> GetDeclarators(SourceMemberMethodSymb
{
var builder = ArrayBuilder<SyntaxNode>.GetInstance();
var visitor = new LocalVariableDeclaratorsCollector(builder);
visitor.Visit(method.BodySyntax);
var bodies = method.Bodies;
visitor.Visit(bodies.Item1 ?? (SyntaxNode)bodies.Item2);
return builder.ToImmutableAndFree();
}
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册