[llvm-branch-commits] [llvm] [AArch64][PAC] Emit tail calls more efficiently (PR #220193)
via llvm-branch-commits
llvm-branch-commits at lists.llvm.org
Tue Sep 1 03:02:15 PDT 2026
llvmorg-github-actions[bot] wrote:
<!--LLVM PR SUMMARY COMMENT-->
@llvm/pr-subscribers-backend-aarch64
Author: Anatoly Trosinenko (atrosinenko)
<details>
<summary>Changes</summary>
It may be required to insert explicit checks that LR was authenticated
successfully before performing a tail call. Previously, such checks were
inserted when expanding the TCRETURN pseudo instructions, if the stack
frame was created by the particular function. This did not take into
account the shrink-wrapping optimization, though.
This commit introduces a separate `PAUTH_CHECK_LR` pseudo instruction.
A conservative heuristic is implemented that drops the completely useless
checks. Furthermore, it moves the remaining checks to the shrink-wrapping
epilogue (if any), but only if that doesn't hurt any regular return code
paths.
---
Patch is 56.01 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/220193.diff
6 Files Affected:
- (modified) llvm/lib/Target/AArch64/AArch64AsmPrinter.cpp (+15-32)
- (modified) llvm/lib/Target/AArch64/AArch64InstrInfo.cpp (+20-14)
- (modified) llvm/lib/Target/AArch64/AArch64InstrInfo.td (+7)
- (modified) llvm/lib/Target/AArch64/AArch64PointerAuth.cpp (+142-17)
- (modified) llvm/test/CodeGen/AArch64/ptrauth-tail-call-shrink-wrapping.ll (+12-36)
- (modified) llvm/test/CodeGen/AArch64/sign-return-address-pauth-lr-mir.ll (+273-129)
``````````diff
diff --git a/llvm/lib/Target/AArch64/AArch64AsmPrinter.cpp b/llvm/lib/Target/AArch64/AArch64AsmPrinter.cpp
index 005f69b08a4d3..a038a0eb12444 100644
--- a/llvm/lib/Target/AArch64/AArch64AsmPrinter.cpp
+++ b/llvm/lib/Target/AArch64/AArch64AsmPrinter.cpp
@@ -190,9 +190,6 @@ class AArch64AsmPrinter : public AsmPrinter {
AArch64PAuth::AuthCheckMethod Method,
const MCSymbol *OnFailure = nullptr);
- // Check authenticated LR before tail calling.
- void emitPtrauthTailCallHardening(const MachineInstr *TC);
-
struct PtrAuthSchema {
static PtrAuthSchema CreateImmReg(AArch64PACKey::ID Key, uint64_t IntDisc,
const MachineOperand &AddrDiscOp);
@@ -2244,29 +2241,6 @@ void AArch64AsmPrinter::emitPtrauthCheckAuthenticatedValue(
OutStreamer->emitLabel(SuccessSym);
}
-// With Pointer Authentication, it may be needed to explicitly check the
-// authenticated value in LR before performing a tail call.
-// Otherwise, the callee may re-sign the invalid return address,
-// introducing a signing oracle.
-void AArch64AsmPrinter::emitPtrauthTailCallHardening(const MachineInstr *TC) {
- if (!AArch64FI->shouldSignReturnAddress(*MF))
- return;
-
- auto LRCheckMethod = STI->getAuthenticatedLRCheckMethod(*MF);
- if (LRCheckMethod == AArch64PAuth::AuthCheckMethod::None)
- return;
-
- const AArch64RegisterInfo *TRI = STI->getRegisterInfo();
- Register ScratchReg =
- TC->readsRegister(AArch64::X16, TRI) ? AArch64::X17 : AArch64::X16;
- assert(!TC->readsRegister(ScratchReg, TRI) &&
- "Neither x16 nor x17 is available as a scratch register");
- AArch64PACKey::ID Key =
- AArch64FI->shouldSignWithBKey() ? AArch64PACKey::IB : AArch64PACKey::IA;
- emitPtrauthCheckAuthenticatedValue(AArch64::LR, ScratchReg, Key,
- LRCheckMethod);
-}
-
bool AArch64AsmPrinter::emitDeactivationSymbolRelocation(Value *DS) {
if (!DS)
return false;
@@ -3519,6 +3493,21 @@ void AArch64AsmPrinter::emitInstruction(const MachineInstr *MI) {
emitPtrauthBranch(MI);
return;
+ case AArch64::PAUTH_CHECK_LR: {
+ assert(MI->getNumImplicitOperands() == 1 && "Scratch register expected");
+ Register ScratchReg = MI->implicit_operands().begin()->getReg();
+
+ auto LRCheckMethod = STI->getAuthenticatedLRCheckMethod(*MF);
+ if (LRCheckMethod == AArch64PAuth::AuthCheckMethod::None)
+ return;
+
+ AArch64PACKey::ID Key =
+ AArch64FI->shouldSignWithBKey() ? AArch64PACKey::IB : AArch64PACKey::IA;
+ emitPtrauthCheckAuthenticatedValue(AArch64::LR, ScratchReg, Key,
+ LRCheckMethod);
+ return;
+ }
+
// Tail calls use pseudo instructions so they have the proper code-gen
// attributes (isCall, isReturn, etc.). We lower them to the real
// instruction here.
@@ -3532,8 +3521,6 @@ void AArch64AsmPrinter::emitInstruction(const MachineInstr *MI) {
Register ScratchReg = Callee == AArch64::X16 ? AArch64::X17 : AArch64::X16;
- emitPtrauthTailCallHardening(MI);
-
// See the comments in emitPtrauthBranch.
if (Callee == AddrDisc)
report_fatal_error("Call target is signed with its own value");
@@ -3555,8 +3542,6 @@ void AArch64AsmPrinter::emitInstruction(const MachineInstr *MI) {
case AArch64::TCRETURNrix17:
case AArch64::TCRETURNrinotx16:
case AArch64::TCRETURNriALL: {
- emitPtrauthTailCallHardening(MI);
-
recordIfImportCall(MI);
MCInst TmpInst;
TmpInst.setOpcode(AArch64::BR);
@@ -3565,8 +3550,6 @@ void AArch64AsmPrinter::emitInstruction(const MachineInstr *MI) {
return;
}
case AArch64::TCRETURNdi: {
- emitPtrauthTailCallHardening(MI);
-
MCOperand Dest;
MCInstLowering.lowerOperand(MI->getOperand(0), Dest);
recordIfImportCall(MI);
diff --git a/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp b/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp
index bcff007a00a90..ce1a7dbac76bf 100644
--- a/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp
+++ b/llvm/lib/Target/AArch64/AArch64InstrInfo.cpp
@@ -230,18 +230,6 @@ unsigned AArch64InstrInfo::getInstSizeInBytes(const MachineInstr &MI) const {
if (auto Size = getLFIInstSizeInBytes(MI))
return *Size;
- if (!MI.isBundle() && isTailCallReturnInst(MI)) {
- NumBytes = Desc.getSize() ? Desc.getSize() : 4;
-
- const auto *MFI = MF->getInfo<AArch64FunctionInfo>();
- if (!MFI->shouldSignReturnAddress(*MF))
- return NumBytes;
-
- auto Method = STI.getAuthenticatedLRCheckMethod(*MF);
- NumBytes += AArch64PAuth::getCheckerSizeInBytes(Method);
- return NumBytes;
- }
-
// Size should be preferably set in
// llvm/lib/Target/AArch64/AArch64InstrInfo.td (default case).
// Specific cases handle instructions of variable sizes
@@ -318,6 +306,15 @@ unsigned AArch64InstrInfo::getInstSizeInBytes(const MachineInstr &MI) const {
break;
}
+ case AArch64::PAUTH_CHECK_LR: {
+ const auto *MFI = MF->getInfo<AArch64FunctionInfo>();
+ if (!MFI->shouldSignReturnAddress(*MF))
+ return 0;
+
+ auto Method = STI.getAuthenticatedLRCheckMethod(*MF);
+ return AArch64PAuth::getCheckerSizeInBytes(Method);
+ }
+
case TargetOpcode::BUNDLE:
NumBytes = getInstBundleSize(MI);
break;
@@ -11774,8 +11771,7 @@ void AArch64InstrInfo::createPauthEpilogueInstr(MachineBasicBlock &MBB,
MachineFunction &MF = *MBB.getParent();
MachineRegisterInfo &MRI = MF.getRegInfo();
const auto *AFI = MF.getInfo<AArch64FunctionInfo>();
- auto &AFL = *static_cast<const AArch64FrameLowering *>(
- MF.getSubtarget().getFrameLowering());
+ const AArch64FrameLowering &AFL = *Subtarget.getFrameLowering();
SmallVector<Register, 3> ImplicitDefs;
if (AFL.getArgumentStackToRestore(MF, MBB)) {
@@ -11804,6 +11800,16 @@ void AArch64InstrInfo::createPauthEpilogueInstr(MachineBasicBlock &MBB,
reportFatalUsageError("Cannot insert PAUTH_EPILOGUE: ran out of registers");
};
+ bool MayCheckLR = Subtarget.getAuthenticatedLRCheckMethod(MF) !=
+ AArch64PAuth::AuthCheckMethod::None;
+ if (ImplicitDefs.empty() && MayCheckLR) {
+ // If we may have to check LR at this point, we need a scratch register -
+ // try to pick a free one among X16 and X17.
+ Register ScratchRegForCheckVA =
+ LiveRegs.available(MRI, AArch64::X16) ? AArch64::X16 : AArch64::X17;
+ ImplicitDefs.push_back(ScratchRegForCheckVA);
+ }
+
// Find out which scratch registers have to be spilled to other GPRs,
// mark the rest as unavailable to be spilled-to.
SmallVector<std::pair<Register, Register>, 3> Spills;
diff --git a/llvm/lib/Target/AArch64/AArch64InstrInfo.td b/llvm/lib/Target/AArch64/AArch64InstrInfo.td
index e876ef7597454..b82c9a95dd7da 100644
--- a/llvm/lib/Target/AArch64/AArch64InstrInfo.td
+++ b/llvm/lib/Target/AArch64/AArch64InstrInfo.td
@@ -2115,6 +2115,13 @@ def PAUTH_PROLOGUE : Pseudo<(outs), (ins), []>, Sched<[]> {
def PAUTH_EPILOGUE : Pseudo<(outs), (ins), []>, Sched<[]>;
}
+// Check that LR contains a correctly-authenticated address - depending on the
+// security vs. performance tradeoff, this may be desired before performing a
+// tail call.
+//
+// A scratch register must be provided as an implicit-def operand.
+def PAUTH_CHECK_LR : Pseudo<(outs), (ins), []>, Sched<[]>;
+
// These pointer authentication instructions require armv8.3a
let Predicates = [HasPAuth] in {
diff --git a/llvm/lib/Target/AArch64/AArch64PointerAuth.cpp b/llvm/lib/Target/AArch64/AArch64PointerAuth.cpp
index 0e4a51286cf54..2dfa8e14c8e24 100644
--- a/llvm/lib/Target/AArch64/AArch64PointerAuth.cpp
+++ b/llvm/lib/Target/AArch64/AArch64PointerAuth.cpp
@@ -14,6 +14,8 @@
#include "AArch64MachineFunctionInfo.h"
#include "AArch64Subtarget.h"
#include "MCTargetDesc/AArch64AddressingModes.h"
+#include "llvm/ADT/BreadthFirstIterator.h"
+#include "llvm/ADT/SmallSet.h"
#include "llvm/CodeGen/CFIInstBuilder.h"
#include "llvm/CodeGen/MachineBasicBlock.h"
#include "llvm/CodeGen/MachineInstrBuilder.h"
@@ -67,6 +69,13 @@ class AArch64PointerAuthImpl {
private:
const AArch64Subtarget *Subtarget = nullptr;
const AArch64InstrInfo *TII = nullptr;
+ const AArch64RegisterInfo *TRI = nullptr;
+
+ bool
+ rewriteProloguesEpilogues(MachineFunction &MF,
+ ArrayRef<MachineInstr *> PAuthPseudoInstrs) const;
+ bool insertLRChecks(MachineFunction &MF,
+ ArrayRef<MachineInstr *> PAuthPseudoInstrs) const;
void signLR(MachineFunction &MF, MachineBasicBlock::iterator MBBI) const;
@@ -512,12 +521,137 @@ unsigned llvm::AArch64PAuth::getCheckerSizeInBytes(AuthCheckMethod Method) {
llvm_unreachable("Unknown AuthCheckMethod enum");
}
+bool AArch64PointerAuthImpl::rewriteProloguesEpilogues(
+ MachineFunction &MF, ArrayRef<MachineInstr *> PAuthPseudoInstrs) const {
+ for (auto *MI : PAuthPseudoInstrs) {
+ switch (MI->getOpcode()) {
+ case AArch64::PAUTH_PROLOGUE:
+ signLR(MF, MI->getIterator());
+ break;
+ case AArch64::PAUTH_EPILOGUE:
+ authenticateLR(MF, MI->getIterator());
+ break;
+ default:
+ llvm_unreachable("Unhandled opcode");
+ }
+ }
+
+ return !PAuthPseudoInstrs.empty();
+}
+
+// Insert PAUTH_CHECK_LR before the tail calls as needed.
+//
+// Currently, if the function creates a stack frame, PAUTH_EPILOGUE is either
+// inserted before every point where the function is exited or at the single
+// point where the function's epilogue was placed due to shrink-wrapping.
+//
+// Putting aside microarchitectural details, there are several possibilities:
+// * checking LR before exiting the function with a regular `ret` (aliased to
+// `ret lr`) wastes CPU time, but it is still permitted from the correctness
+// point of view
+// * if every code path leading to the given tail call involves reloading LR
+// from the stack, then the check can be kept right before the tail call or
+// moved to the shrink-wrapped PAUTH_EPILOGUE - the number of executed
+// instructions is the same in both cases, but the latter may help decreasing
+// the code size
+// * if LR is never spilled to the stack before the given tail call, then the
+// check can be dropped without any further consequences
+// * if, due to shrink-wrapping optimization, the LR is spilled to the stack
+// conditionally before the given tail call, then moving the check right after
+// PAUTH_EPILOGUE would be beneficial both for CPU time and (possibly) the
+// code size when the function is exited via this particular tail call, but
+// may hurt regular function `ret`s of the other code paths.
+//
+// To never make things worse and optimize common cases, this functions uses
+// the heuristic equivalent to the following:
+// 1. Enumerate the set of all PAUTH_EPILOGUE and all tail call instructions.
+// 2. Remove the tail calls that are not reachable from any PAUTH_EPILOGUE and
+// PAUTH_EPILOGUEs that have no tail calls reachable from them from the
+// corresponding sets.
+// 3a. Insert PAUTH_CHECK_LR after each PAUTH_EPILOGUE in the set, if no
+// regular return instruction is reachable from any of them.
+// 3b. Otherwise insert PAUTH_CHECK_LR before every tail call in the set.
+//
+// Note that no special handling is required for the "sign-return-address"="all"
+// case, as the PAUTH_EPILOGUE pseudo instructions are conservatively placed
+// by PEI right before the function is exited.
+bool AArch64PointerAuthImpl::insertLRChecks(
+ MachineFunction &MF, ArrayRef<MachineInstr *> PAuthPseudoInstrs) const {
+ auto CheckMethod = Subtarget->getAuthenticatedLRCheckMethod(MF);
+ if (CheckMethod == AArch64PAuth::AuthCheckMethod::None)
+ return false;
+
+ bool Modified = false;
+
+ bool ShouldCheckAtEpilogues = true;
+ // The set of PAUTH_EPILOGUE instructions followed by at least one tail call.
+ SmallSet<MachineInstr *, 8> EpiloguesToCheck;
+ // The set of tail calls reachable from at least one PAUTH_EPILOGUE.
+ SmallSet<MachineInstr *, 8> TailCallsToCheck;
+
+ for (MachineInstr *ThisMI : PAuthPseudoInstrs) {
+ if (ThisMI->getOpcode() != AArch64::PAUTH_EPILOGUE)
+ continue;
+
+ MachineBasicBlock *ThisBB = ThisMI->getParent();
+ bool HasReachableTailCalls = false;
+ bool HasReachableReturns = false;
+
+ for (MachineBasicBlock *ReachableBB : breadth_first(ThisBB)) {
+ for (auto &TI : ReachableBB->terminators()) {
+ if (TII->isTailCall(TI)) {
+ TailCallsToCheck.insert(&TI);
+ HasReachableTailCalls = true;
+ } else if (TI.isReturn()) {
+ HasReachableReturns = true;
+ }
+ }
+ }
+
+ if (HasReachableTailCalls)
+ EpiloguesToCheck.insert(ThisMI);
+ if (HasReachableTailCalls && HasReachableReturns)
+ ShouldCheckAtEpilogues = false;
+ }
+
+ auto InsertCheck = [&](MachineBasicBlock::iterator MBBI, Register Scratch,
+ bool InsertAfter) {
+ MachineBasicBlock *MBB = MBBI->getParent();
+ DebugLoc DL = MBBI->getDebugLoc();
+
+ auto InsertPt = InsertAfter ? std::next(MBBI) : MBBI;
+ BuildMI(*MBB, InsertPt, DL, TII->get(AArch64::PAUTH_CHECK_LR))
+ .addReg(Scratch, RegState::ImplicitDefine);
+ Modified = true;
+ };
+
+ // TODO When optimization for size is requested, we could move the check to
+ // the shrink-wrapped epilogue unconditionally.
+ if (ShouldCheckAtEpilogues) {
+ for (MachineInstr *MI : EpiloguesToCheck) {
+ Register Scratch =
+ MI->definesRegister(AArch64::X16, TRI) ? AArch64::X16 : AArch64::X17;
+ assert(MI->definesRegister(Scratch, TRI));
+ InsertCheck(MI->getIterator(), Scratch, /*InsertAfter=*/true);
+ }
+ } else {
+ for (MachineInstr *MI : TailCallsToCheck) {
+ Register Scratch =
+ MI->readsRegister(AArch64::X16, TRI) ? AArch64::X17 : AArch64::X16;
+ assert(!MI->readsRegister(Scratch, TRI));
+ InsertCheck(MI->getIterator(), Scratch, /*InsertAfter=*/false);
+ }
+ }
+
+ return Modified;
+}
+
bool AArch64PointerAuthImpl::run(MachineFunction &MF) {
Subtarget = &MF.getSubtarget<AArch64Subtarget>();
TII = Subtarget->getInstrInfo();
+ TRI = Subtarget->getRegisterInfo();
- SmallVector<MachineBasicBlock::instr_iterator> PAuthPseudoInstrs;
-
+ SmallVector<MachineInstr *> PAuthPseudoInstrs;
bool Modified = false;
for (auto &MBB : MF) {
@@ -527,26 +661,17 @@ bool AArch64PointerAuthImpl::run(MachineFunction &MF) {
break;
case AArch64::PAUTH_PROLOGUE:
case AArch64::PAUTH_EPILOGUE:
- PAuthPseudoInstrs.push_back(MI.getIterator());
+ PAuthPseudoInstrs.push_back(&MI);
break;
}
}
}
- for (auto It : PAuthPseudoInstrs) {
- switch (It->getOpcode()) {
- case AArch64::PAUTH_PROLOGUE:
- signLR(MF, It);
- break;
- case AArch64::PAUTH_EPILOGUE:
- authenticateLR(MF, It);
- break;
- default:
- llvm_unreachable("Unhandled opcode");
- }
- It->eraseFromParent();
- Modified = true;
- }
+ Modified |= rewriteProloguesEpilogues(MF, PAuthPseudoInstrs);
+ Modified |= insertLRChecks(MF, PAuthPseudoInstrs);
+
+ for (auto *MI : PAuthPseudoInstrs)
+ MI->eraseFromParent();
return Modified;
}
diff --git a/llvm/test/CodeGen/AArch64/ptrauth-tail-call-shrink-wrapping.ll b/llvm/test/CodeGen/AArch64/ptrauth-tail-call-shrink-wrapping.ll
index 6f71719dc1e6f..85bddb0c62876 100644
--- a/llvm/test/CodeGen/AArch64/ptrauth-tail-call-shrink-wrapping.ll
+++ b/llvm/test/CodeGen/AArch64/ptrauth-tail-call-shrink-wrapping.ll
@@ -107,11 +107,11 @@ define i64 @test_single_tailcall_reloaded_lr(i64 %arg) #0 {
; ASM-NEXT: //NO_APP
; ASM-NEXT: ldr x30, [sp], #16
; ASM-NEXT: autiasp
-; ASM-NEXT: .LBB3_2:
; ASM-NEXT: eor x16, x30, x30, lsl #1
; ASM-NEXT: tbz x16, #62, .Lauth_success_2
; ASM-NEXT: brk #0xc470
; ASM-NEXT: .Lauth_success_2:
+; ASM-NEXT: .LBB3_2:
; ASM-NEXT: b callee
%cond = icmp eq i64 %arg, 0
br i1 %cond, label %if.end, label %if.then
@@ -194,10 +194,6 @@ define i64 @test_single_safe_tailcall_single_return(i64 %arg) #0 {
; ASM-NEXT: ldr x30, [sp], #16
; ASM-NEXT: retaa
; ASM-NEXT: .LBB5_2:
-; ASM-NEXT: eor x16, x30, x30, lsl #1
-; ASM-NEXT: tbz x16, #62, .Lauth_success_5
-; ASM-NEXT: brk #0xc470
-; ASM-NEXT: .Lauth_success_5:
; ASM-NEXT: b callee
%cond = icmp eq i64 %arg, 0
br i1 %cond, label %do.tailcall, label %ret.to.authed.lr
@@ -227,15 +223,11 @@ define i64 @test_two_tailcalls(i64 %arg) #0 {
; ASM-NEXT: ldr x30, [sp], #16
; ASM-NEXT: autiasp
; ASM-NEXT: eor x16, x30, x30, lsl #1
-; ASM-NEXT: tbz x16, #62, .Lauth_success_6
+; ASM-NEXT: tbz x16, #62, .Lauth_success_5
; ASM-NEXT: brk #0xc470
-; ASM-NEXT: .Lauth_success_6:
+; ASM-NEXT: .Lauth_success_5:
; ASM-NEXT: b callee
; ASM-NEXT: .LBB6_2:
-; ASM-NEXT: eor x16, x30, x30, lsl #1
-; ASM-NEXT: tbz x16, #62, .Lauth_success_7
-; ASM-NEXT: brk #0xc470
-; ASM-NEXT: .Lauth_success_7:
; ASM-NEXT: b callee2
%cond = icmp eq i64 %arg, 0
br i1 %cond, label %do.tailcall.safe.lr, label %do.tailcall.authed.lr
@@ -277,15 +269,11 @@ define i64 @test_unlikely_tailcall_after_shrink_wrapped_epilogue(i64 %arg) #0 {
; ASM-NEXT: cmp x8, #11
; ASM-NEXT: b.lo .LBB7_8
; ASM-NEXT: eor x16, x30, x30, lsl #1
-; ASM-NEXT: tbz x16, #62, .Lauth_success_8
+; ASM-NEXT: tbz x16, #62, .Lauth_success_6
; ASM-NEXT: brk #0xc470
-; ASM-NEXT: .Lauth_success_8:
+; ASM-NEXT: .Lauth_success_6:
; ASM-NEXT: b callee
; ASM-NEXT: .LBB7_5:
-; ASM-NEXT: eor x16, x30, x30, lsl #1
-; ASM-NEXT: tbz x16, #62, .Lauth_success_9
-; ASM-NEXT: brk #0xc470
-; ASM-NEXT: .Lauth_success_9:
; ASM-NEXT: b callee2
; ASM-NEXT: .LBB7_6:
; ASM-NEXT: mov x0, x8
@@ -349,25 +337,17 @@ define i64 @test_only_tailcalls_after_shrink_wrapped_epilogue(i64 %arg, i64 %arg
; ASM-NEXT: //NO_APP
; ASM-NEXT: ldr x30, [sp], #16
; ASM-NEXT: autiasp
-; ASM-NEXT: cbz x8, .LBB8_5
; ASM-NEXT: eor x16, x30, x30, lsl #1
-; ASM-NEXT: tbz x16, #62, .Lauth_success_10
+; ASM-NEXT: tbz x16, #62, .Lauth_success_7
; ASM-NEXT: brk #0xc470
-; ASM-NEXT: .Lauth_success_10:
+; ASM-NEXT: .Lauth_success_7:
+; ASM-NEXT: cbz x8, .LBB8_5
; ASM-NEXT: b callee2
; ASM-NEXT: .LBB8_3:
; ASM-NEXT: cmp x1, #999
; ASM-NEXT: b.hi .LBB8_6
-; ASM-NEXT: eor x16, x30, x30, lsl #1
-; ASM-NEXT: tbz x16, #62, .Lauth_success_11
-; ASM-NEXT: brk #0xc470
-; ASM-NEXT: .Lauth_success_11:
; ASM-NEXT: b callee3
; ASM-NEXT: .LBB8_5:
-; ASM-NEXT: eor x16, x30, x30, lsl #1
-; ASM-NEXT: tbz x16, #62, .Lauth_success_12
-; ASM-NEXT: brk #0xc470
-; ASM-NEXT: .Lauth_success_12:
; ASM-NEXT: b callee
; ASM-NEXT: .LBB8_6:
; ASM-NEXT: add x0, x1, #1
@@ -425,21 +405,17 @@ define i64 @test_various_exits_after_shrink_wrapped_epilogue(i64 %arg) #0 {
; ASM-NEXT: cmp x0, #999
; ASM-NEXT: b.hi .LBB9_6
; ASM-NEXT: eor x16, x30, x30, lsl #1
-; ASM-NEXT: tbz x16, #62, .Lauth_success_13
+; ASM-NEXT: tbz x16, #62, .Lauth_success_8
; ASM-NEXT: brk #0xc470
-; ASM-NEXT: .Lauth_success_13:
+; ASM-NEXT: .Lauth_success_8:
; ASM-NEXT: b callee2
; ASM-NEXT: .LBB9_4:
-; ASM-NEXT: eor x16, x30, x30, lsl #1
-; ASM-NEXT: tbz x16, #62, .Lauth_success_14
-; ASM-NEXT: brk #0xc470
-; ASM-NEXT: .Lauth_success_14:
; ASM-NEXT: b callee3
; ASM-NEXT: .LBB9_5:
; ASM-NEXT: eor x16, x30, x30, lsl #1
-; ASM-NEXT: tbz x16, #62, .Lauth_success_15
+; ASM-NEXT: tbz x16, #62, .Lauth_success_9
; ASM-NEXT: brk #0xc470
-; ASM-NEXT: .Lauth_success_15:
+; ASM-NEXT: .Lauth_success_9:
; ASM-NEXT: b callee
; ASM-NEXT: .LBB9_6:
; ASM-NEXT: add x0, x0, #1
diff --git a/llvm/test/CodeGen/AArch64/sign-return-address-pauth-lr-mir.ll b/llvm/test/CodeGen/AArch64/sign-return-address-pauth-lr-mir.ll
index d975350b1e9e6..66e544f9346ae 100644
--- a/llvm/test/CodeGen/AArch64/sign-return-address-pauth-lr-mir.ll
+++ b/llvm/test/CodeGen/AArch64/sign-return-address-pauth-lr-mir.ll
@@ -1,8 +1,11 @@
; NOTE: Assertions have been autogenerated by utils/update_mir_test_checks.py
-; RUN: llc -mtriple=aarch64 -stop-after=aarch64-ptrauth < %s | FileCheck --check-prefixes=CHECK-MIR,COMPAT-MIR %s
-; RUN: llc -mtriple=aarch64 -stop-after=aarch64-ptrauth -mattr=v8.3a < %s | FileCheck --...
[truncated]
``````````
</details>
https://github.com/llvm/llvm-project/pull/220193
More information about the llvm-branch-commits
mailing list