Skip to content

Revert Phase 2 load/call propagation skip in SpillPointers for JWST compiler compatibility#8

Draft
Copilot wants to merge 9 commits intorelease/16.xfrom
copilot/fix-webassembly-fail-tests
Draft

Revert Phase 2 load/call propagation skip in SpillPointers for JWST compiler compatibility#8
Copilot wants to merge 9 commits intorelease/16.xfrom
copilot/fix-webassembly-fail-tests

Conversation

Copy link
Copy Markdown

Copilot AI commented Mar 2, 2026

The previous fix added MI.mayLoad() and MI.isCall() skips in Phase 2 dataflow propagation to prevent pointer-ness from propagating through loads/calls. While this passed reg-stackify.ll, it caused widespread issues in the JWST compiler where pointer values stored as i32 were no longer being spilled.

SpillPointers pass

  • Remove the Phase 2 skips for mayLoad() and isCall(), restoring conservative propagation. Any instruction with a pointer input (including loads whose address is a pointer) will propagate pointer-ness to its result unless blocklisted.
  • Phase 1 seed classification via isLoadOfPotentialPointer() and callee return type checking remain unchanged.

reg-stackify.ll

  • Update store_past_invar_load expectations: the invariant load can no longer sink past the call because its result is now conservatively marked as a potential pointer and spilled.
; Before: store → call → load (sunk) → return $pop
; After:  store → load → call → return

userstack.ll

No changes in this PR (was modified in the initial commit to use unified CHECK patterns with [[PTR]] instead of separate CHECK-32/CHECK-64 auto-generated patterns, to tolerate SpillPointers-inserted spill instructions).


🔒 GitHub Advanced Security automatically protects Copilot coding agent pull requests. You can protect all pull requests by enabling Advanced Security for your repositories. Learn more about Advanced Security.

… flag

The pass was running unconditionally at O1+ optimization levels, inserting
extra store instructions before calls that broke 4 existing CodeGen tests.
By gating behind a CLI flag (defaulting to off), the pass only activates
when explicitly requested for conservative GC support.

Co-authored-by: PLUTOFX <110596339+PLUTOFX@users.noreply.github.com>
Copilot AI changed the title [WIP] Investigate test failures after adding WebAssemblySpillPointers pass Gate WebAssemblySpillPointers pass behind -wasm-enable-spill-pointers flag Mar 2, 2026
Document how to use the flag from both clang (-mllvm -wasm-enable-spill-pointers)
and llc (-wasm-enable-spill-pointers) in the pass file header and README.txt.

Co-authored-by: PLUTOFX <110596339+PLUTOFX@users.noreply.github.com>
Copilot AI and others added 2 commits March 2, 2026 13:58
Co-authored-by: PLUTOFX <110596339+PLUTOFX@users.noreply.github.com>
The 4 test failures were NOT caused by pass logic bugs - the pass correctly
spills pointers that are live across calls to the shadow stack for
conservative GC support. The failures were because the test CHECK patterns
were written before this pass existed and didn't account for the spill stores.

Changes:
- Remove WasmEnableSpillPointers flag gating - pass now always runs at O1+
- Update global.ll: relax call_memcpy checks for spill stores
- Update mem-intrinsics.ll: relax memcpy/memmove/memset result checks
- Update reg-stackify.ll: adjust for changed register numbering and
  invariant load ordering due to spill stores
- Update userstack.ll: adjust stack frame size (48->64) and offsets
  due to spill slot allocation
- Remove flag documentation from SpillPointers.cpp and README.txt

Co-authored-by: PLUTOFX <110596339+PLUTOFX@users.noreply.github.com>
Copilot AI changed the title Gate WebAssemblySpillPointers pass behind -wasm-enable-spill-pointers flag Enable WebAssemblySpillPointers pass unconditionally; update affected tests Mar 2, 2026
Copilot AI and others added 2 commits March 17, 2026 06:06
Co-authored-by: PLUTOFX <110596339+PLUTOFX@users.noreply.github.com>
…ropagation through loads/calls

Three key fixes to WebAssemblySpillPointers:
1. Skip calls that cannot trigger GC (readnone+nounwind, memcpy/memmove/memset)
2. Use MachineMemOperand LLT type to distinguish pointer loads from non-pointer loads
3. Prevent Phase 2 dataflow from propagating pointer-ness through loads and calls
   (their results are already properly classified in Phase 1)

This fixes global.ll, mem-intrinsics.ll, reg-stackify.ll. For userstack.ll,
the spill of ptr %addr is correct (it IS a live pointer across calls), so
test expectations are updated to reflect the new frame layout.

Co-authored-by: PLUTOFX <110596339+PLUTOFX@users.noreply.github.com>
Copilot AI changed the title Enable WebAssemblySpillPointers pass unconditionally; update affected tests Fix SpillPointers pass: reduce false positives in pointer identification Mar 17, 2026
Copilot AI requested a review from PLUTOFX March 17, 2026 06:18
… attributes in SpillPointers pass

Add detailed comments explaining:
- What LLT (Low Level Type) is and how s32 (scalar 32-bit) differs from p0 (pointer)
- Why this distinction matters for WebAssembly where both are i32 at machine level
- What readnone and nounwind function attributes mean and why they guarantee no GC
- How doesNotAccessMemory() maps to readnone and doesNotThrow() maps to nounwind

Co-authored-by: PLUTOFX <110596339+PLUTOFX@users.noreply.github.com>
Copilot AI changed the title Fix SpillPointers pass: reduce false positives in pointer identification Fix SpillPointers pass: reduce false-positive pointer identification to restore 4 failing CodeGen tests Mar 17, 2026
…ar_load test

Remove the Phase 2 dataflow skip for loads and calls, restoring conservative
pointer-ness propagation through these instructions. This is needed for JWST
compiler compatibility where pointer values may be stored as i32 types.

The more conservative propagation means loads whose address operand is a
pointer will also have their result marked as a potential pointer, even if the
MMO type is s32 (scalar). This trades some unnecessary spills for broader
safety in codebases that store pointers as integers.

Update store_past_invar_load test expectations: the invariant load can no
longer be sunk past the call because the SpillPointers pass conservatively
spills the loaded value. This is the expected trade-off for GC safety.

Co-authored-by: PLUTOFX <110596339+PLUTOFX@users.noreply.github.com>
Agent-Logs-Url: https://github.com/PLUTOFX/llvm-project/sessions/4d2b79c7-4d28-42ba-95ce-9394676e5718
Copilot AI changed the title Fix SpillPointers pass: reduce false-positive pointer identification to restore 4 failing CodeGen tests Revert Phase 2 load/call skip in SpillPointers for JWST compiler compatibility Mar 22, 2026
Copilot AI changed the title Revert Phase 2 load/call skip in SpillPointers for JWST compiler compatibility Revert Phase 2 load/call propagation skip in SpillPointers for JWST compiler compatibility Mar 22, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants