Skip to content

Commit e47a6a2

Browse files
topperczmodem
authored andcommitted
[X86] Detect if EFLAGs is live across XBEGIN pseudo instruction. Add it as livein to the basic blocks created when expanding the pseudo
XBEGIN causes several based blocks to be inserted. If flags are live across it we need to make eflags live in the new basic blocks to avoid machine verifier errors. Fixes PR46827 Reviewed By: ivanbaev Differential Revision: https://reviews.llvm.org/D84479 (cherry picked from commit 647e861)
1 parent bf2c0fb commit e47a6a2

File tree

2 files changed

+75
-21
lines changed

2 files changed

+75
-21
lines changed

llvm/lib/Target/X86/X86ISelLowering.cpp

Lines changed: 36 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -30953,6 +30953,34 @@ bool X86TargetLowering::areJTsAllowed(const Function *Fn) const {
3095330953
// X86 Scheduler Hooks
3095430954
//===----------------------------------------------------------------------===//
3095530955

30956+
// Returns true if EFLAG is consumed after this iterator in the rest of the
30957+
// basic block or any successors of the basic block.
30958+
static bool isEFLAGSLiveAfter(MachineBasicBlock::iterator Itr,
30959+
MachineBasicBlock *BB) {
30960+
// Scan forward through BB for a use/def of EFLAGS.
30961+
for (MachineBasicBlock::iterator miI = std::next(Itr), miE = BB->end();
30962+
miI != miE; ++miI) {
30963+
const MachineInstr& mi = *miI;
30964+
if (mi.readsRegister(X86::EFLAGS))
30965+
return true;
30966+
// If we found a def, we can stop searching.
30967+
if (mi.definesRegister(X86::EFLAGS))
30968+
return false;
30969+
}
30970+
30971+
// If we hit the end of the block, check whether EFLAGS is live into a
30972+
// successor.
30973+
for (MachineBasicBlock::succ_iterator sItr = BB->succ_begin(),
30974+
sEnd = BB->succ_end();
30975+
sItr != sEnd; ++sItr) {
30976+
MachineBasicBlock* succ = *sItr;
30977+
if (succ->isLiveIn(X86::EFLAGS))
30978+
return true;
30979+
}
30980+
30981+
return false;
30982+
}
30983+
3095630984
/// Utility function to emit xbegin specifying the start of an RTM region.
3095730985
static MachineBasicBlock *emitXBegin(MachineInstr &MI, MachineBasicBlock *MBB,
3095830986
const TargetInstrInfo *TII) {
@@ -30985,6 +31013,12 @@ static MachineBasicBlock *emitXBegin(MachineInstr &MI, MachineBasicBlock *MBB,
3098531013
MF->insert(I, fallMBB);
3098631014
MF->insert(I, sinkMBB);
3098731015

31016+
if (isEFLAGSLiveAfter(MI, MBB)) {
31017+
mainMBB->addLiveIn(X86::EFLAGS);
31018+
fallMBB->addLiveIn(X86::EFLAGS);
31019+
sinkMBB->addLiveIn(X86::EFLAGS);
31020+
}
31021+
3098831022
// Transfer the remainder of BB and its successor edges to sinkMBB.
3098931023
sinkMBB->splice(sinkMBB->begin(), MBB,
3099031024
std::next(MachineBasicBlock::iterator(MI)), MBB->end());
@@ -31373,27 +31407,8 @@ MachineBasicBlock *X86TargetLowering::EmitVAStartSaveXMMRegsWithCustomInserter(
3137331407
static bool checkAndUpdateEFLAGSKill(MachineBasicBlock::iterator SelectItr,
3137431408
MachineBasicBlock* BB,
3137531409
const TargetRegisterInfo* TRI) {
31376-
// Scan forward through BB for a use/def of EFLAGS.
31377-
MachineBasicBlock::iterator miI(std::next(SelectItr));
31378-
for (MachineBasicBlock::iterator miE = BB->end(); miI != miE; ++miI) {
31379-
const MachineInstr& mi = *miI;
31380-
if (mi.readsRegister(X86::EFLAGS))
31381-
return false;
31382-
if (mi.definesRegister(X86::EFLAGS))
31383-
break; // Should have kill-flag - update below.
31384-
}
31385-
31386-
// If we hit the end of the block, check whether EFLAGS is live into a
31387-
// successor.
31388-
if (miI == BB->end()) {
31389-
for (MachineBasicBlock::succ_iterator sItr = BB->succ_begin(),
31390-
sEnd = BB->succ_end();
31391-
sItr != sEnd; ++sItr) {
31392-
MachineBasicBlock* succ = *sItr;
31393-
if (succ->isLiveIn(X86::EFLAGS))
31394-
return false;
31395-
}
31396-
}
31410+
if (isEFLAGSLiveAfter(SelectItr, BB))
31411+
return false;
3139731412

3139831413
// We found a def, or hit the end of the basic block and EFLAGS wasn't live
3139931414
// out. SelectMI should have a kill flag on EFLAGS.

llvm/test/CodeGen/X86/pr46827.ll

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
; RUN: llc < %s -mtriple=i686-pc-linux -mattr=+rtm -verify-machineinstrs -stop-after=finalize-isel | FileCheck %s
2+
3+
; CHECK: body: |
4+
; CHECK: bb.0.bb107:
5+
; CHECK: successors: %bb.3(0x40000000), %bb.4(0x40000000)
6+
; CHECK: %0:gr32 = MOV32rm %fixed-stack.0, 1, $noreg, 0, $noreg :: (load 4 from %fixed-stack.0, align 16)
7+
; CHECK: %1:gr32 = SUB32ri8 %0, 1, implicit-def $eflags
8+
; CHECK: XBEGIN_4 %bb.4, implicit-def $eax
9+
; CHECK: bb.3.bb107:
10+
; CHECK: successors: %bb.5(0x80000000)
11+
; CHECK: liveins: $eflags
12+
; CHECK: %3:gr32 = MOV32ri -1
13+
; CHECK: JMP_1 %bb.5
14+
; CHECK: bb.4.bb107:
15+
; CHECK: successors: %bb.5(0x80000000)
16+
; CHECK: liveins: $eflags
17+
; CHECK: XABORT_DEF implicit-def $eax
18+
; CHECK: %4:gr32 = COPY $eax
19+
; CHECK: bb.5.bb107:
20+
; CHECK: successors: %bb.1(0x40000000), %bb.2(0x40000000)
21+
; CHECK: liveins: $eflags
22+
; CHECK: %2:gr32 = PHI %3, %bb.3, %4, %bb.4
23+
; CHECK: JCC_1 %bb.2, 5, implicit $eflags
24+
; CHECK: JMP_1 %bb.1
25+
26+
declare i32 @llvm.x86.xbegin() #0
27+
28+
define void @wobble.12(i32 %tmp116) {
29+
bb107: ; preds = %bb42
30+
%tmp117 = icmp eq i32 %tmp116, 1
31+
%tmp127 = tail call i32 @llvm.x86.xbegin() #0
32+
br i1 %tmp117, label %bb129, label %bb250
33+
34+
bb129: ; preds = %bb107
35+
unreachable
36+
37+
bb250: ; preds = %bb107
38+
unreachable
39+
}

0 commit comments

Comments
 (0)