[all-commits] [llvm/llvm-project] 121d53: [AArch64][Windows] Fix swift async context slot pl...

Sébastien Marchand via All-commits all-commits at lists.llvm.org
Wed Aug 5 17:48:32 PDT 2026


  Branch: refs/heads/release/23.x
  Home:   https://github.com/llvm/llvm-project
  Commit: 121d539a6e83609c943f054dcc5b2c5ed48c5281
      https://github.com/llvm/llvm-project/commit/121d539a6e83609c943f054dcc5b2c5ed48c5281
  Author: Sébastien Marchand <sebmarchand at users.noreply.github.com>
  Date:   2026-08-06 (Thu, 06 Aug 2026)

  Changed paths:
    M llvm/lib/Target/AArch64/AArch64FrameLowering.cpp
    A llvm/test/CodeGen/AArch64/swift-async-context-frame-record-win.ll
    M llvm/test/CodeGen/AArch64/swift-async-context-seh.ll
    M llvm/test/CodeGen/AArch64/swift-async-context-slot-offset-win.ll
    M llvm/test/CodeGen/AArch64/swift-async-win.ll
    M llvm/test/CodeGen/AArch64/win-sve.ll

  Log Message:
  -----------
  [AArch64][Windows] Fix swift async context slot placement (#212922)

Swift async functions can miscompile on Windows ARM64 at `-O2`, when
there's enough register pressure that a local gets scavenged into the
callee-save area: the local ends up sharing an address with the saved
caller x29, so the epilogue restores a value the function has already
overwritten. swiftlang/swift#90920 has a reduced repro.

`assignCalleeSavedSpillSlots` creates the swift async context object
before the callee-save loop instead of inside it next to the FP slot.
MachineFrameInfo ends up with it above the frame record while the
prologue stores it below at FP-8, and the 8 byte disagreement leaves a
hole in the middle of the callee-save area. PEI's scavenger hands that
hole to the local. Only reproduces at -O2 and up since scavenging is
gated on the opt level.

```
	sub	sp, sp, #112
	str	x19, [sp, #16]                  // 8-byte Spill
	str	x21, [sp, #24]                  // 8-byte Spill
	stp	x23, x24, [sp, #32]             // 16-byte Folded Spill
	stp	x25, x26, [sp, #48]             // 16-byte Folded Spill
	stp	x27, x28, [sp, #64]             // 16-byte Folded Spill
	stp	x29, x30, [sp, #88]             // 16-byte Folded Spill
	str	xzr, [sp, #80]
	add	x29, sp, #88
	...
	str	x7, [x29]                       // 8-byte Spill
	...
	ldr	x1, [x29]                       // 8-byte Reload
	ldp	x29, x30, [sp, #88]             // 16-byte Folded Reload
```

This creates the object inside the loop so the two agree. The other
option was leaving the creation site alone and teaching MachineFrameInfo
about the expanded 24 byte FP/LR slot, but that puts the layout in two
places. Not sure which is preferred here, I don't know this code well.

This also asserts the saved FP object resolves to FP+0, since nothing
checks that today. Reverting the fix makes it fire on the same funclet.
`store-swift-async-context-clobber-live-reg.ll` already miscompiles with
`-regalloc=fast`, so this isn't Swift specific.

(cherry picked from commit c358e8d90b3b26db86046f19de29bc848f255ac8)



To unsubscribe from these emails, change your notification settings at https://github.com/llvm/llvm-project/settings/notifications


More information about the All-commits mailing list