fix(track-memory-allocations): reserve transform scoping capacity#22621
Merged
Conversation
camc314
approved these changes
May 20, 2026
Member
Author
Merge activity
|
…2621) ## Issue The `Allocations` CI job can fail on PRs that do not touch the transformer because `cargo allocs` can rewrite `allocs_transformer.snap` differently across platforms. In the observed failure, Linux x64 reported one extra transformer system allocation for `App.tsx`, while macOS/arm64 still reported the old count. ## Why The allocation tracker was passing transformer a `Scoping` built differently from the production compiler path. Production builds semantic data with `SemanticBuilder::with_excess_capacity(2.0)` before running transforms, because transforms may add scopes, symbols, and references. The allocation tracker did not reserve that extra semantic capacity. That made the transformer snapshot accidentally include growth of semantic scoping storage. In this case, JSX automatic runtime import generation creates a new root-scope binding. The traced Linux-only allocation happened under `JsxImpl::get_create_element -> AutomaticModuleBindings::import_jsx -> TraverseScoping::add_binding -> Scoping::create_symbol`, when pushing the generated symbol forced the semantic `Scoping` arena to allocate another chunk. Linux got a different allocation count because this is a capacity-boundary effect, not different transformer behavior. The `Scoping` arena layout depends on target layout and alignment. On Linux x64, the generated binding crossed the arena chunk boundary and allocated a new 16-byte-aligned chunk, so the measured transformer count became 27. On macOS/arm64, the same push still fit in the existing semantic arena capacity, so the measured count stayed 26. So the root cause is that transformer allocation tracking was measuring platform-sensitive semantic storage growth. Any unrelated PR could expose the same stale snapshot whenever CI regenerated allocations on a platform that lands on the other side of that capacity boundary. ## Fix Keep `allocs_semantic.snap` measuring regular semantic analysis, but build a separate production-like semantic `Scoping` for transformer measurement using `with_excess_capacity(2.0)`. This matches the compiler and transformer benchmarks, and removes the semantic arena capacity cliff from the transformer allocation snapshot. The transformer allocation snapshot is regenerated after the measurement fix. ## Validation Verified `cargo allocs` leaves the branch clean on macOS/arm64 and in Linux amd64 Docker. AI usage: I used AI assistance to investigate, implement, and validate this change.
59df140 to
b9171ea
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Issue
The
AllocationsCI job can fail on PRs that do not touch the transformer becausecargo allocscan rewriteallocs_transformer.snapdifferently across platforms. In the observed failure, Linux x64 reported one extra transformer system allocation forApp.tsx, while macOS/arm64 still reported the old count.Why
The allocation tracker was passing transformer a
Scopingbuilt differently from the production compiler path. Production builds semantic data withSemanticBuilder::with_excess_capacity(2.0)before running transforms, because transforms may add scopes, symbols, and references. The allocation tracker did not reserve that extra semantic capacity.That made the transformer snapshot accidentally include growth of semantic scoping storage. In this case, JSX automatic runtime import generation creates a new root-scope binding. The traced Linux-only allocation happened under
JsxImpl::get_create_element -> AutomaticModuleBindings::import_jsx -> TraverseScoping::add_binding -> Scoping::create_symbol, when pushing the generated symbol forced the semanticScopingarena to allocate another chunk.Linux got a different allocation count because this is a capacity-boundary effect, not different transformer behavior. The
Scopingarena layout depends on target layout and alignment. On Linux x64, the generated binding crossed the arena chunk boundary and allocated a new 16-byte-aligned chunk, so the measured transformer count became 27. On macOS/arm64, the same push still fit in the existing semantic arena capacity, so the measured count stayed 26.So the root cause is that transformer allocation tracking was measuring platform-sensitive semantic storage growth. Any unrelated PR could expose the same stale snapshot whenever CI regenerated allocations on a platform that lands on the other side of that capacity boundary.
Fix
Keep
allocs_semantic.snapmeasuring regular semantic analysis, but build a separate production-like semanticScopingfor transformer measurement usingwith_excess_capacity(2.0). This matches the compiler and transformer benchmarks, and removes the semantic arena capacity cliff from the transformer allocation snapshot.The transformer allocation snapshot is regenerated after the measurement fix.
Validation
Verified
cargo allocsleaves the branch clean on macOS/arm64 and in Linux amd64 Docker.AI usage: I used AI assistance to investigate, implement, and validate this change.