Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add test case for interfaces without impls for whole hierarchy #98540

Closed
wants to merge 6 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,12 @@ public Task DefaultInterfaceMethodCallIntoClass ()
return RunTest (allowMissingWarnings: true);
}

[Fact]
public Task DimProvidedByUnreferencedIfaceInHierarchy ()
{
return RunTest (allowMissingWarnings: true);
}

[Fact]
public Task GenericDefaultInterfaceMethods ()
{
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,87 @@

// 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.

.assembly extern mscorlib { }

.assembly 'library' { }

.class public auto ansi abstract sealed beforefieldinit Program
extends [mscorlib]System.Object
{
// Nested Types
.class interface nested public auto ansi abstract beforefieldinit IFoo
{
// Methods
.method public hidebysig newslot abstract virtual
instance void Method () cil managed
{
} // end of method IFoo::Method

} // end of class IFoo

.class interface nested public auto ansi abstract beforefieldinit IBar
implements Program/IFoo
{
// Methods
.method public final hidebysig virtual
instance void Program.IFoo.Method () cil managed
{
.override method instance void Program/IFoo::Method()
// Method begins at RVA 0x2068
// Code size 2 (0x2)
.maxstack 8

IL_0000: nop
IL_0001: ret
} // end of method IBar::Program.IFoo.Method

} // end of class IBar

.class interface nested public auto ansi abstract beforefieldinit IBaz
implements Program/IBar
{
} // end of class IBaz

.class nested public auto ansi beforefieldinit MyFoo
extends [mscorlib]System.Object
implements Program/IBaz
{
// Methods
.method public hidebysig specialname rtspecialname
instance void .ctor () cil managed
{
// Method begins at RVA 0x2076
// Code size 8 (0x8)
.maxstack 8

IL_0000: ldarg.0
IL_0001: call instance void [mscorlib]System.Object::.ctor()
IL_0006: nop
IL_0007: ret
} // end of method MyFoo::.ctor

} // end of class MyFoo


// Methods
.method public hidebysig static
void CallMethod (
class Program/IFoo foo
) cil managed
{
.custom instance void [mscorlib]mscorlib.CompilerServices.NullableContextAttribute::.ctor(uint8) = (
01 00 01 00 00
)
// Method begins at RVA 0x2050
// Code size 9 (0x9)
.maxstack 8

IL_0000: nop
IL_0001: ldarg.0
IL_0002: callvirt instance void Program/IFoo::Method()
IL_0007: nop
IL_0008: ret
} // end of method Program::CallMethod

} // end of class Program
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
// 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.

.assembly extern mscorlib { }

.assembly 'library' { }

.class public auto ansi abstract sealed beforefieldinit Program
extends [mscorlib]System.Object
{
// Nested Types
.class interface nested public auto ansi abstract beforefieldinit IBase
{
// Methods
.method public hidebysig abstract virtual static
void Method () cil managed
{
} // end of method IBase::Method

} // end of class IBase

.class interface nested public auto ansi abstract beforefieldinit I2
implements Program/IBase
{
// Methods
.method public hidebysig static
void Program.IBase.Method () cil managed
{
.override method void Program/IBase::Method()
// Method begins at RVA 0x205f
// Code size 2 (0x2)
.maxstack 8

IL_0000: nop
IL_0001: ret
} // end of method I2::Program.IBase.Method

} // end of class I2

.class interface nested public auto ansi abstract beforefieldinit I3
implements Program/I2
{
} // end of class I3

.class interface nested public auto ansi abstract beforefieldinit I4
implements Program/I3
{
} // end of class I4


// Methods
.method public hidebysig static
void CallMethod<(Program/IBase) T> () cil managed
{
.param constraint T, Program/IBase
.custom instance void [mscorlib]mscorlib.CompilerServices.NullableAttribute::.ctor(uint8) = (
01 00 01 00 00
)
// Method begins at RVA 0x2050
// Code size 14 (0xe)
.maxstack 8

IL_0000: nop
IL_0001: constrained. !!T
IL_0007: call void Program/IBase::Method()
IL_000c: nop
IL_000d: ret
} // end of method Program::CallMethod

} // end of class Program
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@


using Mono.Linker.Tests.Cases.Expectations.Assertions;
using Mono.Linker.Tests.Cases.Expectations.Metadata;

namespace Mono.Linker.Tests.Cases.Inheritance.Interfaces.DefaultInterfaceMethods
{
[SetupLinkerArgument ("--skip-unresolved", "true")]
[TestCaseRequirements (TestRunCharacteristics.SupportsDefaultInterfaceMethods, "Requires support for default interface methods")]
[Define ("IL_ASSEMBLY_AVAILABLE")]
[SetupCompileBefore ("library.dll", new[] { "Dependencies/DimProvidedByUnreferencedIfaceInHierarchy.il" })]
[SkipILVerify]

#if IL_ASSEMBLY_AVAILABLE
[KeptMemberInAssembly ("library.dll", typeof(Program.IFoo), "Method()")]
// https://github.com/dotnet/runtime/issues/98536
// [KeptTypeInAssembly ("library.dll", typeof(Program.IBar))]
// [KeptMemberInAssembly ("library.dll", typeof(Program.IBar), "Program.IFoo.Method()")]
// [KeptInterfaceOnTypeInAssembly ("library.dll", typeof (Program.IBar), "library.dll", typeof (Program.IFoo))]
// [KeptInterfaceOnTypeInAssembly ("library.dll", typeof (Program.MyFoo), "library.dll", typeof (Program.IBaz))]
// [KeptTypeInAssembly ("library.dll", typeof(Program.IBaz))]
// [KeptInterfaceOnTypeInAssembly ("library.dll", typeof (Program.IBaz), "library.dll", typeof (Program.IBar))]
[KeptMemberInAssembly ("library.dll", typeof(Program), "CallMethod(Program/IFoo)")]
#endif
class DimProvidedByUnreferencedIfaceInHierarchy
{
static void Main ()
{
#if IL_ASSEMBLY_AVAILABLE
Program.IFoo foo = new Program.MyFoo ();
Program.CallMethod(foo);
#endif
}
}
}



// public static class Program
// {
// [Kept]
// interface IFoo
// {
// void Method();
// }

// [Kept]
// interface IBar : IFoo
// {
// [Kept]
// void IFoo.Method() { }
// }

// [Kept]
// interface IBaz: IBar /* not IFoo */
// {
// }

// [Kept]
// [KeptInterface(typeof(IBaz))]
// class MyFoo : IBaz /* not IBar, not IFoo */
// { }

// static void CallMethod(IFoo foo)
// {
// foo.Method();
// }
// }
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@


using Mono.Linker.Tests.Cases.Expectations.Assertions;
using Mono.Linker.Tests.Cases.Expectations.Metadata;

namespace Mono.Linker.Tests.Cases.Inheritance.Interfaces.DefaultInterfaceMethods
{
[SetupLinkerArgument ("--skip-unresolved", "true")]
[TestCaseRequirements (TestRunCharacteristics.SupportsDefaultInterfaceMethods, "Requires support for default interface methods")]
[Define ("IL_ASSEMBLY_AVAILABLE")]
[SetupCompileBefore ("library.dll", new[] { "Dependencies/StaticDimProvidedByUnreferencedIfaceInHierarchy.il" })]
[SkipILVerify]

#if IL_ASSEMBLY_AVAILABLE
[KeptMemberInAssembly ("library.dll", typeof(Program), "CallMethod<#1>()")]
[KeptTypeInAssembly ("library.dll", typeof(Program.IBase))]
[KeptMemberInAssembly ("library.dll", typeof(Program.IBase), "Method()")]
[KeptTypeInAssembly ("library.dll", typeof(Program.I4))]
// https://github.com/dotnet/runtime/issues/98536
// [KeptTypeInAssembly ("library.dll", typeof(Program.I2))]
// [KeptMemberInAssembly ("library.dll", typeof(Program.I2), "Program.IBase.Method()")]
// [KeptInterfaceOnTypeInAssembly ("library.dll", typeof (Program.I2), "library.dll", typeof (Program.IBase))]
// [KeptTypeInAssembly ("library.dll", typeof(Program.I3))]
// [KeptInterfaceOnTypeInAssembly ("library.dll", typeof (Program.I3), "library.dll", typeof (Program.I2))]
// [KeptInterfaceOnTypeInAssembly ("library.dll", typeof (Program.I4), "library.dll", typeof (Program.I3))]
#endif
class StaticDimProvidedByUnreferencedIfaceInHierarchy
{
static void Main ()
{
#if IL_ASSEMBLY_AVAILABLE
Program.CallMethod<Program.I4>();
#endif
}
}
}



// public static class Program
// {
// [Kept]
// interface IBase
// {
// [Kept]
// static abstract void Method();
// }

// [Kept]
// [KeptInterface(typeof(IBase)]
// interface I2 : IBase
// {
// [Kept]
// static void IBase.Method() { }
// }

// [Kept]
// [KeptInterface(typeof(I2)]
// interface I3 : I2 { }

// [Kept]
// [KeptInterface(typeof(I3)]
// interface I4 : I3 { }

// [Kept]
// static void CallMethod<T>() where T : IBase
// {
// T.Method();
// }
// }
Loading