/
githubmirror
/
roslyn
Обзор
Документация
Войти
/
githubmirror
/
roslyn
Код
Запросы
0
Пакеты
0
Релизы
0
Аналитика
Безопасность
main
src/Compilers/CSharp/Test/Emit/CodeGen/CodeGenConstructorInitTests.cs
1 367 строк
32 KB
David Barbet
Revert "Update ICSharpCode.Decompiler to 7.2.1.6856 (#67875)"
21 апр 2023, 22:03
21 апр 2023, 22:03
ec92e09
Код
Авторство
О чём код?
// Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. // See the LICENSE file in the project root for more information. #nullable disable using System.Collections.Immutable; using Microsoft.CodeAnalysis.CSharp.Symbols; using Microsoft.CodeAnalysis.CSharp.Syntax; using Microsoft.CodeAnalysis.CSharp.Test.Utilities; using Microsoft.CodeAnalysis.Emit; using Microsoft.CodeAnalysis.Test.Utilities; using Microsoft.CodeAnalysis.Text; using Roslyn.Test.Utilities; using Xunit; namespace Microsoft.CodeAnalysis.CSharp.UnitTests.CodeGen { public class CodeGenConstructorInitTests : CSharpTestBase { [Fact] public void TestImplicitConstructor() { var source = @" class C { static void Main() { C c = new C(); } } "; CompileAndVerify(source, expectedOutput: string.Empty). VerifyIL("C..ctor", @" { // Code size 7 (0x7) .maxstack 1 IL_0000: ldarg.0 IL_0001: call ""object..ctor()"" IL_0006: ret } "); } [Fact] public void TestImplicitConstructorInitializer() { var source = @" class C { C() { } static void Main() { C c = new C(); } } "; CompileAndVerify(source, expectedOutput: string.Empty). VerifyIL("C..ctor", @" { // Code size 7 (0x7) .maxstack 1 IL_0000: ldarg.0 IL_0001: call ""object..ctor()"" IL_0006: ret } "); } [Fact] public void TestExplicitBaseConstructorInitializer() { var source = @" class C { C() : base() { } static void Main() { C c = new C(); } } "; CompileAndVerify(source, expectedOutput: string.Empty). VerifyIL("C..ctor", @" { // Code size 7 (0x7) .maxstack 1 IL_0000: ldarg.0 IL_0001: call ""object..ctor()"" IL_0006: ret } "); } [Fact] public void TestExplicitThisConstructorInitializer() { var source = @" class C { C() : this(1) { } C(int x) { } static void Main() { C c = new C(); } } "; CompileAndVerify(source, expectedOutput: string.Empty). VerifyIL("C..ctor", @" { // Code size 8 (0x8) .maxstack 2 IL_0000: ldarg.0 IL_0001: ldc.i4.1 IL_0002: call ""C..ctor(int)"" IL_0007: ret } "); } [Fact] public void TestExplicitOverloadedBaseConstructorInitializer() { var source = @" class B { public B(int x) { } public B(string x) { } } class C : B { C() : base(1) { } static void Main() { C c = new C(); } } "; CompileAndVerify(source, expectedOutput: string.Empty). VerifyIL("C..ctor", @" { // Code size 8 (0x8) .maxstack 2 IL_0000: ldarg.0 IL_0001: ldc.i4.1 IL_0002: call ""B..ctor(int)"" IL_0007: ret } "); } [Fact] public void TestExplicitOverloadedThisConstructorInitializer() { var source = @" class C { C() : this(1) { } C(int x) { } C(string x) { } static void Main() { C c = new C(); } } "; CompileAndVerify(source, expectedOutput: string.Empty). VerifyIL("C..ctor", @" { // Code size 8 (0x8) .maxstack 2 IL_0000: ldarg.0 IL_0001: ldc.i4.1 IL_0002: call ""C..ctor(int)"" IL_0007: ret } "); } [Fact] public void TestComplexInitialization() { var source = @" class B { private int f = E.Init(3, ""B.f""); public B() { System.Console.WriteLine(""B()""); } public B(int x) : this (x.ToString()) { System.Console.WriteLine(""B(int)""); } public B(string x) : this() { System.Console.WriteLine(""B(string)""); } } class C : B { private int f = E.Init(4, ""C.f""); public C() : this(1) { System.Console.WriteLine(""C()""); } public C(int x) : this(x.ToString()) { System.Console.WriteLine(""C(int)""); } public C(string x) : base(x.Length) { System.Console.WriteLine(""C(string)""); } } class E { static void Main() { C c = new C(); } public static int Init(int value, string message) { System.Console.WriteLine(message); return value; } } "; //interested in execution order and number of field initializations CompileAndVerify(source, expectedOutput: @" C.f B.f B() B(string) B(int) C(string) C(int) C() "); } // Successive Operator On Class [WorkItem(540992, "http://vstfdevdiv:8080/DevDiv2/DevDiv/_workitems/edit/540992")] [Fact] public void TestSuccessiveOperatorOnClass() { var text = @" using System; class C { public int num; public C(int i) { this.num = i; } static void Main(string[] args) { C c1 = new C(1); C c2 = new C(2); C c3 = new C(3); bool verify = c1.num == 1 && c2.num == 2 & c3.num == 3; Console.WriteLine(verify); } } "; var expectedOutput = @"True"; CompileAndVerify(text, expectedOutput: expectedOutput); } [Fact] public void TestInitializerInCtor001() { var source = @" class C { public int I{get;} public C() { I = 42; } static void Main() { C c = new C(); System.Console.WriteLine(c.I); } } "; CompileAndVerify(source, expectedOutput: "42"). VerifyIL("C..ctor", @" { // Code size 15 (0xf) .maxstack 2 IL_0000: ldarg.0 IL_0001: call ""object..ctor()"" IL_0006: ldarg.0 IL_0007: ldc.i4.s 42 IL_0009: stfld ""int C.<I>k__BackingField"" IL_000e: ret } "); } [Fact] public void TestInitializerInCtor002() { var source = @" public struct S { public int X{get;} public int Y{get;} public S(int dummy) { X = 42; Y = X; } public static void Main() { S s = new S(1); System.Console.WriteLine(s.Y); } } "; CompileAndVerify(source, expectedOutput: "42"). VerifyIL("S..ctor", @" { // Code size 21 (0x15) .maxstack 2 IL_0000: ldarg.0 IL_0001: ldc.i4.s 42 IL_0003: stfld ""int S.<X>k__BackingField"" IL_0008: ldarg.0 IL_0009: ldarg.0 IL_000a: call ""readonly int S.X.get"" IL_000f: stfld ""int S.<Y>k__BackingField"" IL_0014: ret } "); } [Fact] public void TestInitializerInCtor003() { var source = @" struct C { public int I{get;} public int J{get; set;} public C(int arg) { I = 33; J = I; I = J; I = arg; } static void Main() { C c = new C(42); System.Console.WriteLine(c.I); } } "; CompileAndVerify(source, expectedOutput: "42"). VerifyIL("C..ctor(int)", @" { // Code size 40 (0x28) .maxstack 2 IL_0000: ldarg.0 IL_0001: ldc.i4.s 33 IL_0003: stfld ""int C.<I>k__BackingField"" IL_0008: ldarg.0 IL_0009: ldarg.0 IL_000a: call ""readonly int C.I.get"" IL_000f: call ""void C.J.set"" IL_0014: ldarg.0 IL_0015: ldarg.0 IL_0016: call ""readonly int C.J.get"" IL_001b: stfld ""int C.<I>k__BackingField"" IL_0020: ldarg.0 IL_0021: ldarg.1 IL_0022: stfld ""int C.<I>k__BackingField"" IL_0027: ret } "); } [Fact] public void TestInitializerInCtor004() { var source = @" struct C { public static int I{get;} public static int J{get; set;} static C() { I = 33; J = I; I = J; I = 42; } static void Main() { System.Console.WriteLine(C.I); } } "; CompileAndVerify(source, expectedOutput: "42"). VerifyIL("C..cctor()", @" { // Code size 35 (0x23) .maxstack 1 IL_0000: ldc.i4.s 33 IL_0002: stsfld ""int C.<I>k__BackingField"" IL_0007: call ""int C.I.get"" IL_000c: call ""void C.J.set"" IL_0011: call ""int C.J.get"" IL_0016: stsfld ""int C.<I>k__BackingField"" IL_001b: ldc.i4.s 42 IL_001d: stsfld ""int C.<I>k__BackingField"" IL_0022: ret } "); } [Fact] public void TestInitializerInCtor005() { var source = @" struct C { static int P1 { get; } static int y = (P1 = 123); static void Main() { System.Console.WriteLine(y); System.Console.WriteLine(P1); } } "; CompileAndVerify(source, expectedOutput: @"123 123"). VerifyIL("C..cctor()", @" { // Code size 14 (0xe) .maxstack 2 IL_0000: ldc.i4.s 123 IL_0002: dup IL_0003: stsfld ""int C.<P1>k__BackingField"" IL_0008: stsfld ""int C.y"" IL_000d: ret } "); } [Fact] public void TestInitializerInCtor006() { var source = @" struct C { static int P1 { get; } static int y { get; } = (P1 = 123); static void Main() { System.Console.WriteLine(y); System.Console.WriteLine(P1); } } "; CompileAndVerify(source, expectedOutput: @"123 123"). VerifyIL("C..cctor()", @" { // Code size 14 (0xe) .maxstack 2 IL_0000: ldc.i4.s 123 IL_0002: dup IL_0003: stsfld ""int C.<P1>k__BackingField"" IL_0008: stsfld ""int C.<y>k__BackingField"" IL_000d: ret } "); } [WorkItem(4383, "https://github.com/dotnet/roslyn/issues/4383")] [Fact] public void DecimalConstInit001() { var source = @" using System; using System.Collections.Generic; public static class Module1 { public static void Main() { Console.WriteLine(ClassWithStaticField.Dictionary[""String3""]); } } public class ClassWithStaticField { public const decimal DecimalConstant = 375; private static Dictionary<String, Single> DictionaryField = new Dictionary<String, Single> { {""String1"", 1.0F}, {""String2"", 2.0F}, {""String3"", 3.0F} }; public static Dictionary<String, Single> Dictionary { get { return DictionaryField; } } } "; CompileAndVerify(source, expectedOutput: "3"). VerifyIL("ClassWithStaticField..cctor", @" { // Code size 74 (0x4a) .maxstack 4 IL_0000: ldc.i4 0x177 IL_0005: newobj ""decimal..ctor(int)"" IL_000a: stsfld ""decimal ClassWithStaticField.DecimalConstant"" IL_000f: newobj ""System.Collections.Generic.Dictionary<string, float>..ctor()"" IL_0014: dup IL_0015: ldstr ""String1"" IL_001a: ldc.r4 1 IL_001f: callvirt ""void System.Collections.Generic.Dictionary<string, float>.Add(string, float)"" IL_0024: dup IL_0025: ldstr ""String2"" IL_002a: ldc.r4 2 IL_002f: callvirt ""void System.Collections.Generic.Dictionary<string, float>.Add(string, float)"" IL_0034: dup IL_0035: ldstr ""String3"" IL_003a: ldc.r4 3 IL_003f: callvirt ""void System.Collections.Generic.Dictionary<string, float>.Add(string, float)"" IL_0044: stsfld ""System.Collections.Generic.Dictionary<string, float> ClassWithStaticField.DictionaryField"" IL_0049: ret } "); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void DecimalConstInit002() { var source1 = @" class C { const decimal d1 = 0.1m; } "; var source2 = @" class C { static readonly decimal d1 = 0.1m; } "; var expectedIL = @" { // Code size 16 (0x10) .maxstack 5 IL_0000: ldc.i4.1 IL_0001: ldc.i4.0 IL_0002: ldc.i4.0 IL_0003: ldc.i4.0 IL_0004: ldc.i4.1 IL_0005: newobj ""decimal..ctor(int, int, int, bool, byte)"" IL_000a: stsfld ""decimal C.d1"" IL_000f: ret } "; CompileAndVerify(source1).VerifyIL("C..cctor", expectedIL); CompileAndVerify(source2).VerifyIL("C..cctor", expectedIL); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void DecimalConstInit003() { var source1 = @" class C { const decimal d1 = 0.0m; } "; var source2 = @" class C { static readonly decimal d1 = 0.0m; } "; var expectedIL = @" { // Code size 16 (0x10) .maxstack 5 IL_0000: ldc.i4.0 IL_0001: ldc.i4.0 IL_0002: ldc.i4.0 IL_0003: ldc.i4.0 IL_0004: ldc.i4.1 IL_0005: newobj ""decimal..ctor(int, int, int, bool, byte)"" IL_000a: stsfld ""decimal C.d1"" IL_000f: ret } "; CompileAndVerify(source1).VerifyIL("C..cctor", expectedIL); CompileAndVerify(source2).VerifyIL("C..cctor", expectedIL); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void DecimalConstInit004() { var source1 = @" class C { const decimal d1 = default; const decimal d2 = 0; const decimal d3 = 0m; } "; var source2 = @" class C { static readonly decimal d1 = default; static readonly decimal d2 = 0; static readonly decimal d3 = 0m; } "; var options = TestOptions.DebugDll.WithMetadataImportOptions(MetadataImportOptions.All); CompileAndVerify(source1, symbolValidator: validator, options: options); CompileAndVerify(source2, symbolValidator: validator, options: options); void validator(ModuleSymbol module) { var type = module.ContainingAssembly.GetTypeByMetadataName("C"); Assert.Null(type.GetMember(".cctor")); } } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void StaticLambdaConstructorAlwaysEmitted() { var source = @" class C { void M() { System.Action a1 = () => { }; } } "; CompileAndVerify(source). VerifyIL("C.<>c..cctor", @" { // Code size 11 (0xb) .maxstack 1 IL_0000: newobj ""C.<>c..ctor()"" IL_0005: stsfld ""C.<>c C.<>c.<>9"" IL_000a: ret } "); } [WorkItem(217748, "https://devdiv.visualstudio.com/DevDiv/_workitems?_a=edit&id=217748")] [Fact] public void BadExpressionConstructor() { string source = @"class C { static dynamic F() => 0; dynamic d = F() * 2; }"; CreateCompilationWithMscorlib40AndSystemCore(source).VerifyEmitDiagnostics( // (4,17): error CS0656: Missing compiler required member 'Microsoft.CSharp.RuntimeBinder.CSharpArgumentInfo.Create' // dynamic d = F() * 2; Diagnostic(ErrorCode.ERR_MissingPredefinedMember, "F()").WithArguments("Microsoft.CSharp.RuntimeBinder.CSharpArgumentInfo", "Create").WithLocation(4, 17)); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_01() { string source = @" #nullable enable class C { static int i = 0; static bool b = false; }"; CompileAndVerify( source, symbolValidator: validator, options: TestOptions.DebugDll.WithMetadataImportOptions(MetadataImportOptions.All)); void validator(ModuleSymbol module) { var type = module.ContainingAssembly.GetTypeByMetadataName("C"); Assert.Null(type.GetMember(".cctor")); } } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_02() { string source = @" #nullable enable class C { static string s = null!; }"; CompileAndVerify( source, symbolValidator: validator, options: TestOptions.DebugDll.WithMetadataImportOptions(MetadataImportOptions.All)); void validator(ModuleSymbol module) { var type = module.ContainingAssembly.GetTypeByMetadataName("C"); Assert.Null(type.GetMember(".cctor")); } } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_03() { string source = @" #nullable enable class C { static (int, object) pair = (0, null!); }"; CompileAndVerify(source).VerifyIL("C..cctor()", @"{ // Code size 13 (0xd) .maxstack 2 IL_0000: ldc.i4.0 IL_0001: ldnull IL_0002: newobj ""System.ValueTuple<int, object>..ctor(int, object)"" IL_0007: stsfld ""System.ValueTuple<int, object> C.pair"" IL_000c: ret }"); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_04() { string source = @" #nullable enable class C { static (int, object) pair1 = default; static (int, object) pair2 = default((int, object)); static (int, object) pair3 = default!; static (int, object) pair4 = default((int, object))!; }"; // note: we could make the synthesized constructor smarter and realize that // nothing needs to be emitted for these initializers. // but it doesn't serve any realistic scenarios at this time. CompileAndVerify(source).VerifyIL("C..cctor()", @" { // Code size 1 (0x1) .maxstack 0 IL_0000: ret }"); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_05() { string source = @" #nullable enable class C { static C instance = default!; }"; CompileAndVerify( source, symbolValidator: validator, options: TestOptions.DebugDll.WithMetadataImportOptions(MetadataImportOptions.All)); void validator(ModuleSymbol module) { var type = module.ContainingAssembly.GetTypeByMetadataName("C"); Assert.Null(type.GetMember(".cctor")); } } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_06() { string source = @" #nullable enable struct S { public int x; public int y; } class C { static S field1 = default; static S field2 = default(S); static S field3 = new S(); }"; // note: we could make the synthesized constructor smarter and realize that // nothing needs to be emitted for these initializers. // but it doesn't serve any realistic scenarios at this time. CompileAndVerify(source).VerifyIL("C..cctor()", @" { // Code size 1 (0x1) .maxstack 0 IL_0000: ret }"); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_08() { string source = @" #nullable enable class C { static int x = 1; }"; CompileAndVerify(source).VerifyIL("C..cctor()", @" { // Code size 7 (0x7) .maxstack 1 IL_0000: ldc.i4.1 IL_0001: stsfld ""int C.x"" IL_0006: ret }"); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_09() { string source = @" #nullable enable struct S { public int x; } class C { static S? s1 = null; static S? s2 = default(S?); }"; CompileAndVerify( source, symbolValidator: validator, options: TestOptions.DebugDll.WithMetadataImportOptions(MetadataImportOptions.All)); void validator(ModuleSymbol module) { var type = module.ContainingAssembly.GetTypeByMetadataName("C"); Assert.Null(type.GetMember(".cctor")); } } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_10() { string source = @" #nullable enable struct S { public int x; } class C { static S? s1 = default; }"; // note: we could make the synthesized constructor smarter and realize that // nothing needs to be emitted for these initializers. // but it doesn't serve any realistic scenarios at this time. CompileAndVerify(source).VerifyIL("C..cctor()", @" { // Code size 1 (0x1) .maxstack 0 IL_0000: ret }"); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_11() { string source = @" #nullable enable struct S { public int x; } class C { static S? s1 = new S?(); }"; // note: we could make the synthesized constructor smarter and realize that // nothing needs to be emitted for these initializers. // but it doesn't serve any realistic scenarios at this time. CompileAndVerify(source).VerifyIL("C..cctor()", @" { // Code size 1 (0x1) .maxstack 0 IL_0000: ret }"); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_12() { string source = @" #nullable enable struct S { public int x; } class C { static S? s1 = default(S); }"; CompileAndVerify(source).VerifyIL("C..cctor()", @" { // Code size 20 (0x14) .maxstack 1 .locals init (S V_0) IL_0000: ldloca.s V_0 IL_0002: initobj ""S"" IL_0008: ldloc.0 IL_0009: newobj ""S?..ctor(S)"" IL_000e: stsfld ""S? C.s1"" IL_0013: ret }"); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_13() { string source = @" #nullable enable struct S { public int x; } class C { static S? s1 = new S(); }"; CompileAndVerify(source).VerifyIL("C..cctor()", @" { // Code size 20 (0x14) .maxstack 1 .locals init (S V_0) IL_0000: ldloca.s V_0 IL_0002: initobj ""S"" IL_0008: ldloc.0 IL_0009: newobj ""S?..ctor(S)"" IL_000e: stsfld ""S? C.s1"" IL_0013: ret }"); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_14() { string source = @" #nullable enable struct S { public int x; } class C { static object s1 = default(S); }"; CompileAndVerify(source).VerifyIL("C..cctor()", @" { // Code size 20 (0x14) .maxstack 1 .locals init (S V_0) IL_0000: ldloca.s V_0 IL_0002: initobj ""S"" IL_0008: ldloc.0 IL_0009: box ""S"" IL_000e: stsfld ""object C.s1"" IL_0013: ret }"); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_15() { string source = @" #nullable enable struct S { public int x; } class C { static object s1 = new S(); }"; CompileAndVerify(source).VerifyIL("C..cctor()", @" { // Code size 20 (0x14) .maxstack 1 .locals init (S V_0) IL_0000: ldloca.s V_0 IL_0002: initobj ""S"" IL_0008: ldloc.0 IL_0009: box ""S"" IL_000e: stsfld ""object C.s1"" IL_0013: ret }"); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_16() { string source = @" #nullable enable struct S { public int x; } class C { static object s1 = default(S?); static object s2 = (S?)null; static object s3 = new S?(); }"; // note: we could make the synthesized constructor smarter and realize that // nothing needs to be emitted for these initializers. // but it doesn't serve any realistic scenarios at this time. CompileAndVerify(source).VerifyIL("C..cctor()", @" { // Code size 1 (0x1) .maxstack 0 IL_0000: ret }"); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void SkipSynthesizedStaticConstructor_17() { string source = @" unsafe class C { static System.IntPtr s1 = (System.IntPtr)0; static System.UIntPtr s2 = (System.UIntPtr)0; static void* s3 = (void*)0; }"; // note: we could make the synthesized constructor smarter and realize that // nothing needs to be emitted for the `(void*)0` initializer. // but it doesn't serve any realistic scenarios at this time. CompileAndVerify(source, options: TestOptions.UnsafeDebugDll, verify: Verification.Skipped).VerifyIL("C..cctor()", @" { // Code size 31 (0x1f) .maxstack 1 IL_0000: ldc.i4.0 IL_0001: call ""System.IntPtr System.IntPtr.op_Explicit(int)"" IL_0006: stsfld ""System.IntPtr C.s1"" IL_000b: ldc.i4.0 IL_000c: conv.i8 IL_000d: call ""System.UIntPtr System.UIntPtr.op_Explicit(ulong)"" IL_0012: stsfld ""System.UIntPtr C.s2"" IL_0017: ldc.i4.0 IL_0018: conv.i IL_0019: stsfld ""void* C.s3"" IL_001e: ret }"); } [WorkItem(543606, "http://vstfdevdiv:8080/DevDiv2/DevDiv/_workitems/edit/543606")] [ConditionalFact(typeof(DesktopOnly))] public void StaticNullInitializerHasNoEffectOnTypeIL() { var source1 = @" #nullable enable class C { static string s1; }"; var source2 = @" #nullable enable class C { static string s1 = null!; }"; var expectedIL = @" .class private auto ansi beforefieldinit C extends [mscorlib]System.Object { // Fields .field private static string s1 .custom instance void System.Runtime.CompilerServices.NullableAttribute::.ctor(uint8) = ( 01 00 01 00 00 ) // Methods .method public hidebysig specialname rtspecialname instance void .ctor () cil managed { // Method begins at RVA 0x207f // Code size 7 (0x7) .maxstack 8 IL_0000: ldarg.0 IL_0001: call instance void [mscorlib]System.Object::.ctor() IL_0006: ret } // end of method C::.ctor } // end of class C "; var parseOptions = TestOptions.Regular.WithNoRefSafetyRulesAttribute(); CompileAndVerify(source1, parseOptions: parseOptions).VerifyTypeIL("C", expectedIL); CompileAndVerify(source2, parseOptions: parseOptions).VerifyTypeIL("C", expectedIL); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void ExplicitStaticConstructor_01() { string source = @" #nullable enable class C { static string x = null!; static C() { } }"; CompileAndVerify(source).VerifyIL("C..cctor()", @" { // Code size 1 (0x1) .maxstack 0 IL_0000: ret }"); } [WorkItem(42985, "https://github.com/dotnet/roslyn/issues/42985")] [Fact] public void ExplicitStaticConstructor_02() { string source = @" #nullable enable class C { static string x; static C() { x = null!; } }"; CompileAndVerify(source).VerifyIL("C..cctor()", @" { // Code size 7 (0x7) .maxstack 1 IL_0000: ldnull IL_0001: stsfld ""string C.x"" IL_0006: ret }"); } [Fact, WorkItem(55797, "https://github.com/dotnet/roslyn/issues/55797")] public void TwoParameterlessConstructors() { string source = @" public class C { public C() : Garbage() { } } "; var comp = CreateCompilation(source); comp.VerifyDiagnostics( // (4,12): error CS0501: 'C.C()' must declare a body because it is not marked abstract, extern, or partial // public C() : Garbage() Diagnostic(ErrorCode.ERR_ConcreteMissingBody, "C").WithArguments("C.C()").WithLocation(4, 12), // (4,18): error CS1018: Keyword 'this' or 'base' expected // public C() : Garbage() Diagnostic(ErrorCode.ERR_ThisOrBaseExpected, "Garbage").WithLocation(4, 18), // (4,18): error CS1002: ; expected // public C() : Garbage() Diagnostic(ErrorCode.ERR_SemicolonExpected, "Garbage").WithLocation(4, 18), // (4,18): error CS1520: Method must have a return type // public C() : Garbage() Diagnostic(ErrorCode.ERR_MemberNeedsType, "Garbage").WithLocation(4, 18), // (4,18): error CS0121: The call is ambiguous between the following methods or properties: 'C.C()' and 'C.C()' // public C() : Garbage() Diagnostic(ErrorCode.ERR_AmbigCall, "").WithArguments("C.C()", "C.C()").WithLocation(4, 18) ); } [Fact, WorkItem(55797, "https://github.com/dotnet/roslyn/issues/55797")] public void TwoParameterlessConstructors_2() { string source = @" public class C { public C() : this() { } public C() { } } "; var comp = CreateCompilation(source); comp.VerifyDiagnostics( // (4,18): error CS0121: The call is ambiguous between the following methods or properties: 'C.C()' and 'C.C()' // public C() : this() Diagnostic(ErrorCode.ERR_AmbigCall, "this").WithArguments("C.C()", "C.C()").WithLocation(4, 18), // (7,12): error CS0111: Type 'C' already defines a member called 'C' with the same parameter types // public C() Diagnostic(ErrorCode.ERR_MemberAlreadyExists, "C").WithArguments("C", "C").WithLocation(7, 12) ); } [Fact, WorkItem(55797, "https://github.com/dotnet/roslyn/issues/55797")] public void TwoParameterlessConstructors_3() { string source = @" public class C { public C() : this() { } public C2() { } } "; var comp = CreateCompilation(source); comp.VerifyDiagnostics( // (4,18): error CS0121: The call is ambiguous between the following methods or properties: 'C.C()' and 'C.C()' // public C() : this() Diagnostic(ErrorCode.ERR_AmbigCall, "this").WithArguments("C.C()", "C.C()").WithLocation(4, 18), // (7,12): error CS1520: Method must have a return type // public C2() Diagnostic(ErrorCode.ERR_MemberNeedsType, "C2").WithLocation(7, 12) ); } [Fact, WorkItem(55797, "https://github.com/dotnet/roslyn/issues/55797")] public void TwoParameterlessConstructors_Struct() { string source = @" public struct C { public C() : this() { } public C2() { } } "; var comp = CreateCompilation(source); comp.VerifyDiagnostics( // (4,18): error CS0121: The call is ambiguous between the following methods or properties: 'C.C()' and 'C.C()' // public C() : this() Diagnostic(ErrorCode.ERR_AmbigCall, "this").WithArguments("C.C()", "C.C()").WithLocation(4, 18), // (7,12): error CS1520: Method must have a return type // public C2() Diagnostic(ErrorCode.ERR_MemberNeedsType, "C2").WithLocation(7, 12) ); } } }