Skip to content

Commit 41a0a23

Browse files
committed
[RISCV] Emit lpad for function with returns-twice attribute
Insert landing pads after the callsite of attribute "returs-twice" as these functions could result in a indirect call to land after it.
1 parent 00c8e61 commit 41a0a23

File tree

2 files changed

+97
-1
lines changed

2 files changed

+97
-1
lines changed

llvm/lib/Target/RISCV/RISCVIndirectBranchTracking.cpp

Lines changed: 26 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@
2020
#include "llvm/CodeGen/MachineInstrBuilder.h"
2121
#include "llvm/CodeGen/MachineModuleInfo.h"
2222

23-
#define DEBUG_TYPE "riscv-indrect-branch-tracking"
23+
#define DEBUG_TYPE "riscv-indirect-branch-tracking"
2424
#define PASS_NAME "RISC-V Indirect Branch Tracking"
2525

2626
using namespace llvm;
@@ -61,6 +61,16 @@ static void emitLpad(MachineBasicBlock &MBB, const RISCVInstrInfo *TII,
6161
.addImm(Label);
6262
}
6363

64+
static bool IsCallReturnTwice(llvm::MachineOperand &MOp) {
65+
if (!MOp.isGlobal())
66+
return false;
67+
auto *CalleeFn = dyn_cast<Function>(MOp.getGlobal());
68+
if (!CalleeFn)
69+
return false;
70+
AttributeList Attrs = CalleeFn->getAttributes();
71+
return Attrs.hasFnAttr(Attribute::ReturnsTwice);
72+
}
73+
6474
bool RISCVIndirectBranchTracking::runOnMachineFunction(MachineFunction &MF) {
6575
const auto &Subtarget = MF.getSubtarget<RISCVSubtarget>();
6676
const RISCVInstrInfo *TII = Subtarget.getInstrInfo();
@@ -100,5 +110,20 @@ bool RISCVIndirectBranchTracking::runOnMachineFunction(MachineFunction &MF) {
100110
}
101111
}
102112

113+
// Check for calls to functions with ReturnsTwice attribute and insert
114+
// LPAD after such calls
115+
for (MachineBasicBlock &MBB : MF) {
116+
for (MachineBasicBlock::iterator I = MBB.begin(); I != MBB.end(); ++I) {
117+
if (I->isCall() && I->getNumOperands() > 0) {
118+
if (IsCallReturnTwice(I->getOperand(0))) {
119+
auto NextI = std::next(I);
120+
BuildMI(MBB, NextI, MBB.findDebugLoc(NextI), TII->get(RISCV::AUIPC), RISCV::X0)
121+
.addImm(FixedLabel);
122+
Changed = true;
123+
}
124+
}
125+
}
126+
}
127+
103128
return Changed;
104129
}

llvm/test/CodeGen/RISCV/lpad.ll

Lines changed: 71 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -289,3 +289,74 @@ define void @interrupt() "interrupt"="machine" {
289289
; FIXED-ONE-NEXT: mret
290290
ret void
291291
}
292+
293+
declare i32 @setjmp(ptr) returns_twice
294+
295+
define i32 @test_returns_twice() {
296+
; RV32-LABEL: test_returns_twice:
297+
; RV32: # %bb.0:
298+
; RV32-NEXT: lpad 0
299+
; RV32-NEXT: addi sp, sp, -16
300+
; RV32-NEXT: .cfi_def_cfa_offset 16
301+
; RV32-NEXT: sw ra, 12(sp) # 4-byte Folded Spill
302+
; RV32-NEXT: .cfi_offset ra, -4
303+
; RV32-NEXT: addi a0, sp, 8
304+
; RV32-NEXT: call setjmp
305+
; RV32-NEXT: lpad 0
306+
; RV32-NEXT: lw ra, 12(sp) # 4-byte Folded Reload
307+
; RV32-NEXT: .cfi_restore ra
308+
; RV32-NEXT: addi sp, sp, 16
309+
; RV32-NEXT: .cfi_def_cfa_offset 0
310+
; RV32-NEXT: ret
311+
;
312+
; RV64-LABEL: test_returns_twice:
313+
; RV64: # %bb.0:
314+
; RV64-NEXT: lpad 0
315+
; RV64-NEXT: addi sp, sp, -16
316+
; RV64-NEXT: .cfi_def_cfa_offset 16
317+
; RV64-NEXT: sd ra, 8(sp) # 8-byte Folded Spill
318+
; RV64-NEXT: .cfi_offset ra, -8
319+
; RV64-NEXT: addi a0, sp, 4
320+
; RV64-NEXT: call setjmp
321+
; RV64-NEXT: lpad 0
322+
; RV64-NEXT: ld ra, 8(sp) # 8-byte Folded Reload
323+
; RV64-NEXT: .cfi_restore ra
324+
; RV64-NEXT: addi sp, sp, 16
325+
; RV64-NEXT: .cfi_def_cfa_offset 0
326+
; RV64-NEXT: ret
327+
;
328+
; FIXED-ONE-RV32-LABEL: test_returns_twice:
329+
; FIXED-ONE-RV32: # %bb.0:
330+
; FIXED-ONE-RV32-NEXT: lpad 1
331+
; FIXED-ONE-RV32-NEXT: addi sp, sp, -16
332+
; FIXED-ONE-RV32-NEXT: .cfi_def_cfa_offset 16
333+
; FIXED-ONE-RV32-NEXT: sw ra, 12(sp) # 4-byte Folded Spill
334+
; FIXED-ONE-RV32-NEXT: .cfi_offset ra, -4
335+
; FIXED-ONE-RV32-NEXT: addi a0, sp, 8
336+
; FIXED-ONE-RV32-NEXT: call setjmp
337+
; FIXED-ONE-RV32-NEXT: lpad 1
338+
; FIXED-ONE-RV32-NEXT: lw ra, 12(sp) # 4-byte Folded Reload
339+
; FIXED-ONE-RV32-NEXT: .cfi_restore ra
340+
; FIXED-ONE-RV32-NEXT: addi sp, sp, 16
341+
; FIXED-ONE-RV32-NEXT: .cfi_def_cfa_offset 0
342+
; FIXED-ONE-RV32-NEXT: ret
343+
;
344+
; FIXED-ONE-RV64-LABEL: test_returns_twice:
345+
; FIXED-ONE-RV64: # %bb.0:
346+
; FIXED-ONE-RV64-NEXT: lpad 1
347+
; FIXED-ONE-RV64-NEXT: addi sp, sp, -16
348+
; FIXED-ONE-RV64-NEXT: .cfi_def_cfa_offset 16
349+
; FIXED-ONE-RV64-NEXT: sd ra, 8(sp) # 8-byte Folded Spill
350+
; FIXED-ONE-RV64-NEXT: .cfi_offset ra, -8
351+
; FIXED-ONE-RV64-NEXT: addi a0, sp, 4
352+
; FIXED-ONE-RV64-NEXT: call setjmp
353+
; FIXED-ONE-RV64-NEXT: lpad 1
354+
; FIXED-ONE-RV64-NEXT: ld ra, 8(sp) # 8-byte Folded Reload
355+
; FIXED-ONE-RV64-NEXT: .cfi_restore ra
356+
; FIXED-ONE-RV64-NEXT: addi sp, sp, 16
357+
; FIXED-ONE-RV64-NEXT: .cfi_def_cfa_offset 0
358+
; FIXED-ONE-RV64-NEXT: ret
359+
%buf = alloca [1 x i32], align 4
360+
%call = call i32 @setjmp(ptr %buf)
361+
ret i32 %call
362+
}

0 commit comments

Comments
 (0)