Skip to content

Unnecessary trim analysis warnings from generics #113249

@MichalStrehovsky

Description

@MichalStrehovsky

Below program generates warnings from ILLink. There are no warnings from the analyzer or ILC. Feels like there should be no warnings.

I think we already discussed this in the past but couldn't find a bug. This pattern came up in a discussion with an internal customer.

    D:\ctor\Program.cs(8,5): Trim analysis warning IL2091: Program.<<Main>$>g__NullOrNillValue|0_0<T>(): 'T' generic argument does not satisfy 'DynamicallyAccessedMemberTypes.PublicParameterlessConstructor' in 'Nilable<T>'. The generic parameter 'T' of 'Program.<<Main>$>g__NullOrNillValue|0_0<T>()' does not have matching annotations. The source value must declare at least the same requirements as those declared on the target location it is assigned to.
    D:\ctor\Program.cs(9,9): Trim analysis warning IL2091: Program.<<Main>$>g__NullOrNillValue|0_0<T>(): 'T' generic argument does not satisfy 'DynamicallyAccessedMemberTypes.PublicParameterlessConstructor' in 'Nilable<T>'. The generic parameter 'T' of 'Program.<<Main>$>g__NullOrNillValue|0_0<T>()' does not have matching annotations. The source value must declare at least the same requirements as those declared on the target location it is assigned to.
    D:\ctor\Program.cs(3,1): Trim analysis warning IL2091: Program.<Main>$(String[]): 'T' generic argument does not satisfy 'DynamicallyAccessedMemberTypes.PublicParameterlessConstructor' in 'Nilable<T>'. The generic parameter 'T' of 'Program.<<Main>$>g__NullOrNillValue|0_0<T>()' does not have matching annotations. The source value must declare at least the same requirements as those declared on the target location it is assigned to.
using System.Diagnostics.CodeAnalysis;

NullOrNillValue<Test>();

[return: MaybeNull]
static T NullOrNillValue<T>()
{
    if (default(T) is Nilable<T> nilable)
        return nilable.CreateNil();
    else
        return default;
}

public interface Nilable<
  [DynamicallyAccessedMembers(DynamicallyAccessedMemberTypes.PublicParameterlessConstructor)]
T
>
{
    sealed T CreateNil() => Activator.CreateInstance<T>();
    bool FNil();
}

struct Test : Nilable<Test>
{
    public Test() => Console.WriteLine("Hello");

    public bool FNil() => false;
}

Metadata

Metadata

Assignees

Labels

area-Tools-ILLink.NET linker development as well as trimming analyzers

Type

No type

Projects

Status

No status

Relationships

None yet

Development

No branches or pull requests

Issue actions