Skip to content

Commit 49138d9

Browse files
authored
[X86] Fix SLH crash on llvm.eh.sjlh.longjmp (#77959)
Fix #60081.
1 parent e4a6be0 commit 49138d9

File tree

2 files changed

+36
-2
lines changed

2 files changed

+36
-2
lines changed

llvm/lib/Target/X86/X86SpeculativeLoadHardening.cpp

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1840,7 +1840,7 @@ MachineInstr *X86SpeculativeLoadHardeningPass::sinkPostLoadHardenedInst(
18401840
// just bail. Also check that its register class is one of the ones we
18411841
// can harden.
18421842
Register UseDefReg = UseMI.getOperand(0).getReg();
1843-
if (!UseDefReg.isVirtual() || !canHardenRegister(UseDefReg))
1843+
if (!canHardenRegister(UseDefReg))
18441844
return {};
18451845

18461846
SingleUseMI = &UseMI;
@@ -1863,6 +1863,10 @@ MachineInstr *X86SpeculativeLoadHardeningPass::sinkPostLoadHardenedInst(
18631863
}
18641864

18651865
bool X86SpeculativeLoadHardeningPass::canHardenRegister(Register Reg) {
1866+
// We only support hardening virtual registers.
1867+
if (!Reg.isVirtual())
1868+
return false;
1869+
18661870
auto *RC = MRI->getRegClass(Reg);
18671871
int RegBytes = TRI->getRegSizeInBits(*RC) / 8;
18681872
if (RegBytes > 8)
@@ -1909,7 +1913,6 @@ unsigned X86SpeculativeLoadHardeningPass::hardenValueInRegister(
19091913
Register Reg, MachineBasicBlock &MBB, MachineBasicBlock::iterator InsertPt,
19101914
const DebugLoc &Loc) {
19111915
assert(canHardenRegister(Reg) && "Cannot harden this register!");
1912-
assert(Reg.isVirtual() && "Cannot harden a physical register!");
19131916

19141917
auto *RC = MRI->getRegClass(Reg);
19151918
int Bytes = TRI->getRegSizeInBits(*RC) / 8;

llvm/test/CodeGen/X86/speculative-load-hardening.ll

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1161,3 +1161,34 @@ define void @idempotent_atomic(ptr %x) speculative_load_hardening {
11611161
%tmp = atomicrmw or ptr %x, i32 0 seq_cst
11621162
ret void
11631163
}
1164+
1165+
; Make sure we don't crash on longjmps (PR60081).
1166+
declare void @llvm.eh.sjlj.longjmp(ptr)
1167+
define void @test_longjmp(ptr %env) speculative_load_hardening {
1168+
; X64-LABEL: test_longjmp:
1169+
; X64: # %bb.0:
1170+
; X64-NEXT: pushq %rbp
1171+
; X64-NEXT: .cfi_def_cfa_offset 16
1172+
; X64-NEXT: .cfi_offset %rbp, -16
1173+
; X64-NEXT: movq %rsp, %rax
1174+
; X64-NEXT: movq $-1, %rcx
1175+
; X64-NEXT: sarq $63, %rax
1176+
; X64-NEXT: orq %rax, %rdi
1177+
; X64-NEXT: movq (%rdi), %rbp
1178+
; X64-NEXT: movq 8(%rdi), %rcx
1179+
; X64-NEXT: movq 16(%rdi), %rsp
1180+
; X64-NEXT: orq %rax, %rcx
1181+
; X64-NEXT: jmpq *%rcx
1182+
;
1183+
; X64-LFENCE-LABEL: test_longjmp:
1184+
; X64-LFENCE: # %bb.0:
1185+
; X64-LFENCE-NEXT: pushq %rbp
1186+
; X64-LFENCE-NEXT: .cfi_def_cfa_offset 16
1187+
; X64-LFENCE-NEXT: .cfi_offset %rbp, -16
1188+
; X64-LFENCE-NEXT: movq (%rdi), %rbp
1189+
; X64-LFENCE-NEXT: movq 8(%rdi), %rax
1190+
; X64-LFENCE-NEXT: movq 16(%rdi), %rsp
1191+
; X64-LFENCE-NEXT: jmpq *%rax
1192+
call void @llvm.eh.sjlj.longjmp(ptr %env)
1193+
unreachable
1194+
}

0 commit comments

Comments
 (0)