Skip to content

Commit 5438e6a

Browse files
committed
[RISCV] fix RISCVPushPopOptimizer pass
RISCVPushPopOptimizer pass didn't suggest that CFI instructions can be inserted between cm.pop and ret and couldn't apply optimization in these cases. The patch fix it and allows the pass to remove CFI instructions and combine cm.pop and ret into the one instruction: cm.popret or cm.popretz.
1 parent 0573a78 commit 5438e6a

File tree

1 file changed

+22
-4
lines changed

1 file changed

+22
-4
lines changed

llvm/lib/Target/RISCV/RISCVPushPopOptimizer.cpp

Lines changed: 22 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -45,10 +45,25 @@ char RISCVPushPopOpt::ID = 0;
4545
INITIALIZE_PASS(RISCVPushPopOpt, "riscv-push-pop-opt", RISCV_PUSH_POP_OPT_NAME,
4646
false, false)
4747

48+
template <typename IterT>
49+
static IterT nextNoDebugNoCFIInst(const IterT It, const IterT End) {
50+
return std::find_if_not(std::next(It), End, [](const auto &Inst) {
51+
return Inst.isDebugInstr() || Inst.isCFIInstruction() ||
52+
Inst.isPseudoProbe();
53+
});
54+
}
55+
56+
static void eraseCFIInst(const MachineBasicBlock::iterator Begin,
57+
const MachineBasicBlock::iterator End) {
58+
for (auto &Inst : llvm::make_early_inc_range(llvm::make_range(Begin, End)))
59+
if (Inst.isCFIInstruction())
60+
Inst.eraseFromParent();
61+
}
62+
4863
// Check if POP instruction was inserted into the MBB and return iterator to it.
4964
static MachineBasicBlock::iterator containsPop(MachineBasicBlock &MBB) {
5065
for (MachineBasicBlock::iterator MBBI = MBB.begin(); MBBI != MBB.end();
51-
MBBI = next_nodbg(MBBI, MBB.end()))
66+
MBBI = nextNoDebugNoCFIInst(MBBI, MBB.end()))
5267
if (MBBI->getOpcode() == RISCV::CM_POP)
5368
return MBBI;
5469

@@ -76,6 +91,9 @@ bool RISCVPushPopOpt::usePopRet(MachineBasicBlock::iterator &MBBI,
7691
for (unsigned i = FirstNonDeclaredOp; i < MBBI->getNumOperands(); ++i)
7792
PopRetBuilder.add(MBBI->getOperand(i));
7893

94+
// Remove CFI instructions, they are not needed for cm.popret and cm.popretz
95+
eraseCFIInst(MBBI, NextI);
96+
7997
MBBI->eraseFromParent();
8098
NextI->eraseFromParent();
8199
return true;
@@ -92,8 +110,8 @@ bool RISCVPushPopOpt::adjustRetVal(MachineBasicBlock::iterator &MBBI) {
92110
// Since POP instruction is in Epilogue no normal instructions will follow
93111
// after it. Therefore search only previous ones to find the return value.
94112
for (MachineBasicBlock::reverse_iterator I =
95-
next_nodbg(MBBI.getReverse(), RE);
96-
I != RE; I = next_nodbg(I, RE)) {
113+
nextNoDebugNoCFIInst(MBBI.getReverse(), RE);
114+
I != RE; I = nextNoDebugNoCFIInst(I, RE)) {
97115
MachineInstr &MI = *I;
98116
if (auto OperandPair = TII->isCopyInstrImpl(MI)) {
99117
Register DestReg = OperandPair->Destination->getReg();
@@ -138,7 +156,7 @@ bool RISCVPushPopOpt::runOnMachineFunction(MachineFunction &Fn) {
138156
bool Modified = false;
139157
for (auto &MBB : Fn) {
140158
MachineBasicBlock::iterator MBBI = containsPop(MBB);
141-
MachineBasicBlock::iterator NextI = next_nodbg(MBBI, MBB.end());
159+
MachineBasicBlock::iterator NextI = nextNoDebugNoCFIInst(MBBI, MBB.end());
142160
if (MBBI != MBB.end() && NextI != MBB.end() &&
143161
NextI->getOpcode() == RISCV::PseudoRET)
144162
Modified |= usePopRet(MBBI, NextI, adjustRetVal(MBBI));

0 commit comments

Comments
 (0)