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

Internal Compiler Error: NullReferenceException / NullableWalker.LocalState.SetValue for switch over bool in lambda #55227

Closed
bernd5 opened this issue Jul 29, 2021 · 5 comments · Fixed by #56031

Comments

@bernd5
Copy link
Contributor

bernd5 commented Jul 29, 2021

Version Used: 4.0.0-3.21358.10

Steps to Reproduce:
Compile / Paste the following code into the editor (reduced code):

using System;

static class Program
{
    public static void Main()
    {
    }

    public static object Foo(object a)
    {
        var isNullCheck = new global::System.Func<object, object>((p) =>
        {
            switch (p == null)
            {
                case var isnull:
                    return isnull;
            }
        });
        return isNullCheck(a);
    }
}

Expected Behavior:
Compilation without error

Actual Behavior:
Compiler error NullReferenceException

Stacktrace

StreamJsonRpc.RemoteInvocationException: Der Objektverweis wurde nicht auf eine Objektinstanz festgelegt.
   at StreamJsonRpc.JsonRpc.<InvokeCoreAsync>d__139`1.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
   at Microsoft.CodeAnalysis.Remote.BrokeredServiceConnection`1.<TryInvokeAsync>d__17`1.MoveNext()
--- End of stack trace from previous location where exception was thrown ---
   at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
   at Microsoft.VisualStudio.Telemetry.WindowsErrorReporting.WatsonReport.GetClrWatsonExceptionInfo(Exception exceptionObject)
RPC server exception:
System.NullReferenceException: Der Objektverweis wurde nicht auf eine Objektinstanz festgelegt.
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.LocalState.SetValue(Int32 id, Int32 index, NullableFlowState value)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.DeclareLocal(LocalSymbol local)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.DeclareLocals(ImmutableArray`1 locals)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.VisitSwitchStatementDispatch(BoundSwitchStatement node)
      bei Microsoft.CodeAnalysis.CSharp.AbstractFlowPass`2.VisitSwitchStatement(BoundSwitchStatement node)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.VisitStatementsWithLocalFunctions(BoundBlock block)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.VisitBlock(BoundBlock node)
      bei Microsoft.CodeAnalysis.CSharp.AbstractFlowPass`2.VisitWithStackGuard(BoundNode node)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.AnalyzeLocalFunctionOrLambda(IBoundLambdaOrFunction lambdaOrFunction, MethodSymbol lambdaOrFunctionSymbol, LocalState state, MethodSymbol delegateInvokeMethod, Boolean useDelegateInvokeParameterTypes, Boolean useDelegateInvokeReturnType)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.VisitLambda(BoundLambda node, NamedTypeSymbol delegateTypeOpt, Optional`1 initialState)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.VisitDelegateCreationExpression(BoundDelegateCreationExpression node)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.VisitExpressionWithoutStackGuard(BoundExpression node)
      bei Microsoft.CodeAnalysis.CSharp.BoundTreeVisitor.VisitExpressionWithStackGuard(BoundExpression node)
      bei Microsoft.CodeAnalysis.CSharp.BoundTreeVisitor.VisitExpressionWithStackGuard(Int32& recursionDepth, BoundExpression node)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.VisitOptionalImplicitConversion(BoundExpression expr, TypeWithAnnotations targetTypeOpt, Boolean useLegacyWarnings, Boolean trackMembers, AssignmentKind assignmentKind)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.VisitLocalDeclaration(BoundLocalDeclaration node)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.VisitStatementsWithLocalFunctions(BoundBlock block)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.VisitBlock(BoundBlock node)
      bei Microsoft.CodeAnalysis.CSharp.AbstractFlowPass`2.VisitWithStackGuard(BoundNode node)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.Visit(BoundNode node)
      bei Microsoft.CodeAnalysis.CSharp.AbstractFlowPass`2.VisitMethodBodies(BoundBlock blockBody, BoundBlock expressionBody)
      bei Microsoft.CodeAnalysis.CSharp.AbstractFlowPass`2.VisitNonConstructorMethodBody(BoundNonConstructorMethodBody node)
      bei Microsoft.CodeAnalysis.CSharp.AbstractFlowPass`2.VisitWithStackGuard(BoundNode node)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.Visit(BoundNode node)
      bei Microsoft.CodeAnalysis.CSharp.AbstractFlowPass`2.Scan(Boolean& badRegion)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.Scan(Boolean& badRegion)
      bei Microsoft.CodeAnalysis.CSharp.AbstractFlowPass`2.Analyze(Boolean& badRegion, Optional`1 initialState)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.Analyze(NullableWalker walker, Symbol symbol, DiagnosticBag diagnostics, Optional`1 initialState, Builder snapshotBuilderOpt, Boolean requiresAnalysis)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.Analyze(CSharpCompilation compilation, Symbol symbol, BoundNode node, Binder binder, Conversions conversions, DiagnosticBag diagnostics, Boolean useConstructorExitWarnings, Boolean useDelegateInvokeParameterTypes, Boolean useDelegateInvokeReturnType, MethodSymbol delegateInvokeMethodOpt, VariableState initialState, Builder analyzedNullabilityMapOpt, Builder snapshotBuilderOpt, ArrayBuilder`1 returnTypesOpt, Boolean getFinalNullableState, VariableState& finalNullableState, Boolean requiresAnalysis)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.AnalyzeWithSemanticInfo(CSharpCompilation compilation, Symbol symbol, BoundNode node, Binder binder, VariableState initialState, DiagnosticBag diagnostics, Boolean createSnapshots, Boolean requiresAnalysis)
      bei Microsoft.CodeAnalysis.CSharp.NullableWalker.AnalyzeAndRewrite(CSharpCompilation compilation, Symbol symbol, BoundNode node, Binder binder, VariableState initialState, DiagnosticBag diagnostics, Boolean createSnapshots, SnapshotManager& snapshotManager, ImmutableDictionary`2& remappedSymbols)
      bei Microsoft.CodeAnalysis.CSharp.MethodCompiler.BindMethodBody(MethodSymbol method, TypeCompilationState compilationState, BindingDiagnosticBag diagnostics, VariableState nullableInitialState, ImportChain& importChain, Boolean& originalBodyNested, InitialState& forSemanticModel)
      bei Microsoft.CodeAnalysis.CSharp.MethodCompiler.CompileMethod(MethodSymbol methodSymbol, Int32 methodOrdinal, ProcessedFieldInitializers& processedInitializers, SynthesizedSubmissionFields previousSubmissionFields, TypeCompilationState compilationState)
      bei Microsoft.CodeAnalysis.CSharp.MethodCompiler.CompileNamedType(NamedTypeSymbol containingType)
      bei Microsoft.CodeAnalysis.CSharp.MethodCompiler.<>c__DisplayClass23_0.<CompileNamedTypeAsync>b__0()
   --- Ende der Stapelüberwachung vom vorhergehenden Ort, an dem die Ausnahme ausgelöst wurde ---
      bei System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
      bei Microsoft.VisualStudio.Telemetry.WindowsErrorReporting.WatsonReport.GetClrWatsonExceptionInfo(Exception exceptionObject)
      bei Roslyn.Utilities.UICultureUtilities.<>c__DisplayClass5_0.<WithCurrentUICulture>b__0()
      bei System.Threading.Tasks.Task.Execute()
   --- Ende der Stapelüberwachung vom vorhergehenden Ort, an dem die Ausnahme ausgelöst wurde ---
      bei System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
      bei Microsoft.CodeAnalysis.CSharp.MethodCompiler.WaitForWorkers()
      bei Microsoft.CodeAnalysis.CSharp.MethodCompiler.CompileMethodBodies(CSharpCompilation compilation, PEModuleBuilder moduleBeingBuiltOpt, Boolean emittingPdb, Boolean emitTestCoverageData, Boolean hasDeclarationErrors, Boolean emitMethodBodies, BindingDiagnosticBag diagnostics, Predicate`1 filterOpt, CancellationToken cancellationToken)
      bei Microsoft.CodeAnalysis.CSharp.CSharpCompilation.<GetDiagnosticsForMethodBodiesInTree>g__compileMethodBodiesAndDocComments|217_0(SyntaxTree filterTree, Nullable`1 filterSpan, BindingDiagnosticBag bindingDiagnostics, CancellationToken cancellationToken)
      bei Microsoft.CodeAnalysis.CSharp.CSharpCompilation.GetDiagnosticsForMethodBodiesInTree(SyntaxTree tree, Nullable`1 span, CancellationToken cancellationToken)
      bei Microsoft.CodeAnalysis.CSharp.CSharpCompilation.GetDiagnosticsForSyntaxTree(CompilationStage stage, SyntaxTree syntaxTree, Nullable`1 filterSpanWithinTree, Boolean includeEarlierStages, CancellationToken cancellationToken)
      bei Microsoft.CodeAnalysis.CSharp.SyntaxTreeSemanticModel.GetDiagnostics(Nullable`1 span, CancellationToken cancellationToken)
      bei Microsoft.CodeAnalysis.Diagnostics.CompilationWithAnalyzers.GenerateCompilationEvents(AnalysisScope analysisScope, CancellationToken cancellationToken)
      bei Microsoft.CodeAnalysis.Diagnostics.CompilationWithAnalyzers.<ComputeAnalyzerDiagnosticsAsync>d__67.MoveNext()
   --- Ende der Stapelüberwachung vom vorhergehenden Ort, an dem die Ausnahme ausgelöst wurde ---
      bei System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
      bei System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
      bei Microsoft.CodeAnalysis.Diagnostics.CompilationWithAnalyzers.<ComputeAnalyzerSemanticDiagnosticsAsync>d__66.MoveNext()
   --- Ende der Stapelüberwachung vom vorhergehenden Ort, an dem die Ausnahme ausgelöst wurde ---
      bei System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
      bei System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
      bei Microsoft.CodeAnalysis.Diagnostics.CompilationWithAnalyzers.<GetAnalysisResultCoreAsync>d__64.MoveNext()
   --- Ende der Stapelüberwachung vom vorhergehenden Ort, an dem die Ausnahme ausgelöst wurde ---
      bei System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
      bei System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
      bei Microsoft.CodeAnalysis.Diagnostics.Extensions.<GetAnalysisResultAsync>d__12.MoveNext()
   --- Ende der Stapelüberwachung vom vorhergehenden Ort, an dem die Ausnahme ausgelöst wurde ---
      bei System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
      bei System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
      bei Microsoft.CodeAnalysis.Diagnostics.Extensions.<GetAnalysisResultAsync>d__11.MoveNext()
   --- Ende der Stapelüberwachung vom vorhergehenden Ort, an dem die Ausnahme ausgelöst wurde ---
      bei System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
      bei System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
      bei Microsoft.CodeAnalysis.Remote.Diagnostics.DiagnosticComputer.<AnalyzeAsync>d__9.MoveNext()
   --- Ende der Stapelüberwachung vom vorhergehenden Ort, an dem die Ausnahme ausgelöst wurde ---
      bei System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
      bei System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
      bei Microsoft.CodeAnalysis.Remote.Diagnostics.DiagnosticComputer.<GetDiagnosticsAsync>d__8.MoveNext()
   --- Ende der Stapelüberwachung vom vorhergehenden Ort, an dem die Ausnahme ausgelöst wurde ---
      bei System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
      bei System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
      bei Microsoft.CodeAnalysis.Remote.RemoteDiagnosticAnalyzerService.<>c__DisplayClass3_0.<<CalculateDiagnosticsAsync>b__0>d.MoveNext()
   --- Ende der Stapelüberwachung vom vorhergehenden Ort, an dem die Ausnahme ausgelöst wurde ---
      bei System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
      bei System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
      bei Microsoft.CodeAnalysis.Remote.BrokeredServiceBase.<RunServiceImplAsync>d__12`1.MoveNext()
   --- Ende der Stapelüberwachung vom vorhergehenden Ort, an dem die Ausnahme ausgelöst wurde ---
      bei System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
      bei Microsoft.VisualStudio.Telemetry.WindowsErrorReporting.WatsonReport.GetClrWatsonExceptionInfo(Exception exceptionObject)
@dotnet-issue-labeler dotnet-issue-labeler bot added Area-Compilers untriaged Issues and PRs which have not yet been triaged by a lead labels Jul 29, 2021
@bernd5 bernd5 changed the title NullReferenceException / NullableWalker.LocalState.SetValue for switch over bool in lambda Internal Compiler Error: NullReferenceException / NullableWalker.LocalState.SetValue for switch over bool in lambda Jul 30, 2021
@jaredpar jaredpar added Bug New Language Feature - Nullable Reference Types Nullable Reference Types and removed untriaged Issues and PRs which have not yet been triaged by a lead labels Aug 2, 2021
@jaredpar jaredpar added this to the 17.0 milestone Aug 2, 2021
@jaredpar
Copy link
Member

jaredpar commented Aug 2, 2021

@RikkiGibson, @333fred took a quick look and this doesn't presently repro in main

https://sharplab.io/#v2:EYLgtghglgdgNAFxFANnAJiA1AHwAIBMAjALABQ5eRAbAASH1EDs5A3ubZ/QQR1+2S60AvuT6c8AZkZ0A9sABWAUwDGCWgDFZsgBTzla2hACU42gKFCAbhABOtKAGcAcgFcUKAMIALVQGtaAF5aGCUAd1oAcxR5CBQQECoAOjwAVgAefVUEOFostQA+HR0AB2MggrMhC0taxzCoBBVvWlKg4Jh3FFNBWssavr6VCEclWht7J06PECrBvrwmB0dplABuOdrRXq3jDZ3LReW3Dx9/HRN9oW3hIA===

At least attempting to compile the sample directly doesn't produce any crashes. Did we fix something here recently or is the semantic model doing the walk in a diff way that causes the crash here?

@bernd5
Copy link
Contributor Author

bernd5 commented Aug 2, 2021

Good point.
It still crashes - but only with #nullable enable.

See: here
_container is null

@jaredpar
Copy link
Member

jaredpar commented Aug 2, 2021

Ah yes that is the trick. I really should've thought of that when I was working on the sharplab repro.

@RikkiGibson
Copy link
Contributor

It seems like a bitmap containing flow state wasn't initialized in whatever code path this took. I'm optimistic that if we run this in a test in debug configuration that we'll hit some assert which clues us in to the underlying problem.

@bernd5
Copy link
Contributor Author

bernd5 commented Aug 2, 2021

@RikkiGibson I think you are right. For me it looks like that the constructor is not called for the LocalState. Right before the error is an assert which checks for Id > 0 - which is not true (the struct is just filled with zeros).

See: here

@jaredpar jaredpar modified the milestones: 17.0, 17.1 Aug 3, 2021
@jaredpar jaredpar assigned AlekseyTs and unassigned RikkiGibson Aug 26, 2021
AlekseyTs added a commit to AlekseyTs/roslyn that referenced this issue Aug 31, 2021
…ns before the switch expression, which can cause us to "split" the state.

Fixes dotnet#55227.
AlekseyTs added a commit that referenced this issue Aug 31, 2021
…s before the switch expression, which can cause us to "split" the state. (#56031)

Fixes #55227.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment