Skip to content

Commit b2a2afe

Browse files
Use simple reverse traversal of basic blocks
1 parent 027a2a4 commit b2a2afe

File tree

1 file changed

+16
-13
lines changed

1 file changed

+16
-13
lines changed

llvm/lib/CodeGen/CFIFixup.cpp

Lines changed: 16 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -12,12 +12,14 @@
1212
// The pass relies in constraints LLVM imposes on the placement of
1313
// save/restore points (cf. ShrinkWrap) and has certain preconditions about
1414
// placement of CFI instructions:
15-
// * for any two CFI instructions of the function prologue one dominates
16-
// and is post-dominated by the other
17-
// * possibly multiple epilogue blocks, where each epilogue block is
18-
// complete and self-contained, i.e. CSR restore instructions (and the
19-
// corresponding CFI instructions are not split across two or more blocks.
20-
// * CFI instructions are not contained in any loops
15+
// * For any two CFI instructions of the function prologue one dominates
16+
// and is post-dominated by the other.
17+
// * The function possibly contains multiple epilogue blocks, where each
18+
// epilogue block is complete and self-contained, i.e. CSR restore
19+
// instructions (and the corresponding CFI instructions)
20+
// are not split across two or more blocks.
21+
// * CFI instructions are not contained in any loops.
22+
2123
// Thus, during execution, at the beginning and at the end of each basic block,
2224
// following the prologue, the function can be in one of two states:
2325
// - "has a call frame", if the function has executed the prologue, and
@@ -27,7 +29,7 @@
2729
// which can be computed by a single RPO traversal.
2830

2931
// The location of the prologue is determined by finding the first block in the
30-
// post-order traversal which contains CFI instructions.
32+
// reverse traversal which contains CFI instructions.
3133

3234
// In order to accommodate backends which do not generate unwind info in
3335
// epilogues we compute an additional property "strong no call frame on entry",
@@ -99,14 +101,16 @@ static bool containsEpilogue(const MachineBasicBlock &MBB) {
99101

100102
static MachineBasicBlock *
101103
findPrologueEnd(MachineFunction &MF, MachineBasicBlock::iterator &PrologueEnd) {
102-
for (auto It = po_begin(&MF.front()), End = po_end(&MF.front()); It != End;
103-
++It) {
104-
MachineBasicBlock *MBB = *It;
105-
for (MachineInstr &MI : reverse(MBB->instrs())) {
104+
// Even though we should theoretically traverse the blocks in post-order, we
105+
// can't encode correctly cases where prologue blocks are not laid out in
106+
// topological order. Then, assuming topological order, we can just traverse
107+
// the function in reverse.
108+
for (MachineBasicBlock &MBB : reverse(MF)) {
109+
for (MachineInstr &MI : reverse(MBB.instrs())) {
106110
if (!isPrologueCFIInstruction(MI))
107111
continue;
108112
PrologueEnd = std::next(MI.getIterator());
109-
return MBB;
113+
return &MBB;
110114
}
111115
}
112116
return nullptr;
@@ -123,7 +127,6 @@ bool CFIFixup::runOnMachineFunction(MachineFunction &MF) {
123127

124128
// Find the prologue and the point where we can issue the first
125129
// `.cfi_remember_state`.
126-
127130
MachineBasicBlock::iterator PrologueEnd;
128131
MachineBasicBlock *PrologueBlock = findPrologueEnd(MF, PrologueEnd);
129132
if (PrologueBlock == nullptr)

0 commit comments

Comments
 (0)