Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/mono/linker.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/test
diff options
context:
space:
mode:
Diffstat (limited to 'test')
-rw-r--r--test/ILLink.RoslynAnalyzer.Tests/DataFlowTests.cs6
-rw-r--r--test/ILLink.RoslynAnalyzer.Tests/RequiresCapabilityTests.cs8
-rw-r--r--test/Mono.Linker.Tests.Cases/DataFlow/CompilerGeneratedCodeAccessedViaReflection.cs523
-rw-r--r--test/Mono.Linker.Tests.Cases/RequiresCapability/ReflectionAccessFromCompilerGeneratedCode.cs213
-rw-r--r--test/Mono.Linker.Tests.Cases/RequiresCapability/RequiresInCompilerGeneratedCode.cs136
-rw-r--r--test/Mono.Linker.Tests.Cases/RequiresCapability/RequiresOnClass.cs18
-rw-r--r--test/Mono.Linker.Tests.Cases/Warnings/WarningSuppression/SuppressWarningsInCompilerGeneratedCode.cs23
7 files changed, 898 insertions, 29 deletions
diff --git a/test/ILLink.RoslynAnalyzer.Tests/DataFlowTests.cs b/test/ILLink.RoslynAnalyzer.Tests/DataFlowTests.cs
index b92038a6a..5e7ccb3dd 100644
--- a/test/ILLink.RoslynAnalyzer.Tests/DataFlowTests.cs
+++ b/test/ILLink.RoslynAnalyzer.Tests/DataFlowTests.cs
@@ -71,6 +71,12 @@ namespace ILLink.RoslynAnalyzer.Tests
}
[Fact]
+ public Task CompilerGeneratedCodeAccessedViaReflection ()
+ {
+ return RunTest ();
+ }
+
+ [Fact]
public Task DynamicDependencyDataflow ()
{
return RunTest (nameof (DynamicDependencyDataflow));
diff --git a/test/ILLink.RoslynAnalyzer.Tests/RequiresCapabilityTests.cs b/test/ILLink.RoslynAnalyzer.Tests/RequiresCapabilityTests.cs
index 52873a9d0..ad36b4884 100644
--- a/test/ILLink.RoslynAnalyzer.Tests/RequiresCapabilityTests.cs
+++ b/test/ILLink.RoslynAnalyzer.Tests/RequiresCapabilityTests.cs
@@ -6,7 +6,7 @@ using Xunit;
namespace ILLink.RoslynAnalyzer.Tests
{
- public sealed class RequiresCapabilityTests : LinkerTestBase
+ public sealed partial class RequiresCapabilityTests : LinkerTestBase
{
protected override string TestSuiteName => "RequiresCapability";
@@ -17,6 +17,12 @@ namespace ILLink.RoslynAnalyzer.Tests
}
[Fact]
+ public Task ReflectionAccessFromCompilerGeneratedCode ()
+ {
+ return RunTest ();
+ }
+
+ [Fact]
public Task RequiresAccessedThrough ()
{
return RunTest (nameof (RequiresAccessedThrough));
diff --git a/test/Mono.Linker.Tests.Cases/DataFlow/CompilerGeneratedCodeAccessedViaReflection.cs b/test/Mono.Linker.Tests.Cases/DataFlow/CompilerGeneratedCodeAccessedViaReflection.cs
new file mode 100644
index 000000000..1b5f65c7e
--- /dev/null
+++ b/test/Mono.Linker.Tests.Cases/DataFlow/CompilerGeneratedCodeAccessedViaReflection.cs
@@ -0,0 +1,523 @@
+// Copyright (c) .NET Foundation and contributors. All rights reserved.
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
+
+using System;
+using System.Collections.Generic;
+using System.Diagnostics.CodeAnalysis;
+using System.Linq;
+using System.Linq.Expressions;
+using System.Runtime.InteropServices;
+using System.Text;
+using System.Threading.Tasks;
+using Mono.Linker.Tests.Cases.DataFlow;
+using Mono.Linker.Tests.Cases.Expectations.Assertions;
+using Mono.Linker.Tests.Cases.Expectations.Helpers;
+
+namespace Mono.Linker.Tests.Cases.DataFlow
+{
+ [SkipKeptItemsValidation]
+ [ExpectedNoWarnings]
+ class CompilerGeneratedCodeAccessedViaReflection
+ {
+ public static void Main ()
+ {
+ IteratorStateMachines.Test ();
+ AsyncStateMachines.Test ();
+ AsyncIteratorStateMachines.Test ();
+ Lambdas.Test ();
+ LocalFunctions.Test ();
+ }
+
+ class BaseTypeWithIteratorStateMachines
+ {
+ // Annotations aren't propagated to hoisted locals: https://github.com/dotnet/linker/issues/2001
+ [ExpectedWarning ("IL2077", nameof (DataFlowTypeExtensions.RequiresAll), CompilerGeneratedCode = true)]
+ public static IEnumerable<int> BaseIteratorWithCorrectDataflow ()
+ {
+ var t = GetAll ();
+ yield return 0;
+ t.RequiresAll ();
+ }
+ }
+
+ [ExpectedWarning ("IL2120", "<" + nameof (BaseIteratorWithCorrectDataflow) + ">", "MoveNext",
+ ProducedBy = ProducedBy.Trimmer)]
+ [DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.All)]
+ class IteratorStateMachines : BaseTypeWithIteratorStateMachines
+ {
+ public static IEnumerable<int> IteratorWithoutDataflow ()
+ {
+ yield return 0;
+ }
+
+ [ExpectedWarning ("IL2026", "--MethodWithRequires--", CompilerGeneratedCode = true)]
+ [ExpectedWarning ("IL3002", "--MethodWithRequires--",
+ ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", "--MethodWithRequires--",
+ ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL2119", "<" + nameof (IteratorCallsMethodWithRequires) + ">", "MoveNext", CompilerGeneratedCode = true)]
+ public static IEnumerable<int> IteratorCallsMethodWithRequires ()
+ {
+ yield return 0;
+ MethodWithRequires ();
+ }
+
+ [ExpectedWarning ("IL2119", "<" + nameof (IteratorWithCorrectDataflow) + ">", "MoveNext", CompilerGeneratedCode = true)]
+ // Annotations aren't propagated to hoisted locals: https://github.com/dotnet/linker/issues/2001
+ [ExpectedWarning ("IL2077", nameof (DataFlowTypeExtensions.RequiresAll), CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)]
+ public static IEnumerable<int> IteratorWithCorrectDataflow ()
+ {
+ var t = GetAll ();
+ yield return 0;
+ t.RequiresAll ();
+ }
+
+ [ExpectedWarning ("IL2119", "<" + nameof (IteratorWithProblematicDataflow) + ">", "MoveNext", CompilerGeneratedCode = true)]
+ // Annotations aren't propagated to hoisted locals: https://github.com/dotnet/linker/issues/2001
+ [ExpectedWarning ("IL2077", nameof (DataFlowTypeExtensions.RequiresAll), CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)]
+ public static IEnumerable<int> IteratorWithProblematicDataflow ()
+ {
+ var t = GetWithPublicMethods ();
+ yield return 0;
+ t.RequiresAll ();
+ }
+
+ [ExpectedWarning ("IL2112", nameof (RUCTypeWithIterators) + "()", "--RUCTypeWithIterators--", CompilerGeneratedCode = true)]
+ [RequiresUnreferencedCode ("--RUCTypeWithIterators--")]
+ class RUCTypeWithIterators
+ {
+ [ExpectedWarning ("IL2112", nameof (StaticIteratorCallsMethodWithRequires), "--RUCTypeWithIterators--",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2112", "<" + nameof (StaticIteratorCallsMethodWithRequires) + ">", "--RUCTypeWithIterators--", CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)] // state machine ctor
+ [ExpectedWarning ("IL3002", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ public static IEnumerable<int> StaticIteratorCallsMethodWithRequires ()
+ {
+ yield return 0;
+ MethodWithRequires ();
+ }
+
+ // BUG: this should also give IL2112 for the InstanceIteratorCallsMethodWithRequires state machine constructor.
+ // https://github.com/dotnet/linker/issues/2806
+ // [ExpectedWarning ("IL2026", "<" + nameof (RUCTypeWithIterators.InstanceIteratorCallsMethodWithRequires) + ">")]
+ // With that, the IL2119 warning should also go away.
+ [ExpectedWarning ("IL2119", "<" + nameof (InstanceIteratorCallsMethodWithRequires) + ">", "MoveNext", CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL3002", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ public IEnumerable<int> InstanceIteratorCallsMethodWithRequires ()
+ {
+ yield return 0;
+ MethodWithRequires ();
+ }
+ }
+
+ [ExpectedWarning ("IL2118", "<" + nameof (IteratorWithProblematicDataflow) + ">", "MoveNext",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", "<" + nameof (IteratorCallsMethodWithRequires) + ">", "MoveNext",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", "<" + nameof (IteratorWithCorrectDataflow) + ">", "MoveNext",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", "<" + nameof (BaseIteratorWithCorrectDataflow) + ">", "MoveNext",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2026", nameof (RUCTypeWithIterators) + "()", "--RUCTypeWithIterators--")]
+ // Expect to see warnings about RUC on type, for all static state machine members.
+ [ExpectedWarning ("IL2026", nameof (RUCTypeWithIterators.StaticIteratorCallsMethodWithRequires) + "()", "--RUCTypeWithIterators--")]
+ [ExpectedWarning ("IL2026", "<" + nameof (RUCTypeWithIterators.StaticIteratorCallsMethodWithRequires) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ // BUG: this should also give IL2026 for the InstanceIteratorCallsMethodWithRequires state machine constructor.
+ // https://github.com/dotnet/linker/issues/2806
+ // [ExpectedWarning ("IL2026", "<" + nameof (RUCTypeWithIterators.InstanceIteratorCallsMethodWithRequires) + ">")]
+ // With that, the IL2118 warning should also go away.
+ [ExpectedWarning ("IL2118", "<" + nameof (RUCTypeWithIterators.InstanceIteratorCallsMethodWithRequires) + ">", "MoveNext",
+ ProducedBy = ProducedBy.Trimmer)]
+ public static void Test (IteratorStateMachines test = null)
+ {
+ typeof (IteratorStateMachines).RequiresAll ();
+
+ test.GetType ().RequiresAll ();
+ }
+ }
+
+ class AsyncStateMachines
+ {
+ public static async Task AsyncWithoutDataflow ()
+ {
+ }
+
+ [ExpectedWarning ("IL2026", "--MethodWithRequires--", CompilerGeneratedCode = true)]
+ [ExpectedWarning ("IL3002", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ public static async Task AsyncCallsMethodWithRequires ()
+ {
+ MethodWithRequires ();
+ }
+
+ // Annotations aren't propagated to hoisted locals: https://github.com/dotnet/linker/issues/2001
+ [ExpectedWarning ("IL2077", nameof (DataFlowTypeExtensions.RequiresAll), CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)]
+ public static async Task AsyncWithCorrectDataflow ()
+ {
+ var t = GetAll ();
+ t.RequiresAll ();
+ }
+
+ // Annotations aren't propagated to hoisted locals: https://github.com/dotnet/linker/issues/2001
+ [ExpectedWarning ("IL2077", nameof (DataFlowTypeExtensions.RequiresAll), CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)]
+ public static async Task AsyncWithProblematicDataflow ()
+ {
+ var t = GetWithPublicMethods ();
+ t.RequiresAll ();
+ }
+
+ [ExpectedWarning ("IL2118", "<" + nameof (AsyncWithProblematicDataflow) + ">", "MoveNext",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", "<" + nameof (AsyncCallsMethodWithRequires) + ">", "MoveNext",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", "<" + nameof (AsyncWithCorrectDataflow) + ">", "MoveNext",
+ ProducedBy = ProducedBy.Trimmer)]
+ public static void Test ()
+ {
+ typeof (AsyncStateMachines).RequiresAll ();
+ }
+ }
+
+ class AsyncIteratorStateMachines
+ {
+ public static async IAsyncEnumerable<int> AsyncIteratorWithoutDataflow ()
+ {
+ yield return await MethodAsync ();
+ }
+
+ [ExpectedWarning ("IL2026", "--MethodWithRequires--", CompilerGeneratedCode = true)]
+ [ExpectedWarning ("IL3002", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ public static async IAsyncEnumerable<int> AsyncIteratorCallsMethodWithRequires ()
+ {
+ yield return await MethodAsync ();
+ MethodWithRequires ();
+ }
+
+ // Annotations aren't propagated to hoisted locals: https://github.com/dotnet/linker/issues/2001
+ [ExpectedWarning ("IL2077", nameof (DataFlowTypeExtensions.RequiresAll), CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)]
+ public static async IAsyncEnumerable<int> AsyncIteratorWithCorrectDataflow ()
+ {
+ var t = GetAll ();
+ yield return await MethodAsync ();
+ t.RequiresAll ();
+ }
+
+ // Annotations aren't propagated to hoisted locals: https://github.com/dotnet/linker/issues/2001
+ [ExpectedWarning ("IL2077", nameof (DataFlowTypeExtensions.RequiresAll),
+ nameof (AsyncIteratorWithProblematicDataflow), CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)]
+ public static async IAsyncEnumerable<int> AsyncIteratorWithProblematicDataflow ()
+ {
+ var t = GetWithPublicMethods ();
+ yield return await MethodAsync ();
+ t.RequiresAll ();
+ }
+
+ [ExpectedWarning ("IL2118", "<" + nameof (AsyncIteratorWithProblematicDataflow) + ">", "MoveNext",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", "<" + nameof (AsyncIteratorCallsMethodWithRequires) + ">", "MoveNext",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", "<" + nameof (AsyncIteratorWithCorrectDataflow) + ">", "MoveNext",
+ ProducedBy = ProducedBy.Trimmer)]
+ public static void Test ()
+ {
+ typeof (AsyncIteratorStateMachines).RequiresAll ();
+ }
+ }
+
+ [DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.All)]
+ class Lambdas
+ {
+ static void LambdaWithoutDataflow ()
+ {
+ var lambda = () => 0;
+ lambda ();
+ }
+
+ static void LambdaCallsMethodWithRequires ()
+ {
+ var lambda =
+ [ExpectedWarning ("IL2026", "--MethodWithRequires--")]
+ [ExpectedWarning ("IL3002", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL2119", "<" + nameof (LambdaCallsMethodWithRequires) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ () => MethodWithRequires ();
+ lambda ();
+ }
+
+ static void LambdaWithCorrectDataflow ()
+ {
+ var lambda =
+ // Annotations aren't propagated to hoisted locals: https://github.com/dotnet/linker/issues/2001
+ [ExpectedWarning ("IL2119", "<" + nameof (LambdaWithCorrectDataflow) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ () => {
+ var t = GetAll ();
+ t.RequiresAll ();
+ };
+ lambda ();
+ }
+
+ [ExpectedWarning ("IL2111", "<" + nameof (LambdaWithCorrectParameter) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ static void LambdaWithCorrectParameter ()
+ {
+ var lambda =
+ [ExpectedWarning ("IL2114", "<" + nameof (LambdaWithCorrectParameter) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ ([DynamicallyAccessedMembersAttribute (DynamicallyAccessedMemberTypes.All)] Type t) => {
+ t.RequiresAll ();
+ };
+ lambda (null);
+ }
+
+ static void LambdaWithProblematicDataflow ()
+ {
+ var lambda =
+ [ExpectedWarning ("IL2119", "<" + nameof (LambdaWithProblematicDataflow) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2072", nameof (DataFlowTypeExtensions.RequiresAll),
+ ProducedBy = ProducedBy.Trimmer)]
+ () => {
+ var t = GetWithPublicMethods ();
+ t.RequiresAll ();
+ };
+ lambda ();
+ }
+
+ static void LambdaWithCapturedTypeToDAM ()
+ {
+ var t = GetWithPublicMethods ();
+ var lambda =
+ [ExpectedWarning ("IL2119", "<" + nameof (LambdaWithCapturedTypeToDAM) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ // Annotations aren't propagated to hoisted locals: https://github.com/dotnet/linker/issues/2001
+ [ExpectedWarning ("IL2077", nameof (DataFlowTypeExtensions.RequiresAll),
+ ProducedBy = ProducedBy.Trimmer)]
+ () => {
+ t.RequiresAll ();
+ };
+ lambda ();
+ }
+
+ static void LambdaWithCapturedInt ()
+ {
+ int i = 0;
+ var lambda =
+ () => i;
+ i++;
+ lambda ();
+ }
+
+ [ExpectedWarning ("IL2112", nameof (RUCTypeWithLambdas) + "()", "--RUCTypeWithLambdas--", CompilerGeneratedCode = true)]
+ [RequiresUnreferencedCode ("--RUCTypeWithLambdas--")]
+ class RUCTypeWithLambdas
+ {
+ public void MethodWithLambdas ()
+ {
+ var lambda =
+ [ExpectedWarning ("IL2119", "<" + nameof (MethodWithLambdas) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL3002", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ () => MethodWithRequires ();
+
+ int i = 0;
+ var lambdaWithCapturedState =
+ [ExpectedWarning ("IL2119", "<" + nameof (MethodWithLambdas) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL3002", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ () => {
+ i++;
+ MethodWithRequires ();
+ };
+
+ lambda ();
+ lambdaWithCapturedState ();
+ }
+ }
+
+ [ExpectedWarning ("IL2118", "<" + nameof (LambdaCallsMethodWithRequires) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", "<" + nameof (LambdaWithCorrectDataflow) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2111", "<" + nameof (LambdaWithCorrectParameter) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", "<" + nameof (LambdaWithProblematicDataflow) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", "<" + nameof (LambdaWithCapturedTypeToDAM) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ // Expect RUC warnings for static, compiler-generated code warnings for instance.
+ [ExpectedWarning ("IL2026", nameof (RUCTypeWithLambdas) + "()", "--RUCTypeWithLambdas--")]
+ [ExpectedWarning ("IL2118", "<" + nameof (RUCTypeWithLambdas.MethodWithLambdas) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", "<" + nameof (RUCTypeWithLambdas.MethodWithLambdas) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ public static void Test (Lambdas test = null)
+ {
+ typeof (Lambdas).RequiresAll ();
+
+ test.GetType ().RequiresAll ();
+ }
+ }
+
+ [DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.All)]
+ class LocalFunctions
+ {
+ static void LocalFunctionWithoutDataflow ()
+ {
+ int LocalFunction () => 0;
+ LocalFunction ();
+ }
+
+ static void LocalFunctionCallsMethodWithRequires ()
+ {
+ [ExpectedWarning ("IL2026", "--MethodWithRequires--")]
+ [ExpectedWarning ("IL3002", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL2119", "<" + nameof (LocalFunctionCallsMethodWithRequires) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ void LocalFunction () => MethodWithRequires ();
+ LocalFunction ();
+ }
+
+ static void LocalFunctionWithCorrectDataflow ()
+ {
+ [ExpectedWarning ("IL2119", "<" + nameof (LocalFunctionWithCorrectDataflow) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ void LocalFunction ()
+ {
+ var t = GetAll ();
+ t.RequiresAll ();
+ };
+ LocalFunction ();
+ }
+
+ static void LocalFunctionWithProblematicDataflow ()
+ {
+ [ExpectedWarning ("IL2072", nameof (DataFlowTypeExtensions.RequiresAll),
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2119", "<" + nameof (LocalFunctionWithProblematicDataflow) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ void LocalFunction ()
+ {
+ var t = GetWithPublicMethods ();
+ t.RequiresAll ();
+ };
+ LocalFunction ();
+ }
+
+ static void LocalFunctionWithCapturedTypeToDAM ()
+ {
+ var t = GetAll ();
+ [ExpectedWarning ("IL2119", "<" + nameof (LocalFunctionWithCapturedTypeToDAM) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ // Annotations aren't propagated to hoisted locals: https://github.com/dotnet/linker/issues/2001
+ [ExpectedWarning ("IL2077", nameof (DataFlowTypeExtensions.RequiresAll),
+ ProducedBy = ProducedBy.Trimmer)]
+ void LocalFunction ()
+ {
+ t.RequiresAll ();
+ };
+ LocalFunction ();
+ }
+
+ static void LocalFunctionWithCapturedInt ()
+ {
+ int i = 0;
+ int LocalFunction () => i;
+ i++;
+ LocalFunction ();
+ }
+
+ [ExpectedWarning ("IL2112", nameof (RUCTypeWithLocalFunctions) + "()", CompilerGeneratedCode = true)]
+ [RequiresUnreferencedCode ("--RUCTypeWithLocalFunctions--")]
+ class RUCTypeWithLocalFunctions
+ {
+ public void MethodWithLocalFunctions ()
+ {
+ [ExpectedWarning ("IL2112", "<" + nameof (MethodWithLocalFunctions) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL3002", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ void LocalFunction () => MethodWithRequires ();
+
+ [ExpectedWarning ("IL2112", "<" + nameof (MethodWithLocalFunctions) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL3002", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ static void StaticLocalFunction () => MethodWithRequires ();
+
+ int i = 0;
+ [ExpectedWarning ("IL2112", "<" + nameof (MethodWithLocalFunctions) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL3002", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", "--MethodWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ void LocalFunctionWithCapturedState ()
+ {
+ i++;
+ MethodWithRequires ();
+ }
+
+ LocalFunction ();
+ StaticLocalFunction ();
+ LocalFunctionWithCapturedState ();
+ }
+ }
+
+ [ExpectedWarning ("IL2118", nameof (LocalFunctionCallsMethodWithRequires),
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", nameof (LocalFunctionWithCorrectDataflow),
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", nameof (LocalFunctionWithProblematicDataflow),
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", nameof (LocalFunctionWithCapturedTypeToDAM),
+ ProducedBy = ProducedBy.Trimmer)]
+ // Expect RUC warnings for static, compiler-generated code warnings for instance.
+ [ExpectedWarning ("IL2026", nameof (RUCTypeWithLocalFunctions) + "()", "--RUCTypeWithLocalFunctions--")]
+ [ExpectedWarning ("IL2026", "<" + nameof (RUCTypeWithLocalFunctions.MethodWithLocalFunctions) + ">", "LocalFunctionWithCapturedState",
+ ProducedBy = ProducedBy.Trimmer)] // displayclass ctor
+ [ExpectedWarning ("IL2026", "<" + nameof (RUCTypeWithLocalFunctions.MethodWithLocalFunctions) + ">", "StaticLocalFunction",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2026", "<" + nameof (RUCTypeWithLocalFunctions.MethodWithLocalFunctions) + ">", "LocalFunction",
+ ProducedBy = ProducedBy.Trimmer)]
+ public static void Test (LocalFunctions test = null)
+ {
+ typeof (LocalFunctions).RequiresAll ();
+
+ test.GetType ().RequiresAll ();
+ }
+ }
+
+ [RequiresUnreferencedCode ("--MethodWithRequires--")]
+ [RequiresAssemblyFiles ("--MethodWithRequires--")]
+ [RequiresDynamicCode ("--MethodWithRequires--")]
+ static void MethodWithRequires ()
+ {
+ }
+
+ static async Task<int> MethodAsync ()
+ {
+ return await Task.FromResult (0);
+ }
+
+
+ [return: DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.PublicMethods)]
+ static Type GetWithPublicMethods () => null;
+
+ [return: DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.All)]
+ static Type GetAll () => null;
+ }
+}
diff --git a/test/Mono.Linker.Tests.Cases/RequiresCapability/ReflectionAccessFromCompilerGeneratedCode.cs b/test/Mono.Linker.Tests.Cases/RequiresCapability/ReflectionAccessFromCompilerGeneratedCode.cs
new file mode 100644
index 000000000..14fd917fb
--- /dev/null
+++ b/test/Mono.Linker.Tests.Cases/RequiresCapability/ReflectionAccessFromCompilerGeneratedCode.cs
@@ -0,0 +1,213 @@
+// Copyright (c) .NET Foundation and contributors. All rights reserved.
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
+
+using System;
+using System.Collections.Generic;
+using System.Diagnostics.CodeAnalysis;
+using System.Threading.Tasks;
+using Mono.Linker.Tests.Cases.Expectations.Assertions;
+using Mono.Linker.Tests.Cases.Expectations.Helpers;
+
+namespace Mono.Linker.Tests.Cases.RequiresCapability
+{
+ [SkipKeptItemsValidation]
+ [ExpectedNoWarnings]
+ public class ReflectionAccessFromCompilerGeneratedCode
+ {
+ public static void Main ()
+ {
+ ReflectionAccessFromStateMachine.Test ();
+ ReflectionAccessFromLocalFunction.Test ();
+ ReflectionAccessFromLambda.Test ();
+ }
+
+ class ReflectionAccessFromStateMachine
+ {
+ [ExpectedWarning ("IL2026", "--TypeWithMethodWithRequires.MethodWithRequires--", CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2026", "--MethodWithLocalFunctionWithRUC.LocalFunction--", CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", nameof (TypeWithMethodWithRequires.MethodWithLocalFunctionCallsRUC), "LocalFunction", CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2111", nameof (TypeWithMethodWithRequires.MethodWithAnnotations), CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)]
+ static IEnumerable<int> TestIterator ()
+ {
+ typeof (TypeWithMethodWithRequires).RequiresAll ();
+ yield return 0;
+ }
+
+ [RequiresUnreferencedCode ("--TestIteratorWithRUC--")]
+ static IEnumerable<int> TestIteratorWithRUC ()
+ {
+ typeof (TypeWithMethodWithRequires).RequiresAll ();
+ yield return 0;
+ }
+
+ [ExpectedWarning ("IL2026", "--TypeWithMethodWithRequires.MethodWithRequires--", CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2026", "--MethodWithLocalFunctionWithRUC.LocalFunction--", CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", nameof (TypeWithMethodWithRequires.MethodWithLocalFunctionCallsRUC), "LocalFunction", CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2111", nameof (TypeWithMethodWithRequires.MethodWithAnnotations), CompilerGeneratedCode = true,
+ ProducedBy = ProducedBy.Trimmer)]
+ static async void TestAsync ()
+ {
+ typeof (TypeWithMethodWithRequires).RequiresAll ();
+ await MethodAsync ();
+ }
+
+ [RequiresUnreferencedCode ("--TestAsyncWithRUC--")]
+ static async void TestAsyncWithRUC ()
+ {
+ typeof (TypeWithMethodWithRequires).RequiresAll ();
+ await MethodAsync ();
+ }
+
+ [ExpectedWarning ("IL2026", "--TestIteratorWithRUC--")]
+ [ExpectedWarning ("IL2026", "--TestAsyncWithRUC--")]
+ public static void Test ()
+ {
+ TestIterator ();
+ TestIteratorWithRUC ();
+ TestAsync ();
+ TestAsyncWithRUC ();
+ }
+ }
+
+ class ReflectionAccessFromLocalFunction
+ {
+ static void TestLocalFunction ()
+ {
+ [ExpectedWarning ("IL2026", "--TypeWithMethodWithRequires.MethodWithRequires--",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2026", "--MethodWithLocalFunctionWithRUC.LocalFunction--",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", nameof (TypeWithMethodWithRequires.MethodWithLocalFunctionCallsRUC), "LocalFunction",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2111", nameof (TypeWithMethodWithRequires.MethodWithAnnotations),
+ ProducedBy = ProducedBy.Trimmer)]
+ void LocalFunction ()
+ {
+ typeof (TypeWithMethodWithRequires).RequiresAll ();
+ }
+ LocalFunction ();
+ }
+
+ [ExpectedWarning ("IL2026", "--LocalFunction--")]
+ static void TestLocalFunctionWithRUC ()
+ {
+ [RequiresUnreferencedCode ("--LocalFunction--")]
+ void LocalFunction ()
+ {
+ typeof (TypeWithMethodWithRequires).RequiresAll ();
+ }
+ LocalFunction ();
+ }
+
+ [RequiresUnreferencedCode ("--TestLocalFunctionInMethodWithRUC--")]
+ static void TestLocalFunctionInMethodWithRUC ()
+ {
+ void LocalFunction ()
+ {
+ typeof (TypeWithMethodWithRequires).RequiresAll ();
+ }
+ LocalFunction ();
+ }
+
+ [ExpectedWarning ("IL2026", "--TestLocalFunctionInMethodWithRUC--")]
+ public static void Test ()
+ {
+ TestLocalFunction ();
+ TestLocalFunctionWithRUC ();
+ TestLocalFunctionInMethodWithRUC ();
+ }
+ }
+
+ class ReflectionAccessFromLambda
+ {
+ static void TestLambda ()
+ {
+ var lambda =
+ [ExpectedWarning ("IL2026", "--TypeWithMethodWithRequires.MethodWithRequires--",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2026", "--MethodWithLocalFunctionWithRUC.LocalFunction--",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", nameof (TypeWithMethodWithRequires.MethodWithLocalFunctionCallsRUC), "LocalFunction",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2111", nameof (TypeWithMethodWithRequires.MethodWithAnnotations),
+ ProducedBy = ProducedBy.Trimmer)]
+ () => {
+ typeof (TypeWithMethodWithRequires).RequiresAll ();
+ };
+ lambda ();
+ }
+
+ [ExpectedWarning ("IL2026", "--TestLambdaInMethodWithRUC--")]
+ static void TestLambdaWithRUC ()
+ {
+ var lambda =
+ [RequiresUnreferencedCode ("--TestLambdaInMethodWithRUC--")]
+ () => {
+ typeof (TypeWithMethodWithRequires).RequiresAll ();
+ };
+ lambda ();
+ }
+
+ [RequiresUnreferencedCode ("--TestLambdaInMethodWithRUC--")]
+ static void TestLambdaInMethodWithRUC ()
+ {
+ var lambda =
+ () => {
+ typeof (TypeWithMethodWithRequires).RequiresAll ();
+ };
+ lambda ();
+ }
+
+ [ExpectedWarning ("IL2026", "--TestLambdaInMethodWithRUC--")]
+ public static void Test ()
+ {
+ TestLambda ();
+ TestLambdaWithRUC ();
+ TestLambdaInMethodWithRUC ();
+ }
+ }
+
+ static async Task<int> MethodAsync ()
+ {
+ return await Task.FromResult (0);
+ }
+
+ class TypeWithMethodWithRequires
+ {
+ [RequiresUnreferencedCode ("--TypeWithMethodWithRequires.MethodWithRequires--")]
+ [RequiresAssemblyFiles ("--TypeWithMethodWithRequires.MethodWithRequires--")]
+ [RequiresDynamicCode ("--TypeWithMethodWithRequires.MethodWithRequires--")]
+ public static void MethodWithRequires ()
+ {
+ }
+
+ public static void MethodWithAnnotations ([DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.All)] Type t) { }
+
+ [ExpectedWarning ("IL2026", "--MethodWithLocalFunctionWithRUC.LocalFunction--")]
+ public static void MethodWithLocalFunctionWithRUC ()
+ {
+ [RequiresUnreferencedCode ("--MethodWithLocalFunctionWithRUC.LocalFunction--")]
+ void LocalFunction ()
+ { }
+ LocalFunction ();
+ }
+
+ public static void MethodWithLocalFunctionCallsRUC ()
+ {
+ [ExpectedWarning ("IL2026", "--MethodWithRUC--")]
+ void LocalFunction () => MethodWithRUC ();
+ LocalFunction ();
+ }
+ }
+
+ [RequiresUnreferencedCode ("--MethodWithRUC--")]
+ static void MethodWithRUC () { }
+ }
+}
diff --git a/test/Mono.Linker.Tests.Cases/RequiresCapability/RequiresInCompilerGeneratedCode.cs b/test/Mono.Linker.Tests.Cases/RequiresCapability/RequiresInCompilerGeneratedCode.cs
index d3f277902..79b795c66 100644
--- a/test/Mono.Linker.Tests.Cases/RequiresCapability/RequiresInCompilerGeneratedCode.cs
+++ b/test/Mono.Linker.Tests.Cases/RequiresCapability/RequiresInCompilerGeneratedCode.cs
@@ -1,4 +1,4 @@
-// Copyright (c) .NET Foundation and contributors. All rights reserved.
+// Copyright (c) .NET Foundation and contributors. All rights reserved.
// Licensed under the MIT license. See LICENSE file in the project root for full license information.
using System;
@@ -618,7 +618,8 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
{
LocalFunction ();
- [ExpectedWarning ("IL2026", "--MethodWithRequires--", ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2026", "--MethodWithRequires--",
+ ProducedBy = ProducedBy.Trimmer)]
void LocalFunction () => typeof (RequiresInCompilerGeneratedCode)
.GetMethod ("MethodWithRequires", System.Reflection.BindingFlags.NonPublic)
.Invoke (null, new object[] { });
@@ -656,7 +657,8 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
{
LocalFunction ();
- [ExpectedWarning ("IL2026", "--TypeWithMethodWithRequires.MethodWithRequires--", ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2026", "--TypeWithMethodWithRequires.MethodWithRequires--",
+ ProducedBy = ProducedBy.Trimmer)]
void LocalFunction () => typeof (TypeWithMethodWithRequires).RequiresNonPublicMethods ();
}
@@ -869,19 +871,38 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
}
}
- class DynamicallyAccessedLocalFunctionUnused
+ class DynamicallyAccessedLocalFunctionUnusedShouldWarn
+ {
+ [ExpectedWarning ("IL2118", nameof (TestCallMethodWithRequiresInDynamicallyAccessedLocalFunction), "LocalFunction", ProducedBy = ProducedBy.Trimmer)]
+ public static void TestCallMethodWithRequiresInDynamicallyAccessedLocalFunction ()
+ {
+ typeof (DynamicallyAccessedLocalFunctionUnusedShouldWarn).RequiresNonPublicMethods ();
+
+ // The linker isn't able to figure out which user method this local function
+ // belongs to, but it doesn't warn because it is only accessed via reflection.
+ // Instead this warns on the reflection access.
+ [ExpectedWarning ("IL2026", "--MethodWithRequires--",
+ ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3002", "--MethodWithRequires--",
+ ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", "--MethodWithRequires--",
+ ProducedBy = ProducedBy.Analyzer)]
+ void LocalFunction () => MethodWithRequires ();
+ }
+ }
+
+ class DynamicallyAccessedLocalFunctionUnusedShouldSuppress
{
[RequiresUnreferencedCode ("Suppress in body")]
[RequiresAssemblyFiles ("Suppress in body")]
[RequiresDynamicCode ("Suppress in body")]
public static void TestCallMethodWithRequiresInDynamicallyAccessedLocalFunction ()
{
- typeof (DynamicallyAccessedLocalFunctionUnused).RequiresNonPublicMethods ();
+ typeof (DynamicallyAccessedLocalFunctionUnusedShouldSuppress).RequiresNonPublicMethods ();
- // This local function is unused except for the dynamic reference above,
- // so the linker isn't able to figure out which user method it belongs to,
- // and the warning is not suppressed.
- [ExpectedWarning ("IL2026", "--MethodWithRequires--", ProducedBy = ProducedBy.Trimmer)]
+ // The linker isn't able to figure out which user method this local function
+ // belongs to, but it doesn't warn because it is only accessed via reflection,
+ // in a RUC scope.
void LocalFunction () => MethodWithRequires ();
}
}
@@ -906,6 +927,26 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
[ExpectedWarning ("IL2026")]
[ExpectedWarning ("IL3002", ProducedBy = ProducedBy.Analyzer)]
[ExpectedWarning ("IL3050", ProducedBy = ProducedBy.Analyzer)]
+ static void TestSuppressionOnLocalFunctionWithAssignment ()
+ {
+ LocalFunction (); // This will produce a warning since the local function has Requires on it
+
+ [RequiresUnreferencedCode ("Suppress in body")]
+ [RequiresAssemblyFiles ("Suppress in body")]
+ [RequiresDynamicCode ("Suppress in body")]
+ void LocalFunction (Type unknownType = null)
+ {
+ MethodWithRequires ();
+ typeWithNonPublicMethods = unknownType;
+ }
+ }
+
+ [DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.NonPublicMethods)]
+ static Type typeWithNonPublicMethods;
+
+ [ExpectedWarning ("IL2026")]
+ [ExpectedWarning ("IL3002", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", ProducedBy = ProducedBy.Analyzer)]
static void TestSuppressionOnLocalFunctionWithNestedLocalFunction ()
{
LocalFunction (); // This will produce a warning since the local function has Requires on it
@@ -994,8 +1035,10 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
TestGenericLocalFunctionWithAnnotationsAndClosure<TestType> ();
TestCallMethodWithRequiresInLtftnLocalFunction ();
DynamicallyAccessedLocalFunction.TestCallMethodWithRequiresInDynamicallyAccessedLocalFunction ();
- DynamicallyAccessedLocalFunctionUnused.TestCallMethodWithRequiresInDynamicallyAccessedLocalFunction ();
+ DynamicallyAccessedLocalFunctionUnusedShouldWarn.TestCallMethodWithRequiresInDynamicallyAccessedLocalFunction ();
+ DynamicallyAccessedLocalFunctionUnusedShouldSuppress.TestCallMethodWithRequiresInDynamicallyAccessedLocalFunction ();
TestSuppressionOnLocalFunction ();
+ TestSuppressionOnLocalFunctionWithAssignment ();
TestSuppressionOnLocalFunctionWithNestedLocalFunction ();
TestSuppressionOnOuterAndLocalFunction ();
TestSuppressionOnOuterWithSameName.Test ();
@@ -1043,6 +1086,20 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
lambda ();
}
+ [ExpectedWarning ("IL2026", "--LambdaWithRequires--")]
+ [ExpectedWarning ("IL3002", "--LambdaWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", "--LambdaWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ static void TestLambdaWithRequires ()
+ {
+ Action lambda =
+ [RequiresUnreferencedCodeAttribute ("--LambdaWithRequires--")]
+ [RequiresAssemblyFiles ("--LambdaWithRequires--")]
+ [RequiresDynamicCode ("--LambdaWithRequires--")]
+ () => MethodWithRequires ();
+
+ lambda ();
+ }
+
static void TestCallUnused ()
{
Action _ =
@@ -1052,6 +1109,18 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
() => MethodWithRequires ();
}
+ [ExpectedWarning ("IL2026", "--LambdaWithRequires--")]
+ [ExpectedWarning ("IL3002", "--LambdaWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ [ExpectedWarning ("IL3050", "--LambdaWithRequires--", ProducedBy = ProducedBy.Analyzer)]
+ static void TestLambdaWithRequiresUnused ()
+ {
+ Action _ =
+ [RequiresUnreferencedCode ("--LambdaWithRequires--")]
+ [RequiresAssemblyFiles ("--LambdaWithRequires--")]
+ [RequiresDynamicCode ("--LambdaWithRequires--")]
+ () => MethodWithRequires ();
+ }
+
static void TestCallWithClosure (int p = 0)
{
Action lambda =
@@ -1125,6 +1194,8 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
{
TestCall ();
TestCallUnused ();
+ TestLambdaWithRequires ();
+ TestLambdaWithRequiresUnused ();
TestCallWithClosure ();
TestCallWithClosureUnused ();
TestReflectionAccess ();
@@ -1390,6 +1461,13 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
MethodWithGenericWhichRequiresMethods<TypeWithMethodWithRequires> ();
}
+ [ExpectedWarning ("IL2026", "--TypeWithMethodWithRequires.MethodWithRequires--", CompilerGeneratedCode = true)]
+ static IEnumerable<int> TestDynamicallyAccessedMethodViaGenericTypeParameterInIterator ()
+ {
+ yield return 1;
+ new TypeWithGenericWhichRequiresMethods<TypeWithMethodWithRequires> ();
+ }
+
static void TestLocalFunctionInIteratorLocalFunction ()
{
IteratorLocalFunction ();
@@ -1428,6 +1506,7 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
{
TestIteratorLocalFunctionInAsync ();
TestDynamicallyAccessedMethodViaGenericMethodParameterInIterator ();
+ TestDynamicallyAccessedMethodViaGenericTypeParameterInIterator ();
TestLocalFunctionInIteratorLocalFunction ();
TestLocalFunctionCalledFromIteratorLocalFunctionAndMethod ();
}
@@ -1716,6 +1795,11 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
// state machine members.
[ExpectedWarning ("IL2026", "Requires to suppress", ProducedBy = ProducedBy.Trimmer)]
[ExpectedWarning ("IL2026", "Requires to suppress", ProducedBy = ProducedBy.Trimmer)]
+ // Linker warns about reflection access to compiler-generated state machine members.
+ [ExpectedWarning ("IL2118", nameof (StateMachinesOnlyReferencedViaReflection), "<" + nameof (TestAsyncOnlyReferencedViaReflectionWhichShouldWarn) + ">", "MoveNext()",
+ ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2118", nameof (StateMachinesOnlyReferencedViaReflection), "<" + nameof (TestIteratorOnlyReferencedViaReflectionWhichShouldWarn) + ">", "MoveNext()",
+ ProducedBy = ProducedBy.Trimmer)]
static void TestAll ()
{
typeof (StateMachinesOnlyReferencedViaReflection).RequiresAll ();
@@ -1751,6 +1835,14 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
void LocalFunction () => MethodWithRequires ();
}
+ static void TestLocalFunctionWithRequiresOnlyAccessedViaReflection ()
+ {
+ [RequiresUnreferencedCode ("--TestLocalFunctionWithRequiresOnlyAccessedViaReflection--")]
+ [RequiresAssemblyFiles ("--TestLocalFunctionWithRequiresOnlyAccessedViaReflection--")]
+ [RequiresDynamicCode ("--TestLocalFunctionWithRequiresOnlyAccessedViaReflection--")]
+ void LocalFunction () => MethodWithRequires ();
+ }
+
[ExpectedWarning ("IL2026", "LocalFunction")]
[ExpectedWarning ("IL3002", "LocalFunction", ProducedBy = ProducedBy.Analyzer)]
[ExpectedWarning ("IL3050", "LocalFunction", ProducedBy = ProducedBy.Analyzer)]
@@ -1778,6 +1870,16 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
void LocalFunction () => MethodWithRequires ();
}
+ [RequiresUnreferencedCode ("--TestLocalFunctionInMethodWithRequiresOnlyAccessedViaReflection--")]
+ [RequiresAssemblyFiles ("--TestLocalFunctionInMethodWithRequiresOnlyAccessedViaReflection--")]
+ [RequiresDynamicCode ("--TestLocalFunctionInMethodWithRequiresOnlyAccessedViaReflection--")]
+ static void TestLocalFunctionInMethodWithRequiresOnlyAccessedViaReflection ()
+ {
+ // This is unused, except for the reflection access. Don't warn about MethodWithRequires
+ // because the reflection access will warn about accessing compiler-generated code.
+ void LocalFunction () => MethodWithRequires ();
+ }
+
[RequiresUnreferencedCode ("--TestLocalFunctionWithClosureInMethodWithRequires--")]
[RequiresAssemblyFiles ("--TestLocalFunctionWithClosureInMethodWithRequires--")]
[RequiresDynamicCode ("--TestLocalFunctionWithClosureInMethodWithRequires--")]
@@ -1795,13 +1897,18 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
// Warnings for Reflection access to methods with Requires
[ExpectedWarning ("IL2026", "--TestLocalFunctionInMethodWithRequires--")]
[ExpectedWarning ("IL2026", "--TestLocalFunctionWithClosureInMethodWithRequires--")]
+ [ExpectedWarning ("IL2026", "--TestLocalFunctionInMethodWithRequiresOnlyAccessedViaReflection--")]
// The linker correctly emits warnings about reflection access to local functions with Requires
// or which inherit Requires from the containing method. The analyzer doesn't bind to local functions
// so does not warn here.
[ExpectedWarning ("IL2026", "--TestLocalFunctionWithRequires--", ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2026", "--TestLocalFunctionWithRequiresOnlyAccessedViaReflection--", ProducedBy = ProducedBy.Trimmer)]
[ExpectedWarning ("IL2026", "--TestLocalFunctionWithClosureWithRequires--", ProducedBy = ProducedBy.Trimmer)]
[ExpectedWarning ("IL2026", "--TestLocalFunctionInMethodWithRequires--", ProducedBy = ProducedBy.Trimmer)]
[ExpectedWarning ("IL2026", "--TestLocalFunctionWithClosureInMethodWithRequires--", ProducedBy = ProducedBy.Trimmer)]
+ // Linker warns about reflection access to compiler-generated code
+ [ExpectedWarning ("IL2118", nameof (LocalFunctionsReferencedViaReflection), nameof (TestLocalFunctionInMethodWithRequiresOnlyAccessedViaReflection),
+ ProducedBy = ProducedBy.Trimmer)]
static void TestAll ()
{
typeof (LocalFunctionsReferencedViaReflection).RequiresAll ();
@@ -1810,11 +1917,16 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
// Warnings for Reflection access to methods with Requires
[ExpectedWarning ("IL2026", "--TestLocalFunctionInMethodWithRequires--")]
[ExpectedWarning ("IL2026", "--TestLocalFunctionWithClosureInMethodWithRequires--")]
+ [ExpectedWarning ("IL2026", "--TestLocalFunctionInMethodWithRequiresOnlyAccessedViaReflection--")]
// NonPublicMethods warns for local functions not emitted into display classes.
[ExpectedWarning ("IL2026", "--TestLocalFunctionWithRequires--", ProducedBy = ProducedBy.Trimmer)]
+ [ExpectedWarning ("IL2026", "--TestLocalFunctionWithRequiresOnlyAccessedViaReflection--", ProducedBy = ProducedBy.Trimmer)]
[ExpectedWarning ("IL2026", "--TestLocalFunctionWithClosureWithRequires--", ProducedBy = ProducedBy.Trimmer)]
[ExpectedWarning ("IL2026", "--TestLocalFunctionInMethodWithRequires--", ProducedBy = ProducedBy.Trimmer)]
[ExpectedWarning ("IL2026", "--TestLocalFunctionWithClosureInMethodWithRequires--", ProducedBy = ProducedBy.Trimmer)]
+ // Linker warns about reflection access to compiler-generated code
+ [ExpectedWarning ("IL2118", nameof (LocalFunctionsReferencedViaReflection), "<" + nameof (TestLocalFunctionInMethodWithRequiresOnlyAccessedViaReflection) + ">",
+ ProducedBy = ProducedBy.Trimmer)]
static void TestNonPublicMethods ()
{
typeof (LocalFunctionsReferencedViaReflection).RequiresNonPublicMethods ();
@@ -2053,6 +2165,10 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
{
}
+ class TypeWithGenericWhichRequiresMethods<[DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.NonPublicMethods)] T>
+ {
+ }
+
class TypeWithGenericWhichRequiresNonPublicFields<[DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.NonPublicFields)] T> { }
class TestType { }
diff --git a/test/Mono.Linker.Tests.Cases/RequiresCapability/RequiresOnClass.cs b/test/Mono.Linker.Tests.Cases/RequiresCapability/RequiresOnClass.cs
index 9cb6e8a50..a0ecc2e51 100644
--- a/test/Mono.Linker.Tests.Cases/RequiresCapability/RequiresOnClass.cs
+++ b/test/Mono.Linker.Tests.Cases/RequiresCapability/RequiresOnClass.cs
@@ -719,12 +719,30 @@ namespace Mono.Linker.Tests.Cases.RequiresCapability
instance.GetType ().GetField ("publicField");
}
+ [DynamicallyAccessedMembers (DynamicallyAccessedMemberTypes.All)]
+ class DAMAnnotatedClassAccessedFromRUCScope
+ {
+ [ExpectedWarning ("IL2112", "DAMAnnotatedClassAccessedFromRUCScope.RUCMethod", ProducedBy = ProducedBy.Trimmer)]
+ [RequiresUnreferencedCode ("--RUCMethod--")]
+ public static void RUCMethod () { }
+ }
+
+ // RUC on the callsite to GetType should not suppress warnings about the
+ // attribute on the type.
+ [RequiresUnreferencedCode ("--TestDAMOnTypeAccessInRUCScope--")]
+ static void TestDAMOnTypeAccessInRUCScope (DAMAnnotatedClassAccessedFromRUCScope instance = null)
+ {
+ instance.GetType ().GetMethod ("RUCMethod");
+ }
+
+ [ExpectedWarning ("IL2026", "--TestDAMOnTypeAccessInRUCScope--")]
public static void Test ()
{
TestDAMAccess ();
TestDirectReflectionAccess ();
TestDynamicDependencyAccess ();
TestDAMOnTypeAccess (null);
+ TestDAMOnTypeAccessInRUCScope ();
}
}
diff --git a/test/Mono.Linker.Tests.Cases/Warnings/WarningSuppression/SuppressWarningsInCompilerGeneratedCode.cs b/test/Mono.Linker.Tests.Cases/Warnings/WarningSuppression/SuppressWarningsInCompilerGeneratedCode.cs
index d1e1cc5f6..0c9bd06b1 100644
--- a/test/Mono.Linker.Tests.Cases/Warnings/WarningSuppression/SuppressWarningsInCompilerGeneratedCode.cs
+++ b/test/Mono.Linker.Tests.Cases/Warnings/WarningSuppression/SuppressWarningsInCompilerGeneratedCode.cs
@@ -279,6 +279,7 @@ namespace Mono.Linker.Tests.Cases.Warnings.WarningSuppression
class DynamicallyAccessedLocalFunction
{
+ [ExpectedWarning ("IL2118", "LocalFunction", ProducedBy = ProducedBy.Trimmer)]
[UnconditionalSuppressMessage ("Test", "IL2026")]
public static void TestCallRUCMethodInDynamicallyAccessedLocalFunction ()
{
@@ -290,21 +291,6 @@ namespace Mono.Linker.Tests.Cases.Warnings.WarningSuppression
}
}
- class DynamicallyAccessedLocalFunctionUnused
- {
- [UnconditionalSuppressMessage ("Test", "IL2026")]
- public static void TestCallRUCMethodInDynamicallyAccessedLocalFunction ()
- {
- typeof (DynamicallyAccessedLocalFunctionUnused).RequiresNonPublicMethods ();
-
- // This local function is unused except for the dynamic reference above,
- // so the linker isn't able to figure out which user method it belongs to,
- // and the warning is not suppressed.
- [ExpectedWarning ("IL2026", "--RequiresUnreferencedCodeMethod--", ProducedBy = ProducedBy.Trimmer)]
- void LocalFunction () => RequiresUnreferencedCodeMethod ();
- }
- }
-
static void TestSuppressionOnLocalFunction ()
{
LocalFunction ();
@@ -370,7 +356,6 @@ namespace Mono.Linker.Tests.Cases.Warnings.WarningSuppression
TestGenericLocalFunctionWithAnnotationsAndClosure<TestType> ();
TestCallRUCMethodInLtftnLocalFunction ();
DynamicallyAccessedLocalFunction.TestCallRUCMethodInDynamicallyAccessedLocalFunction ();
- DynamicallyAccessedLocalFunctionUnused.TestCallRUCMethodInDynamicallyAccessedLocalFunction ();
TestSuppressionOnLocalFunction ();
TestSuppressionOnOuterAndLocalFunction ();
TestSuppressionOnOuterWithSameName.Test ();
@@ -441,10 +426,11 @@ namespace Mono.Linker.Tests.Cases.Warnings.WarningSuppression
class DynamicallyAccessedLambda
{
+ [ExpectedWarning ("IL2118", nameof (TestCallRUCMethodInDynamicallyAccessedLambda), ProducedBy = ProducedBy.Trimmer)]
[UnconditionalSuppressMessage ("Test", "IL2026")]
public static void TestCallRUCMethodInDynamicallyAccessedLambda ()
{
- typeof (DynamicallyAccessedLambda).RequiresNonPublicMethods ();
+ typeof (DynamicallyAccessedLambda).RequiresAll ();
Action lambda = () => RequiresUnreferencedCodeMethod ();
@@ -454,10 +440,11 @@ namespace Mono.Linker.Tests.Cases.Warnings.WarningSuppression
class DynamicallyAccessedLambdaUnused
{
+ [ExpectedWarning ("IL2118", nameof (TestCallRUCMethodInDynamicallyAccessedLambda), ProducedBy = ProducedBy.Trimmer)]
[UnconditionalSuppressMessage ("Test", "IL2026")]
public static void TestCallRUCMethodInDynamicallyAccessedLambda ()
{
- typeof (DynamicallyAccessedLambdaUnused).RequiresNonPublicMethods ();
+ typeof (DynamicallyAccessedLambdaUnused).RequiresAll ();
Action _ = () => RequiresUnreferencedCodeMethod ();
}