[llvm] c31f0a0 - AArch64: correct epilogue/prologue emission for swift async

Saleem Abdulrasool via llvm-commits llvm-commits at lists.llvm.org
Wed Mar 9 10:41:29 PST 2022


Author: Saleem Abdulrasool
Date: 2022-03-09T18:41:10Z
New Revision: c31f0a00503a36bc6fa6c27b94369ded6c37ba59

URL: https://github.com/llvm/llvm-project/commit/c31f0a00503a36bc6fa6c27b94369ded6c37ba59
DIFF: https://github.com/llvm/llvm-project/commit/c31f0a00503a36bc6fa6c27b94369ded6c37ba59.diff

LOG: AArch64: correct epilogue/prologue emission for swift async

The prologue and epilogue emission were unbalanced in light of different
strategies of async frame context emission.  Adjust the epilogue emission
to match the prologue emission.  This makes the elision work properly as
well as the deployment based.  Due to the fact that the epilogue always
was clearing a bit (which should not be set in the first place), the
client would not notice the behavioural issue unless the deployment
version was in effect.

Added: 
    llvm/test/CodeGen/AArch64/swift-async-pei.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 5057cab7e7e52..1c21f9a58ab84 100644
--- a/llvm/lib/Target/AArch64/AArch64FrameLowering.cpp
+++ b/llvm/lib/Target/AArch64/AArch64FrameLowering.cpp
@@ -1846,15 +1846,27 @@ void AArch64FrameLowering::emitEpilogue(MachineFunction &MF,
   }
 
   if (hasFP(MF) && AFI->hasSwiftAsyncContext()) {
-    // We need to reset FP to its untagged state on return. Bit 60 is currently
-    // used to show the presence of an extended frame.
-
-    // BIC x29, x29, #0x1000_0000_0000_0000
-    BuildMI(MBB, MBB.getFirstTerminator(), DL, TII->get(AArch64::ANDXri),
-            AArch64::FP)
-        .addUse(AArch64::FP)
-        .addImm(0x10fe)
-        .setMIFlag(MachineInstr::FrameDestroy);
+    switch (MF.getTarget().Options.SwiftAsyncFramePointer) {
+    case SwiftAsyncFramePointerMode::DeploymentBased:
+      // Avoid the reload as it is GOT relative, and instead fall back to the
+      // hardcoded value below.  This allows a mismatch between the OS and
+      // application without immediately terminating on the 
diff erence.
+      LLVM_FALLTHROUGH;
+    case SwiftAsyncFramePointerMode::Always:
+      // We need to reset FP to its untagged state on return. Bit 60 is
+      // currently used to show the presence of an extended frame.
+
+      // BIC x29, x29, #0x1000_0000_0000_0000
+      BuildMI(MBB, MBB.getFirstTerminator(), DL, TII->get(AArch64::ANDXri),
+              AArch64::FP)
+          .addUse(AArch64::FP)
+          .addImm(0x10fe)
+          .setMIFlag(MachineInstr::FrameDestroy);
+      break;
+
+    case SwiftAsyncFramePointerMode::Never:
+      break;
+    }
   }
 
   const StackOffset &SVEStackSize = getSVEStackSize(MF);

