I have been working on an application for about two and a half years now and last month we went live and published our .NET application. The application is a WPF application that uses .NET version 5.0.17 and its main purpose is to do calculations for separation vessels. It consists mostly of UserControls, connected to ViewModels that use “calculation runners” to asynchronously do long calculations for these vessels.
Since the release we have been getting TypeInitializationException almost daily. I spent these two and half years working on the application almost daily, but never encountered the issue once, while working on four different devices. It also happens inconsistently and across multiple classes. We make backup’s of the project right before the crash to replicate the issue, but the exception doesn’t happen again when replicating the steps.
Below are the specifics for the exception. The exception happens inside a Task.Run block and throws a TypeInitializationException with a NullPointerException as inner exception, but it never contains any information about what class actually contains a null value. I also tried wrapping the code in Task.Run() within a try-catch block, but that also results in the exact same exception, which leads me to think the exception is inside the Task.Run.
I have been breaking my head over this issue the past month but I can’t figure out what’s wrong for the life of me.
System.TypeInitializationException
The type initializer for '<Module>' threw an exception.
at MySep.Studio.DesignCalculationRunner.Run(Int32 vesselIndex, Boolean openProjectFile)
at System.Runtime.CompilerServices.AsyncMethodBuilderCore.Start[TStateMachine](TStateMachine& stateMachine)
at MySep.Studio.DesignCalculationRunner.Run(Int32 vesselIndex, Boolean openProjectFile)
at MySep.Studio.DesignCalculationRunner.<>c__DisplayClass0_0.<<RunAsync>b__1>d.MoveNext()
--- End of stack trace from previous location ---
at MySep.Studio.DesignCalculationRunner.RunAsync(Int32 vesselIndex, Action chainMethod, Boolean openProjectFile)
at System.Threading.Tasks.Task.<>c.<ThrowAsync>b__140_0(Object state)
at System.Windows.Threading.ExceptionWrapper.InternalRealCall(Delegate callback, Object args, Int32 numArgs)
at System.Windows.Threading.ExceptionWrapper.TryCatchWhen(Object source, Delegate callback, Object args, Int32 numArgs, Delegate catchHandler)
MySep.Studio
the inner exception:
System.NullReferenceException: Object reference not set to an instance of an object.
(without any further information on where the exception happens)
the code:
internal static async void RunAsync(int vesselIndex, Action chainMethod = null, bool openProjectFile=false)
{
//ParamName is undefined now, should be vessel tag or so, "Vessel" is fine for now
DockHelper.ToggleSpinner(true, "Running design calculations...");
//Await project
Project proj = await Task.Run(async () =>
{
return await Run(vesselIndex, openProjectFile);
});
//Refresh application
DockHelper.RefreshAllControls(vesselIndex);
//After calc method
if (chainMethod != null) chainMethod();
//Event bus after calc
EventBus.Publish(Events.PerformanceCalculation);
//Wait for spinner
await Task.Run(async () =>
{
await Task.Delay(400);
});
//Toggle spinner
DockHelper.ToggleSpinner(false);
}
internal static async Task<Project> Run(int vesselIndex, bool openProjectFile=false)
{
//Create param
MySepParam mySepParam = new MySepParam();
mySepParam.LiquidLevelSetIndex = 0;
mySepParam.SectionName = "Vessel";
mySepParam.VesselIndex = vesselIndex;
mySepParam.BEAccessCode = Global.BEAccessCode;
mySepParam.OpenProjectFile = openProjectFile;
//Set globals
Global.ProjectName = Global.Project.Name;
Global.VesselIndex = vesselIndex;
//Write sentry breadcrumb
SentryHelper.AddBreadcrumb($"Calculation - Design");
//Run
var allResults = Global.Project.VesselsResults;
var vesselResult = DesignCalculationHelper.DesignCalculation(Global.Project.Vessels[vesselIndex], mySepParam).VesselResults;
if (allResults.Count <= vesselIndex)
allResults.Add(vesselResult);
else
allResults[vesselIndex] = vesselResult;
await Task.Delay(1);
return Global.Project;
}
I tried:
Wrapping everything in try-catch blocks.
throwing the InnerException instead of the exception in Jira.
Searching for classes that could possibly contain null values.
But all to no avail
Edit
Someone in the comments suggested it might be a duplicate of this issue. This is not the case as this user can’t run his application because of a generic TypeInitializationException with an InnerException explaining what static variable is missing. In my case the message is “The type initializer for '' threw an exception” and does not further explain what part of the application causes the exception. It looks more like this issue, but that one is from 12 years ago and uses .NET 2.0. The InnerException is also different and says “The C++ module failed to load during appdomain initialization.”
The suggested solution here was “Your customer needs to get their machine stable again, then reinstall .NET”, however I have a hard time believing it’s an unstable .NET version that is causing this, since we have a lot of users that have encountered this issue once or twice.
Update: I solved it by upgrading to NET 8, I don’t know what caused the issue.