From 381a37ec3a906541029584b8c52df842790c0c87 Mon Sep 17 00:00:00 2001 From: AlekseyTs Date: Fri, 9 Oct 2015 16:07:29 -0700 Subject: [PATCH] Give non-empty names to copy parameters of anonymous methods. It is unexpected to have parameters originated from source having empty names in correct programs. Fixes #4527. --- .../Portable/Symbols/Source/LambdaSymbol.cs | 2 +- .../Symbols/Synthesized/GeneratedNames.cs | 5 +++ .../FlowAnalysis/RegionAnalysisTests.cs | 4 +- .../Test/Semantic/Semantics/LambdaTests.cs | 41 +++++++++++++++++++ 4 files changed, 49 insertions(+), 3 deletions(-) diff --git a/src/Compilers/CSharp/Portable/Symbols/Source/LambdaSymbol.cs b/src/Compilers/CSharp/Portable/Symbols/Source/LambdaSymbol.cs index 0509cc7d969..265a029ce55 100644 --- a/src/Compilers/CSharp/Portable/Symbols/Source/LambdaSymbol.cs +++ b/src/Compilers/CSharp/Portable/Symbols/Source/LambdaSymbol.cs @@ -346,7 +346,7 @@ private static ParameterSymbol CopyParameter(ParameterSymbol parameter, MethodSy parameter.Type, parameter.Ordinal, parameter.RefKind, - string.Empty); // Make sure nothing binds to this. + GeneratedNames.LambdaCopyParameterName(parameter)); // Make sure nothing binds to this. } public sealed override bool Equals(object symbol) diff --git a/src/Compilers/CSharp/Portable/Symbols/Synthesized/GeneratedNames.cs b/src/Compilers/CSharp/Portable/Symbols/Synthesized/GeneratedNames.cs index 6ebc7dda6b1..889c280173d 100644 --- a/src/Compilers/CSharp/Portable/Symbols/Synthesized/GeneratedNames.cs +++ b/src/Compilers/CSharp/Portable/Symbols/Synthesized/GeneratedNames.cs @@ -460,5 +460,10 @@ internal static string ReusableHoistedLocalFieldName(int number) Debug.Assert((char)GeneratedNameKind.ReusableHoistedLocalField == '7'); return "<>7__wrap" + StringExtensions.GetNumeral(number); } + + internal static string LambdaCopyParameterName(ParameterSymbol sourceParameter) + { + return "<" + sourceParameter.Name + ">"; + } } } diff --git a/src/Compilers/CSharp/Test/Semantic/FlowAnalysis/RegionAnalysisTests.cs b/src/Compilers/CSharp/Test/Semantic/FlowAnalysis/RegionAnalysisTests.cs index ebe20974aa4..f8be1209342 100644 --- a/src/Compilers/CSharp/Test/Semantic/FlowAnalysis/RegionAnalysisTests.cs +++ b/src/Compilers/CSharp/Test/Semantic/FlowAnalysis/RegionAnalysisTests.cs @@ -1593,7 +1593,7 @@ public static void Main() Assert.Null(GetSymbolNamesJoined(analysis.AlwaysAssigned)); Assert.Equal("p", GetSymbolNamesJoined(analysis.Captured)); Assert.Equal("i", GetSymbolNamesJoined(analysis.UnsafeAddressTaken)); - Assert.Equal("", GetSymbolNamesJoined(analysis.VariablesDeclared)); + Assert.Equal("

", GetSymbolNamesJoined(analysis.VariablesDeclared)); Assert.Equal("p", GetSymbolNamesJoined(analysis.DataFlowsIn)); Assert.Null(GetSymbolNamesJoined(analysis.DataFlowsOut)); @@ -1601,7 +1601,7 @@ public static void Main() Assert.Equal("p", GetSymbolNamesJoined(analysis.ReadInside)); Assert.Equal("i", GetSymbolNamesJoined(analysis.ReadOutside)); - Assert.Equal("", GetSymbolNamesJoined(analysis.WrittenInside)); + Assert.Equal("

", GetSymbolNamesJoined(analysis.WrittenInside)); Assert.Equal("i, p, d", GetSymbolNamesJoined(analysis.WrittenOutside)); } diff --git a/src/Compilers/CSharp/Test/Semantic/Semantics/LambdaTests.cs b/src/Compilers/CSharp/Test/Semantic/Semantics/LambdaTests.cs index d556466231a..d17764d5649 100644 --- a/src/Compilers/CSharp/Test/Semantic/Semantics/LambdaTests.cs +++ b/src/Compilers/CSharp/Test/Semantic/Semantics/LambdaTests.cs @@ -1396,5 +1396,46 @@ public interface IColumn { } var compilation = CreateCompilationWithMscorlib(source, new[] { SystemCoreRef, CSharpRef }, options: TestOptions.ReleaseExe); CompileAndVerify(compilation, expectedOutput: "Select"); } + + [Fact, WorkItem(4527, "https://github.com/dotnet/roslyn/issues/4527")] + public void AnonymousMethodExpressionWithoutParameterList() + { + var source = +@" +using System; +using System.Threading.Tasks; + +namespace RoslynAsyncDelegate +{ + class Program + { + static EventHandler MyEvent; + + static void Main(string[] args) + { + MyEvent += async delegate { await Task.Delay(0); }; + } + } +} + +"; + var compilation = CreateCompilationWithMscorlib45(source, options: TestOptions.DebugExe); + + var tree = compilation.SyntaxTrees[0]; + var model = compilation.GetSemanticModel(tree); + + var node1 = tree.GetRoot().DescendantNodes().Where(n => n.IsKind(SyntaxKind.AnonymousMethodExpression)).Single(); + + Assert.Equal("async delegate { await Task.Delay(0); }", node1.ToString()); + + Assert.Equal("void System.EventHandler.Invoke(System.Object sender, System.EventArgs e)", model.GetTypeInfo(node1).ConvertedType.GetMembers("Invoke").Single().ToTestDisplayString()); + + var lambdaParameters = ((MethodSymbol)(model.GetSymbolInfo(node1)).Symbol).Parameters; + + Assert.Equal("System.Object ", lambdaParameters[0].ToTestDisplayString()); + Assert.Equal("System.EventArgs ", lambdaParameters[1].ToTestDisplayString()); + + CompileAndVerify(compilation); + } } } -- GitLab