[browser][coreclr] Flow property values from runtime build to relink - #132715
Conversation
The Mono wasm-tools workload decides whether a per-app native relink is needed by comparing the app's MSBuild properties against the values baked into the runtime pack, transporting those baked values in wasm-props.json. The CoreCLR browser-wasm path had no equivalent, so an app that changed InvariantGlobalization, the heap sizes, or diagnostics silently got a prebuilt dotnet.native.wasm that did not match its configuration. Recreate the mechanism for CoreCLR using plain MSBuild instead of JSON: the runtime build emits BrowserWasmApp.CoreCLR.Generated.props declaring a _RuntimeFoo property for each tracked property Foo plus a registry item, and _CoreCLRSetWasmBuildNativeDefaults compares each app value against the baked one. Values are available at evaluation time and no custom task factory is involved, and the file is a normal .props so items can be added later without changing the transport. Semantics mirror Mono's _SetWasmBuildNativeDefaults: a mismatch sets WasmBuildNative, and an explicit WasmBuildNative=false alongside a mismatch is an error. When the generated file is absent the target degrades to the pre-existing heuristics. The browserhost memory settings are lifted into eng/native.wasm.targets so the CMake link flags and the emitted runtime-pack defaults cannot drift. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: b79bc26a-0d03-4fa7-b8a8-a52b83e17a16
Replace JSON-style runtime setting transport with MSBuild metadata consumed by the CoreCLR browser-wasm SDK. Package the relink registry and validate mismatches during app builds. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: b79bc26a-0d03-4fa7-b8a8-a52b83e17a16
|
Azure Pipelines: Successfully started running 4 pipeline(s). 12 pipeline(s) were filtered out due to trigger conditions. There may be pipelines that require an authorized user to comment /azp run to run. |
|
Tagging subscribers to 'arch-wasm': @lewing, @pavelsavara |
native.wasm.targets is now imported by app-level relink builds (via BrowserWasmApp.CoreCLR.targets), not just the in-tree runtime build, but two issues prevented it from working correctly outside the runtime repo: - The unconditional Import of AcquireEmscriptenSdk.targets/AcquireWasiSdk.targets only exists in-tree; packaged app builds have RepositoryEngineeringDir unset, so the import failed the build. Guard both imports with existence/emptiness checks. - The relink registry (_CoreCLRPropertyThatTriggersRelinking) is gated on RuntimeFlavor == 'CoreCLR', but that property is only set during the runtime repo's own build; app builds only set UseMonoRuntime=false. Default RuntimeFlavor to CoreCLR in BrowserWasmApp.CoreCLR.targets (which is only imported when UseMonoRuntime=='false') so the registry populates for consuming apps too. Also extends CoreCLRWasmNativeDefaultsTests with two previously-untested relink triggers mirroring Mono's WasmNativeDefaultsTests: a NativeFileReference item and WasmPerformanceInstrumentation. All 18 tests in the class pass against a freshly rebuilt workload SDK pack. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: b79bc26a-0d03-4fa7-b8a8-a52b83e17a16
Run the CoreCLR native defaults test class from the CoreCLR Wasm CI job list and remove redundant runtime flavor conditions from the class. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: b79bc26a-0d03-4fa7-b8a8-a52b83e17a16
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>\nCopilot-Session: b79bc26a-0d03-4fa7-b8a-a52b83e17a16
|
Azure Pipelines: Successfully started running 4 pipeline(s). 12 pipeline(s) were filtered out due to trigger conditions. There may be pipelines that require an authorized user to comment /azp run to run. |
There was a problem hiding this comment.
Pull request overview
This PR propagates CoreCLR browser-Wasm runtime-pack settings through MSBuild/CMake targets to detect app-level relink mismatches.
Changes:
- Adds packaged browser-host defaults, relink metadata, and CMake arguments.
- Implements CoreCLR relink detection and memory-setting propagation.
- Adds CoreCLR tests, scenario registration, and invariant test configuration.
Blocking findings:
- Critical (1 vote):
eng/native.wasm.targetsomits required defaults for Mono browser-host builds. - Critical (1 vote):
BrowserWasmApp.CoreCLR.targetsdoes not normalizeEmccInitialHeapSize.
Reviewed changes
Copilot reviewed 8 out of 8 changed files in this pull request and generated 2 comments.
Show a summary per file
| File | Summary |
|---|---|
src/native/corehost/browserhost/CMakeLists.txt |
Uses configurable browser-host memory settings. |
src/mono/wasm/Wasm.Build.Tests/CoreCLRWasmNativeDefaultsTests.cs |
Tests CoreCLR relink decisions. |
src/mono/nuget/Microsoft.NET.Runtime.WebAssembly.Sdk/Microsoft.NET.Runtime.WebAssembly.Sdk.pkgproj |
Packages shared native target metadata. |
src/mono/browser/build/BrowserWasmApp.CoreCLR.targets |
Implements CoreCLR relink behavior and native settings. |
src/libraries/System.Runtime/tests/System.Globalization.Tests/Invariant/Invariant.Tests.csproj |
Adjusts unresolved P/Invoke warning handling. |
eng/testing/scenarios/BuildWasmAppsJobsListCoreCLR.txt |
Registers the CoreCLR test suite. |
eng/native.wasm.targets |
Defines runtime defaults, relink metadata, and CMake arguments. |
Directory.Build.props |
Formatting-only change. |
Suppressed comments (3)
eng/native.wasm.targets:50
- These are still source-file literals, so they do not actually carry the values from the runtime-pack build into the SDK. For example, a runtime build invoked with
/p:BrowserHostStackSize=4MBpasses 4MB to CMake and produces a pack with a 4MB stack, but the packagednative.wasm.targetscontinues to advertise2MB; an app that relinks for a native reference will then use 2MB and no mismatch is detected because the registry compares against the stale packaged value. Generate the registry/default props from the evaluated runtime build (or otherwise make the runtime pack and SDK consume the same packaged values) rather than duplicating fallbacks.
[!NOTE] This review comment was created by GitHub Copilot.
<BrowserHostInitialHeapSize Condition="'$(BrowserHostInitialHeapSize)' == ''">33554432</BrowserHostInitialHeapSize>
<BrowserHostMaximumHeapSize Condition="'$(BrowserHostMaximumHeapSize)' == ''">2147483648</BrowserHostMaximumHeapSize>
<BrowserHostStackSize Condition="'$(BrowserHostStackSize)' == ''">2MB</BrowserHostStackSize>
eng/native.wasm.targets:56
EnableDiagnosticsdoes not affect any native link input here: the CoreCLR path emits the diagnostics JS/assets andDOTNET_*environment variables, while the native diagnostics/perf-tracing code is selected by the CMake feature flags. Adding it to this registry therefore makes every CoreCLR app withEnableDiagnostics=truepay for a full emcc relink even though the native link is unchanged;BrowserHostEnableDiagnosticsis not passed to CMake either. Please remove this entry from the runtime-pack mismatch registry unless a corresponding native link option is added.
<_CoreCLRPropertyThatTriggersRelinking Include="EnableDiagnostics" RuntimePackValue="$(BrowserHostEnableDiagnostics)" />
src/mono/browser/build/BrowserWasmApp.CoreCLR.targets:198
WasmPerformanceInstrumentationis consumed as a boot-timeDOTNET_WasmPerformanceInstrumentationsetting; it does not change_CoreCLRWriteLinkRsp's native libraries or link flags, and the browser profiler code is compiled into the runtime wheneverPERFTRACING_DISABLE_THREADSis enabled. This condition therefore adds an expensive native relink for instrumentation-only apps without changing the native result. Please leave this out of the relink-default logic and let the boot configuration enable instrumentation.
[!NOTE]
This review comment was generated by GitHub Copilot.
<WasmBuildNative Condition="'$(WasmBuildNative)' == '' and '$(WasmPerformanceInstrumentation)' != ''">true</WasmBuildNative>
browserhost is built for every browser host flavor, so gating the CMAKE_BROWSERHOST_* arguments on RuntimeFlavor=CoreCLR left a Mono browser host configure without them and tripped the new fatal check. Move the memory defaults and those arguments to all browser builds and keep only the CoreCLR relink registry flavor-gated. Also collapse EmccInitialHeapSize and its legacy EmccTotalMemory alias into WasmInitialHeapSize, matching the Mono path, so the documented property is seen by the relink registry and used by the emcc link. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: b79bc26a-0d03-4fa7-b8a8-a52b83e17a16
Conflict in src/mono/browser/build/BrowserWasmApp.CoreCLR.targets: main (dotnet#132339) relocated the EmSdkRepo.Defaults.props import to just after the native.wasm.targets import, which is where this branch added the packaged native.wasm.targets import. Kept both and ordered EmSdkRepo.Defaults.props after both native.wasm.targets imports, preserving the requirement that it follow AcquireEmscriptenSdk.targets setting EMSDK_PATH in-tree. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: b79bc26a-0d03-4fa7-b8a8-a52b83e17a16
Adding InvariantTimezone to the CoreCLR browser relink registry makes this project auto-relink, so it now reaches ManagedToNativeGenerator. Its untrimmed library-test closure pulls in Azure.Identity, whose foreign-platform P/Invokes (libsecret, Security.framework, CoreFoundation, kernel32, ntdll, advapi32) are unresolvable on wasm and fail the build with WASM0066 under warn-as-error. Same fix already applied to Invariant.Tests; these are the only two library test projects that set a relink-registry property. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: b79bc26a-0d03-4fa7-b8a8-a52b83e17a16
|
Compared the
So this PR has +2 test projects with Projects on PR:
Project on main:
Note AI-generated content (via GitHub Copilot CLI). |
|
/ba-g The macos failure is unrelated |
One textual conflict, in BrowserWasmApp.CoreCLR.targets: dotnet#132715 added WarnOnUnresolvedPInvokeModules to the ManagedToNativeGenerator call that this branch replaces with crossgen2. Kept the crossgen2 invocation; everything else that PR added to the file - the RuntimeFlavor default, the native.wasm.targets import, the relink property registry and the runtime-pack heap-size defaults - merged cleanly and is preserved. The same PR also introduced WasmWarnOnUnresolvedPInvokeModules: a default here and a suppression in two test projects. This branch deletes the WASM0066 warning they exist for, so all three were dead on arrival - a semantic conflict git had nothing to flag, since the files did not overlap textually. Removed them, the way this branch already removed the suppressions that predated it. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: f6d6e5a4-5b25-4198-b42d-d5b2dc781f47
Contributes to #126100
Summary
CoreCLR browser-Wasm applications need a native relink when their settings differ from the values used to build the runtime-pack browser host. This change carries those runtime-pack values through the WebAssembly SDK's MSBuild targets and compares them during app builds, replacing the JSON transport mechanism with packaged
.props/.targetslogic.The implementation:
RuntimePackValuemetadata to detect mismatches and set or validateWasmBuildNative.RuntimeFlavortoCoreCLRfor app-level CoreCLR builds so the packaged registry is active.WasmBuildNative=false,NativeFileReference, andWasmPerformanceInstrumentation.Validation: all 18
CoreCLRWasmNativeDefaultsTestspassed against a freshly rebuilt workload SDK pack.Note
This pull request description was generated with GitHub Copilot.