dotnet / runtime

.NET is a cross-platform runtime for cloud, mobile, desktop, and IoT apps.
https://docs.microsoft.com/dotnet/core/
MIT License
15.27k stars 4.73k forks source link

Random null reference in NativeAOT build #70946

Closed davidfowl closed 2 years ago

davidfowl commented 2 years ago

Description

EXEC : error : Object reference not set to an instance of an object. [C:\Users\david\source\repos\WebApplication35\WebApplication35\WebApplication35.csp
roj]
  System.NullReferenceException: Object reference not set to an instance of an object.
     at System.Collections.Concurrent.ConcurrentDictionary`2.TryGetValueInternal(TKey key, Int32 hashcode, TValue& value)
     at System.Collections.Concurrent.ConcurrentDictionary`2.GetOrAdd(TKey key, Func`2 valueFactory)
     at ILCompiler.DependencyAnalysis.ConstructedEETypeNode.ComputeNonRelocationBasedDependencies(NodeFactory factory) in /_/src/coreclr/tools/aot/ILCom
  piler.Compiler/Compiler/DependencyAnalysis/ConstructedEETypeNode.cs:line 64
     at ILCompiler.DependencyAnalysis.ObjectNode.GetStaticDependencies(NodeFactory factory) in /_/src/coreclr/tools/Common/Compiler/DependencyAnalysis/O
  bjectNode.cs:line 59
     at ILCompiler.DependencyAnalysisFramework.DependencyAnalyzer`2.GetStaticDependenciesImpl(DependencyNodeCore`1 node) in /_/src/coreclr/tools/aot/ILC
  ompiler.DependencyAnalysisFramework/DependencyAnalyzer.cs:line 181
     at ILCompiler.DependencyAnalysisFramework.DependencyAnalyzer`2.GetStaticDependencies(DependencyNodeCore`1 node) in /_/src/coreclr/tools/aot/ILCompi
  ler.DependencyAnalysisFramework/DependencyAnalyzer.cs:line 221
     at ILCompiler.DependencyAnalysisFramework.DependencyAnalyzer`2.ProcessMarkStack() in /_/src/coreclr/tools/aot/ILCompiler.DependencyAnalysisFramewor
  k/DependencyAnalyzer.cs:line 256
     at ILCompiler.DependencyAnalysisFramework.DependencyAnalyzer`2.ComputeMarkedNodes() in /_/src/coreclr/tools/aot/ILCompiler.DependencyAnalysisFramew
  ork/DependencyAnalyzer.cs:line 307
     at ILCompiler.RyuJitCompilation.CompileInternal(String outputFile, ObjectDumper dumper) in /_/src/coreclr/tools/aot/ILCompiler.RyuJit/Compiler/RyuJ
  itCompilation.cs:line 88
     at ILCompiler.Compilation.ILCompiler.ICompilation.Compile(String outputFile, ObjectDumper dumper) in /_/src/coreclr/tools/aot/ILCompiler.Compiler/C
  ompiler/Compilation.cs:line 526
     at ILCompiler.Program.Run(String[] args) in /_/src/coreclr/tools/aot/ILCompiler/Program.cs:line 893
     at ILCompiler.Program.Main(String[] args) in /_/src/coreclr/tools/aot/ILCompiler/Program.cs:line 1085
C:\Program Files\dotnet\sdk\7.0.100-preview.6.22314.18\Sdks\Microsoft.DotNet.ILCompiler\build\Microsoft.NETCore.Native.targets(273,5): error MSB3073: Th
e command ""C:\Users\david\.nuget\packages\runtime.win-x64.microsoft.dotnet.ilcompiler\7.0.0-preview.6.22312.1\tools\\ilc" @"obj\Release\net7.0\win-x64\
native\WebApplication35.ilc.rsp"" exited with code 1. [C:\Users\david\source\repos\WebApplication35\WebApplication35\WebApplication35.csproj]

Reproduction Steps

I only saw this once, a recompile worked but the code was here:

using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Primitives;
using System.Diagnostics.CodeAnalysis;
using System.Linq.Expressions;
using System.Reflection;

var builder = WebApplication.CreateBuilder(args);

var app = builder.Build();

// This works
//IQueryCollection q = default;
// _ = q?["x"];

// This works
// _ = typeof(IQueryCollection).GetMember("Item");

// This works
// [DynamicDependency("get_Item(System.String)", typeof(IQueryCollection))]

// This works
// var getter = typeof(IQueryCollection).GetMethod("get_Item", BindingFlags.Public | BindingFlags.Instance, new[] { typeof(string) })!;

// This works
// var getter = typeof(IHeaderDictionary).GetProperty("Item");

// var q = Expression.Parameter(typeof(IQueryCollection), "q");
// var p = Expression.Property(q, getter);

app.MapGet("/", () => "Hello World");

app.MapGet("/q", ([FromHeader(Name = "Accept")] string accept) => accept);

app.MapGet("/r/{id}", (int id) => $"Hello {id}");

// app.MapGet("/pq", (Person p) => $"Got a person with {p.Name}");

app.MapGet("/p", () => new Person2("Name"));

app.MapPost("/", (Person2 p) => p);

app.MapPost("/async", async (Person2 p) =>
{
    await Task.Delay(1000);
    return p;
});

app.Run();

record struct Person(string Name)
{
    public static bool TryParse(string value, out Person p)
    {
        p = new(value);
        return true;
    }
}

record Person2(string Name)// : IBindableFromHttpContext<Person2>
{
    public static ValueTask<Person2?> BindAsync(HttpContext context, ParameterInfo parameter)
    {
        return new(new Person2("From Bind async"));
    }
}

Expected behavior

No null ref.

Actual behavior

Null reference

Regression?

No response

Known Workarounds

No response

Configuration

No response

Other information

No response

stephentoub commented 2 years ago

Duplicate of https://github.com/dotnet/runtime/issues/69192