-
Notifications
You must be signed in to change notification settings - Fork 5.3k
Description
Our HTTP3 support depends on having an msquic assembly around to load. In many cases, this assembly isn't available (for example in a Docker container where the developer didn't explicitly add the msquic package). When this happens, all the code in System.Net.Quic.dll is basically dead code that will never execute. However, the code can't be trimmed because we take a hard-dependency on it from System.Net.Http.dll.
We already have a couple of places that allow this feature to be shut off or trimmed away on platforms that don't support msquic:
runtime/src/libraries/System.Net.Http/src/System/Net/Http/GlobalHttpSettings.cs
Lines 29 to 34 in e232f79
| // Default to allowing HTTP/3, but enable that to be overridden by an | |
| // AppContext switch, or by an environment variable being set to false/0. | |
| public static bool AllowHttp3 { get; } = RuntimeSettingParser.QueryRuntimeSettingSwitch( | |
| "System.Net.SocketsHttpHandler.Http3Support", | |
| "DOTNET_SYSTEM_NET_HTTP_SOCKETSHTTPHANDLER_HTTP3SUPPORT", | |
| true); |
runtime/src/libraries/System.Net.Http/src/System/Net/Http/SocketsHttpHandler/HttpConnectionPool.cs
Line 304 in e232f79
| internal static bool IsHttp3Supported() => (OperatingSystem.IsLinux() && !OperatingSystem.IsAndroid()) || OperatingSystem.IsWindows() || OperatingSystem.IsMacOS(); |
We should consider making these switches a full-blown feature switch. Basically we should:
- Add an entry to System.Net.Http's
ILLink.Substitutions.xmlfile which would changeIsHttp3Supported()to always returnfalsewhen theSystem.Net.SocketsHttpHandler.Http3Supportruntime switch is set tofalse. - Add an MSBuild property and RuntimeHostConfigurationOption entry to https://github.com/dotnet/sdk/blob/main/src/Tasks/Microsoft.NET.Build.Tasks/targets/Microsoft.NET.Sdk.targets#L386-L399 that allows a developer to trim away HTTP3 support.
Note that Kestrel also has a hard-dependency on System.Net.Quic in UseKestrel(). So Kestrel would need to be updated as well to respect this feature switch, if we wanted to trim this code away in a web app.
Doing some quick prototyping on my machine, this can save about 250KB of IL from a trimmed ASP.NET Linux server app. When publishing with -p:PublishAot=true, the savings drops to about 43KB in the native executable.