runtime: Quic exception in the guts of making an http request
Description
I have a game server that is using dotnet core 3.1, and I have recently begun building it for .net 7 to get away on a newer supported .net version. We are building this game server in self contained mode with a targeted runtime to make it completely self sufficient.
This server application is a console app, and one of the first things it does as part of starting up the server into the configured map is query mod.io for a template file to see if it needs to download the template file or whether the file hash matches the local file.
This fairly basic http query is failing seemingly within the code that is supposed to be checking whether QuicConnection IsSupported. Here is a callstack
BuildVerseServer.Server - DownloadTemplateFromModIO Exception
System.AggregateException: One or more errors occurred. (The type initializer for 'System.Net.Quic.MsQuicApi' threw an exception.)
---> System.TypeInitializationException: The type initializer for 'System.Net.Quic.MsQuicApi' threw an exception.
---> System.Runtime.InteropServices.SEHException (0x80004005): External component has thrown an exception.
at System.Net.Quic.MsQuicApi.TryOpenMsQuic(QUIC_API_TABLE*& apiTable, Int32& openStatus)
at System.Net.Quic.MsQuicApi..cctor()
--- End of inner exception stack trace ---
at System.Net.Quic.QuicConnection.get_IsSupported()
at System.Net.Http.HttpConnectionPool..ctor(HttpConnectionPoolManager poolManager, HttpConnectionKind kind, String host, Int32 port, String sslHostName, Uri proxyUri)
at System.Net.Http.HttpConnectionPoolManager.SendAsyncCore(HttpRequestMessage request, Uri proxyUri, Boolean async, Boolean doRequestAuth, Boolean isProxyConnect, CancellationToken cancellationToken)
at System.Net.Http.HttpConnectionPoolManager.SendAsync(HttpRequestMessage request, Boolean async, Boolean doRequestAuth, CancellationToken cancellationToken)
at System.Net.Http.HttpConnectionHandler.SendAsync(HttpRequestMessage request, Boolean async, CancellationToken cancellationToken)
at System.Net.Http.HttpMessageHandlerStage.SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
at System.Net.Http.DiagnosticsHandler.SendAsync(HttpRequestMessage request, Boolean async, CancellationToken cancellationToken)
at System.Net.Http.RedirectHandler.SendAsync(HttpRequestMessage request, Boolean async, CancellationToken cancellationToken)
at System.Net.Http.HttpClient.<SendAsync>g__Core|83_0(HttpRequestMessage request, HttpCompletionOption completionOption, CancellationTokenSource cts, Boolean disposeCts, CancellationTokenSource pendingRequestsCts, CancellationToken originalCancellationToken)
at Modio.Connection.Send[T](Request request) in C:\JenkinsHome\workspace\CreativerseStandalone\Server\Modio\Http\Connection.cs:line 41
at Modio.SearchClient`1.ToPagedEnumerable()+MoveNext() in C:\JenkinsHome\workspace\CreativerseStandalone\Server\Modio\Clients\SearchClient.cs:line 90
at Modio.SearchClient`1.ToPagedEnumerable()+System.Threading.Tasks.Sources.IValueTaskSource<System.Boolean>.GetResult()
at Modio.SearchClient`1.ToList() in C:\JenkinsHome\workspace\CreativerseStandalone\Server\Modio\Clients\SearchClient.cs:line 54
at Modio.SearchClient`1.ToList() in C:\JenkinsHome\workspace\CreativerseStandalone\Server\Modio\Clients\SearchClient.cs:line 54
After some reading in several issues here on github. It seems that some of this Quic stuff or higher http versions that utilize it should be opt-in, and we aren’t opting in, so I’m not sure why it is attempting to use/initialize Quic. In any case I thought it seemed suspect that the bowels of a completely optional component Quic could fail out of the entire attempt, rather than be caught and treated as non supported.
Reproduction Steps
Reproduction is impractical to communicate, because this occurs in a highly specific circumstance of running the dedicated server app via steam on the steam deck handheld gaming device. What’s more, is that this only occurs when running the server in this way. If we run the native linux version of the server via terminal on the steam deck, this issue does not occur. My guess is the presence of Quic support is being effected by the emulation layer that apps run on when launched via steam on the steam deck device.
Expected behavior
I guess I would expect Quic support to report false and the app to continue without it, not fail with an exception all the way back up to user code.
Actual behavior
Within the call context of System.Net.Quic.QuicConnection.get_IsSupported(), an uncaught exception causes the entire callstack to unwind back to user code and the http request to fail completely.
Regression?
We are brand new at experimenting with running our game/server on the steam deck device. These issues are unique to running the application on top of the proton emulation layer, so while one may point to that as being the emulation layers problem, the nature of the failure to me suggests there is the possibility of a supposedly optional component(Quic) IsSupported function failing spectacularly and breaking the whole attempt.
Known Workarounds
None
Configuration
.net 7 steam OS
Other information
No response
About this issue
- Original URL
- State: closed
- Created a year ago
- Comments: 17 (13 by maintainers)
You can do
LD_DEBUG=libs ./myApp
That would show library loading and any bits not visible by the package manager.