[mips] Fix compact branch hazard detection, part 2
Follow up to D27209 fix, this patch now properly handles single transient instruction in basic block. Patch by Aleksandar Beserminji. Differential Revision: https://reviews.llvm.org/D27856 llvm-svn: 290361
This commit is contained in:
@@ -103,24 +103,23 @@ static Iter getNextMachineInstrInBB(Iter Position) {
|
||||
|
||||
// Find the next real instruction from the current position, looking through
|
||||
// basic block boundaries.
|
||||
static Iter getNextMachineInstr(Iter Position) {
|
||||
if (std::next(Position) == Position->getParent()->end()) {
|
||||
const MachineBasicBlock * MBB = (&*Position)->getParent();
|
||||
for (auto *Succ : MBB->successors()) {
|
||||
if (MBB->isLayoutSuccessor(Succ)) {
|
||||
Iter I = Succ->begin();
|
||||
Iter Next = getNextMachineInstrInBB(I);
|
||||
if (Next == Succ->end()) {
|
||||
return getNextMachineInstr(I);
|
||||
} else {
|
||||
return I;
|
||||
}
|
||||
}
|
||||
static Iter getNextMachineInstr(Iter Position, MachineBasicBlock *Parent) {
|
||||
if (Position == Parent->end()) {
|
||||
MachineBasicBlock *Succ = Parent->getNextNode();
|
||||
if (Succ != nullptr && Parent->isSuccessor(Succ)) {
|
||||
Position = Succ->begin();
|
||||
Parent = Succ;
|
||||
} else {
|
||||
llvm_unreachable(
|
||||
"Should have identified the end of the function earlier!");
|
||||
}
|
||||
llvm_unreachable("Should have identified the end of the function earlier!");
|
||||
}
|
||||
|
||||
return getNextMachineInstrInBB(Position);
|
||||
Iter Instr = getNextMachineInstrInBB(Position);
|
||||
if (Instr == Parent->end()) {
|
||||
return getNextMachineInstr(Instr, Parent);
|
||||
}
|
||||
return Instr;
|
||||
}
|
||||
|
||||
bool MipsHazardSchedule::runOnMachineFunction(MachineFunction &MF) {
|
||||
@@ -146,13 +145,7 @@ bool MipsHazardSchedule::runOnMachineFunction(MachineFunction &MF) {
|
||||
bool LastInstInFunction =
|
||||
std::next(I) == FI->end() && std::next(FI) == MF.end();
|
||||
if (!LastInstInFunction) {
|
||||
if (std::next(I) != FI->end()) {
|
||||
// Start looking from the next instruction in the basic block.
|
||||
Inst = getNextMachineInstr(std::next(I));
|
||||
} else {
|
||||
// Next instruction in the physical successor basic block.
|
||||
Inst = getNextMachineInstr(I);
|
||||
}
|
||||
Inst = getNextMachineInstr(std::next(I), &*FI);
|
||||
}
|
||||
|
||||
if (LastInstInFunction || !TII->SafeInForbiddenSlot(*Inst)) {
|
||||
|
||||
@@ -0,0 +1,34 @@
|
||||
; RUN: llc -march=mips64el -O0 -mcpu=mips64r6 < %s | FileCheck %s
|
||||
; RUN: llc -march=mips64 -O0 -mcpu=mips64r6 < %s | FileCheck %s
|
||||
|
||||
@boo = global i32 0, align 4
|
||||
|
||||
; Function Attrs: nounwind
|
||||
define void @_Z3foov() #0 {
|
||||
entry:
|
||||
%0 = load volatile i32, i32* @boo, align 4
|
||||
switch i32 %0, label %sw.epilog [
|
||||
i32 0, label %sw.bb
|
||||
i32 1, label %sw.bb1
|
||||
i32 2, label %sw.bb1
|
||||
]
|
||||
|
||||
sw.bb: ; preds = %entry
|
||||
store volatile i32 1, i32* @boo, align 4
|
||||
br label %sw.epilog
|
||||
; CHECK: beqzc
|
||||
; CHECK-NEXT: nop
|
||||
; CHECK-NEXT: .LBB
|
||||
; CHECK-NEXT: j
|
||||
|
||||
sw.bb1: ; preds = %entry, %entry
|
||||
store volatile i32 2, i32* @boo, align 4
|
||||
br label %sw.epilog
|
||||
; CHECK: bnezc
|
||||
; CHECK-NEXT: nop
|
||||
; CHECK-NEXT: .LBB
|
||||
; CHECK-NEXT: j
|
||||
|
||||
sw.epilog: ; preds = %entry, %sw.bb1, %sw.bb
|
||||
ret void
|
||||
}
|
||||
Reference in New Issue
Block a user