diff  --git a/llvm/test/CodeGen/AArch64/swift-async-pei.ll b/llvm/test/CodeGen/AArch64/swift-async-pei.ll
new file mode 100644
index 0000000000000..2369457d81b3a
--- /dev/null
+++ b/llvm/test/CodeGen/AArch64/swift-async-pei.ll
@@ -0,0 +1,64 @@
+; RUN: llc -mtriple arm64-apple-ios -filetype asm -o - %s -swift-async-fp always | FileCheck %s -check-prefix CHECK-IOS-ALWAYS
+; RUN: llc -mtriple arm64-apple-ios -filetype asm -o - %s -swift-async-fp never | FileCheck %s -check-prefix CHECK-IOS-NEVER
+; RUN: llc -mtriple arm64-apple-ios -filetype asm -o - %s -swift-async-fp auto | FileCheck %s -check-prefix CHECK-IOS-AUTO
+; RUN: llc -mtriple arm64_32-apple-watchos -filetype asm -o - %s -swift-async-fp always | FileCheck %s -check-prefix CHECK-WATCHOS-ALWAYS
+; RUN: llc -mtriple arm64_32-apple-watchos -filetype asm -o - %s -swift-async-fp never | FileCheck %s -check-prefix CHECK-WATCHOS-NEVER
+; RUN: llc -mtriple arm64_32-apple-watchos -filetype asm -o - %s -swift-async-fp auto | FileCheck %s -check-prefix CHECK-WATCHOS-AUTO
+
+declare i8** @llvm.swift.async.context.addr()
+
+define swifttailcc void @f(i8* swiftasync %ctx) {
+  %1 = bitcast i8* %ctx to i8**
+  %2 = load i8*, i8** %1, align 8
+  %3 = tail call i8** @llvm.swift.async.context.addr()
+  store i8* %2, i8** %3, align 8
+  ret void
+}
+
+; CHECK-IOS-NEVER: sub sp, sp, #32
+; CHECK-IOS-NEVER: stp x29, x30, [sp, #16]
+; ...
+; CHECK-IOS-NEVER: ldp x29, x30, [sp, #16]
+; CHECK-IOS-NEVER: add sp, sp, #32
+
+; CHECK-IOS-ALWAYS: orr x29, x29, #0x1000000000000000
+; CHECK-IOS-ALWAYS: sub sp, sp, #32
+; CHECK-IOS-ALWAYS: stp x29, x30, [sp, #16]
+; ...
+; CHECK-IOS-ALWAYS: ldp x29, x30, [sp, #16]
+; CHECK-IOS-ALWAYS: and x29, x29, #0xefffffffffffffff
+; CHECK-IOS-ALWAYS: add sp, sp, #32
+
+; CHECK-IOS-AUTO: adrp x16, _swift_async_extendedFramePointerFlags at GOTPAGE
+; CHECK-IOS-AUTO: ldr x16, [x16, _swift_async_extendedFramePointerFlags at GOTPAGEOFF]
+; CHECK-IOS-AUTO: orr x29, x29, x16
+; CHECK-IOS-AUTO: sub sp, sp, #32
+; CHECK-IOS-AUTO: stp x29, x30, [sp, #16]
+; ...
+; CHECK-IOS-AUTO: ldp x29, x30, [sp, #16]
+; CHECK-IOS-AUTO: and x29, x29, #0xefffffffffffffff
+; CHECK-IOS-AUTO: add sp, sp, #32
+
+; CHECK-WATCHOS-NEVER: sub sp, sp, #32
+; CHECK-WATCHOS-NEVER: stp x29, x30, [sp, #16]
+; ...
+; CHECK-WATCHOS-NEVER: ldp x29, x30, [sp, #16]
+; CHECK-WATCHOS-NEVER: add sp, sp, #32
+
+; CHECK-WATCHOS-ALWAYS: orr x29, x29, #0x1000000000000000
+; CHECK-WATCHOS-ALWAYS: sub sp, sp, #32
+; CHECK-WATCHOS-ALWAYS: stp x29, x30, [sp, #16]
+; ...
+; CHECK-WATCHOS-ALWAYS: ldp x29, x30, [sp, #16]
+; CHECK-WATCHOS-ALWAYS: and x29, x29, #0xefffffffffffffff
+; CHECK-WATCHOS-ALWAYS: add sp, sp, #32
+
+; CHECK-WATCHOS-AUTO: adrp x16, _swift_async_extendedFramePointerFlags at GOTPAGE
+; CHECK-WATCHOS-AUTO: ldr w16, [x16, _swift_async_extendedFramePointerFlags at GOTPAGEOFF]
+; CHECK-WATCHOS-AUTO: orr x29, x29, x16, lsl #32
+; CHECK-WATCHOS-AUTO: sub sp, sp, #32
+; CHECK-WATCHOS-AUTO: stp x29, x30, [sp, #16]
+; ...
+; CHECK-WATCHOS-AUTO: ldp x29, x30, [sp, #16]
+; CHECK-WATCHOS-AUTO: and x29, x29, #0xefffffffffffffff
+; CHECK-WATCHOS-AUTO: add sp, sp, #32


        


More information about the llvm-commits mailing list