You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Make native interop cancellation stress gate independent of runner timing #78
The native runtime package gate runs native-interop-race --batches 100 --width 32 to verify cancellation, result-pool cleanup, and generated interop accounting across four V8 contexts. On a contended macOS hosted runner, the probe rejected otherwise valid calls with:
Generated native interop invocation was rejected: Native interop invocation queue is full
Observed failure on run 34961173025:
12,800 intended operations
12,672 generated calls
12,672 cancellations
128 queue-full faults
all four result/operation pools drained to zero afterward
The native engine, 21 CTests, 150-document/514-subtest required web-platform subset, media profiles, and 55 Avalonia tests had already passed. The failure was in the stress harness pacing.
Root cause
After disposing each batch's managed invokers, the probe slept for a fixed 20 ms and enqueued native-interop-race-barrier.js. TryExecuteScript only accepts that script asynchronously; it does not wait for execution. On a slower runner, cancelled promise work could remain ahead of the barrier, so multiple batches accumulated in the bounded 64-entry native interop queue.
The initial fixture installation had the same asynchronous assumption.
Fix
Draft PR #76 at consolidated commit 41cf43cc34355f9511df94631f49baa87ff8818f uses EngineMetrics.ExecutedScripts as a completion fence:
Read the current counter.
Enqueue the fixture or barrier script.
Poll until ExecutedScripts advances, with a five-second deadline.
Start the next batch only after the barrier queued behind the prior interop work has executed.
This preserves the full 100 x 32 x 4 stress workload and the queue bound. It removes wall-clock timing as a correctness condition and still fails on a real worker stall, lost script, interop fault, accounting mismatch, or leaked result/operation slot.
Validation
The benchmark project builds with zero warnings and errors. The complete PR #76 matrix passed:
hosted macOS, Ubuntu, and Windows builds
NativeAOT contracts and Linux native contracts
packaged Linux x64, macOS arm64, and Windows x64 runtimes
cross-RID candidate and required evidence
release-package verification
installed-package consumers on all three RIDs
The NuGet publish and release-commit guard were skipped by design because this is a draft, non-release revision.
Implemented in draft PR #76 at 41cf43cc34355f9511df94631f49baa87ff8818f.
The probe now waits for the initial fixture and every per-batch barrier by polling EngineMetrics.ExecutedScripts with a five-second deadline. This proves that the script queued behind the prior cancelled promise work actually executed before the next batch starts; TryExecuteScript acceptance alone is no longer treated as completion.
Final package run 34962268212 passed:
Linux x64: 6m49s
macOS arm64: 7m32s
Windows x64: 11m41s
all 12,800 generated calls completed through success/cancellation with no queue-full faults
all result and operation pools drained
cross-RID required/candidate evidence, release package verification, and all three consumer installs passed
The benchmark project also builds locally with zero warnings/errors. Generated bin/obj outputs were removed after validation.
Activity
wieslawsoltes commentedon Sep 15, 2026
Implemented in draft PR #76 at
41cf43cc34355f9511df94631f49baa87ff8818f.The probe now waits for the initial fixture and every per-batch barrier by polling
EngineMetrics.ExecutedScriptswith a five-second deadline. This proves that the script queued behind the prior cancelled promise work actually executed before the next batch starts;TryExecuteScriptacceptance alone is no longer treated as completion.Final package run 34962268212 passed:
The benchmark project also builds locally with zero warnings/errors. Generated
bin/objoutputs were removed after validation.