[llvm] a90228b - [AArch64][Windows] Fix the slot offset of the swift async context register.
Hiroshi Yamauchi via llvm-commits
llvm-commits at lists.llvm.org
Thu Jul 27 12:33:03 PDT 2023
Author: Hiroshi Yamauchi
Date: 2023-07-27T12:32:43-07:00
New Revision: a90228b911d3c70833a4abe63b81e02a7a8da1f5
URL: https://github.com/llvm/llvm-project/commit/a90228b911d3c70833a4abe63b81e02a7a8da1f5
DIFF: https://github.com/llvm/llvm-project/commit/a90228b911d3c70833a4abe63b81e02a7a8da1f5.diff
LOG: [AArch64][Windows] Fix the slot offset of the swift async context register.
This fixes a code gen issue where savings the swift async context
register (x22) accidentally overwrites the saved value of another
callee-saved register, corrupts its value and causes a crash.
Differential Revision: https://reviews.llvm.org/D156391
Added:
llvm/test/CodeGen/AArch64/swift-async-context-slot-offset-win.ll
Modified:
llvm/lib/Target/AArch64/AArch64FrameLowering.cpp
Removed:
################################################################################
diff --git a/llvm/lib/Target/AArch64/AArch64FrameLowering.cpp b/llvm/lib/Target/AArch64/AArch64FrameLowering.cpp
index d66800664c0ca6..a623339af65f2f 100644
--- a/llvm/lib/Target/AArch64/AArch64FrameLowering.cpp
+++ b/llvm/lib/Target/AArch64/AArch64FrameLowering.cpp
@@ -2699,7 +2699,8 @@ static void computeCalleeSaveRegisterPairs(
// Swift's async context is directly before FP, so allocate an extra
// 8 bytes for it.
if (NeedsFrameRecord && AFI->hasSwiftAsyncContext() &&
- RPI.Reg2 == AArch64::FP)
+ ((!IsWindows && RPI.Reg2 == AArch64::FP) ||
+ (IsWindows && RPI.Reg2 == AArch64::LR)))
ByteOffset += StackFillDir * 8;
assert(!(RPI.isScalable() && RPI.isPaired()) &&
@@ -2728,7 +2729,8 @@ static void computeCalleeSaveRegisterPairs(
// The FP, LR pair goes 8 bytes into our expanded 24-byte slot so that the
// Swift context can directly precede FP.
if (NeedsFrameRecord && AFI->hasSwiftAsyncContext() &&
- RPI.Reg2 == AArch64::FP)
+ ((!IsWindows && RPI.Reg2 == AArch64::FP) ||
+ (IsWindows && RPI.Reg2 == AArch64::LR)))
Offset += 8;
RPI.Offset = Offset / Scale;
diff --git a/llvm/test/CodeGen/AArch64/swift-async-context-slot-offset-win.ll b/llvm/test/CodeGen/AArch64/swift-async-context-slot-offset-win.ll
new file mode 100644
index 00000000000000..86e459a4af7172
--- /dev/null
+++ b/llvm/test/CodeGen/AArch64/swift-async-context-slot-offset-win.ll
@@ -0,0 +1,32 @@
+; RUN: llc -mtriple aarch64-unknown-windows-msvc -filetype asm %s -o - | FileCheck %s
+
+; Check that the slot offset of the async context (x22) doesn't
+; conflict with that of another callee-saved register (x21 here) and
+; saving it won't overwrite the saved value of the callee-saved
+; register.
+;
+; CHECK: sub sp, sp, #64
+; CHECK: str x19, [sp, #16]
+; CHECK: str x21, [sp, #24]
+; CHECK-NOT: stp x29, x30, [sp, #32]
+; CHECK: stp x29, x30, [sp, #40]
+; CHECK-NOT: str x22, [sp, #24]
+; CHECK: str x22, [sp, #32]
+
+declare ptr @llvm.swift.async.context.addr()
+declare swiftcc i64 @foo(i64 %0, i64 %1)
+declare swifttailcc void @tail(ptr swiftasync %0, ptr swiftself dereferenceable(8) %1, i64 %2)
+define internal swifttailcc void @test(ptr swiftasync %0, ptr swiftself %1, i64 %2) {
+entry:
+ %3 = load ptr, ptr %0, align 8
+ %4 = call ptr @llvm.swift.async.context.addr()
+ store ptr %3, ptr %4, align 8
+ %5 = call swiftcc i64 @foo(i64 %2, i64 %2)
+ %6 = call swiftcc i64 @foo(i64 %2, i64 %5)
+ %7 = call swiftcc i64 @foo(i64 %5, i64 %2)
+ %8 = call swiftcc i64 @foo(i64 %7, i64 %6)
+ %9 = call swiftcc i64 @foo(i64 %2, i64 %8)
+ %10 = call ptr @llvm.swift.async.context.addr()
+ musttail call swifttailcc void @tail(ptr swiftasync %10, ptr swiftself %1, i64 %2)
+ ret void
+}
More information about the llvm-commits
mailing list