mirror of
https://github.com/RPCS3/llvm-mirror.git
synced 2024-11-23 03:02:36 +01:00
IfConversion: Use references instead of pointers where possible; NFC
Also put some commonly used subexpressions into variables. llvm-svn: 278895
This commit is contained in:
parent
03300c54a0
commit
9d6df3637c
@ -207,13 +207,13 @@ namespace {
|
||||
void ScanInstructions(BBInfo &BBI,
|
||||
MachineBasicBlock::iterator &Begin,
|
||||
MachineBasicBlock::iterator &End) const;
|
||||
void AnalyzeBlock(MachineBasicBlock *MBB,
|
||||
void AnalyzeBlock(MachineBasicBlock &MBB,
|
||||
std::vector<std::unique_ptr<IfcvtToken>> &Tokens);
|
||||
bool FeasibilityAnalysis(BBInfo &BBI, SmallVectorImpl<MachineOperand> &Cond,
|
||||
bool isTriangle = false, bool RevBranch = false);
|
||||
void AnalyzeBlocks(MachineFunction &MF,
|
||||
std::vector<std::unique_ptr<IfcvtToken>> &Tokens);
|
||||
void InvalidatePreds(MachineBasicBlock *BB);
|
||||
void InvalidatePreds(MachineBasicBlock &MBB);
|
||||
void RemoveExtraEdges(BBInfo &BBI);
|
||||
bool IfConvertSimple(BBInfo &BBI, IfcvtKind Kind);
|
||||
bool IfConvertTriangle(BBInfo &BBI, IfcvtKind Kind);
|
||||
@ -463,9 +463,9 @@ bool IfConverter::ReverseBranchCondition(BBInfo &BBI) const {
|
||||
|
||||
/// Returns the next block in the function blocks ordering. If it is the end,
|
||||
/// returns NULL.
|
||||
static inline MachineBasicBlock *getNextBlock(MachineBasicBlock *BB) {
|
||||
MachineFunction::iterator I = BB->getIterator();
|
||||
MachineFunction::iterator E = BB->getParent()->end();
|
||||
static inline MachineBasicBlock *getNextBlock(MachineBasicBlock &MBB) {
|
||||
MachineFunction::iterator I = MBB.getIterator();
|
||||
MachineFunction::iterator E = MBB.getParent()->end();
|
||||
if (++I == E)
|
||||
return nullptr;
|
||||
return &*I;
|
||||
@ -656,9 +656,9 @@ bool IfConverter::ValidDiamond(BBInfo &TrueBBI, BBInfo &FalseBBI,
|
||||
MachineBasicBlock *FT = FalseBBI.TrueBB;
|
||||
|
||||
if (!TT && blockAlwaysFallThrough(TrueBBI))
|
||||
TT = getNextBlock(TrueBBI.BB);
|
||||
TT = getNextBlock(*TrueBBI.BB);
|
||||
if (!FT && blockAlwaysFallThrough(FalseBBI))
|
||||
FT = getNextBlock(FalseBBI.BB);
|
||||
FT = getNextBlock(*FalseBBI.BB);
|
||||
if (TT != FT)
|
||||
return false;
|
||||
if (!TT && (TrueBBI.IsBrAnalyzable || FalseBBI.IsBrAnalyzable))
|
||||
@ -847,9 +847,9 @@ bool IfConverter::FeasibilityAnalysis(BBInfo &BBI,
|
||||
/// Analyze the structure of the sub-CFG starting from the specified block.
|
||||
/// Record its successors and whether it looks like an if-conversion candidate.
|
||||
void IfConverter::AnalyzeBlock(
|
||||
MachineBasicBlock *MBB, std::vector<std::unique_ptr<IfcvtToken>> &Tokens) {
|
||||
MachineBasicBlock &MBB, std::vector<std::unique_ptr<IfcvtToken>> &Tokens) {
|
||||
struct BBState {
|
||||
BBState(MachineBasicBlock *BB) : MBB(BB), SuccsAnalyzed(false) {}
|
||||
BBState(MachineBasicBlock &MBB) : MBB(&MBB), SuccsAnalyzed(false) {}
|
||||
MachineBasicBlock *MBB;
|
||||
|
||||
/// This flag is true if MBB's successors have been analyzed.
|
||||
@ -905,8 +905,8 @@ void IfConverter::AnalyzeBlock(
|
||||
|
||||
// Push the False and True blocks to the stack.
|
||||
State.SuccsAnalyzed = true;
|
||||
BBStack.push_back(BBI.FalseBB);
|
||||
BBStack.push_back(BBI.TrueBB);
|
||||
BBStack.push_back(*BBI.FalseBB);
|
||||
BBStack.push_back(*BBI.TrueBB);
|
||||
continue;
|
||||
}
|
||||
|
||||
@ -1040,7 +1040,7 @@ void IfConverter::AnalyzeBlock(
|
||||
void IfConverter::AnalyzeBlocks(
|
||||
MachineFunction &MF, std::vector<std::unique_ptr<IfcvtToken>> &Tokens) {
|
||||
for (MachineBasicBlock &MBB : MF)
|
||||
AnalyzeBlock(&MBB, Tokens);
|
||||
AnalyzeBlock(MBB, Tokens);
|
||||
|
||||
// Sort to favor more complex ifcvt scheme.
|
||||
std::stable_sort(Tokens.begin(), Tokens.end(), IfcvtTokenCmp);
|
||||
@ -1048,11 +1048,11 @@ void IfConverter::AnalyzeBlocks(
|
||||
|
||||
/// Returns true either if ToMBB is the next block after MBB or that all the
|
||||
/// intervening blocks are empty (given MBB can fall through to its next block).
|
||||
static bool canFallThroughTo(MachineBasicBlock *BB, MachineBasicBlock *ToBB) {
|
||||
MachineFunction::iterator PI = BB->getIterator();
|
||||
static bool canFallThroughTo(MachineBasicBlock &MBB, MachineBasicBlock &ToMBB) {
|
||||
MachineFunction::iterator PI = MBB.getIterator();
|
||||
MachineFunction::iterator I = std::next(PI);
|
||||
MachineFunction::iterator TI = ToBB->getIterator();
|
||||
MachineFunction::iterator E = BB->getParent()->end();
|
||||
MachineFunction::iterator TI = ToMBB.getIterator();
|
||||
MachineFunction::iterator E = MBB.getParent()->end();
|
||||
while (I != TI) {
|
||||
// Check isSuccessor to avoid case where the next block is empty, but
|
||||
// it's not a successor.
|
||||
@ -1065,10 +1065,10 @@ static bool canFallThroughTo(MachineBasicBlock *BB, MachineBasicBlock *ToBB) {
|
||||
|
||||
/// Invalidate predecessor BB info so it would be re-analyzed to determine if it
|
||||
/// can be if-converted. If predecessor is already enqueued, dequeue it!
|
||||
void IfConverter::InvalidatePreds(MachineBasicBlock *BB) {
|
||||
for (const MachineBasicBlock *Predecessor : BB->predecessors()) {
|
||||
void IfConverter::InvalidatePreds(MachineBasicBlock &MBB) {
|
||||
for (const MachineBasicBlock *Predecessor : MBB.predecessors()) {
|
||||
BBInfo &PBBI = BBAnalysis[Predecessor->getNumber()];
|
||||
if (PBBI.IsDone || PBBI.BB == BB)
|
||||
if (PBBI.IsDone || PBBI.BB == &MBB)
|
||||
continue;
|
||||
PBBI.IsAnalyzed = false;
|
||||
PBBI.IsEnqueued = false;
|
||||
@ -1076,11 +1076,11 @@ void IfConverter::InvalidatePreds(MachineBasicBlock *BB) {
|
||||
}
|
||||
|
||||
/// Inserts an unconditional branch from \p MBB to \p ToMBB.
|
||||
static void InsertUncondBranch(MachineBasicBlock *BB, MachineBasicBlock *ToBB,
|
||||
static void InsertUncondBranch(MachineBasicBlock &MBB, MachineBasicBlock &ToMBB,
|
||||
const TargetInstrInfo *TII) {
|
||||
DebugLoc dl; // FIXME: this is nowhere
|
||||
SmallVector<MachineOperand, 0> NoCond;
|
||||
TII->InsertBranch(*BB, ToBB, nullptr, NoCond, dl);
|
||||
TII->InsertBranch(MBB, &ToMBB, nullptr, NoCond, dl);
|
||||
}
|
||||
|
||||
/// Remove true / false edges if either / both are no longer successors.
|
||||
@ -1109,24 +1109,25 @@ static void UpdatePredRedefs(MachineInstr &MI, LivePhysRegs &Redefs) {
|
||||
Redefs.stepForward(MI, Clobbers);
|
||||
|
||||
// Now add the implicit uses for each of the clobbered values.
|
||||
for (auto Reg : Clobbers) {
|
||||
for (auto Clobber : Clobbers) {
|
||||
// FIXME: Const cast here is nasty, but better than making StepForward
|
||||
// take a mutable instruction instead of const.
|
||||
MachineOperand &Op = const_cast<MachineOperand&>(*Reg.second);
|
||||
unsigned Reg = Clobber.first;
|
||||
MachineOperand &Op = const_cast<MachineOperand&>(*Clobber.second);
|
||||
MachineInstr *OpMI = Op.getParent();
|
||||
MachineInstrBuilder MIB(*OpMI->getParent()->getParent(), OpMI);
|
||||
if (Op.isRegMask()) {
|
||||
// First handle regmasks. They clobber any entries in the mask which
|
||||
// means that we need a def for those registers.
|
||||
if (LiveBeforeMI.count(Reg.first))
|
||||
MIB.addReg(Reg.first, RegState::Implicit);
|
||||
if (LiveBeforeMI.count(Reg))
|
||||
MIB.addReg(Reg, RegState::Implicit);
|
||||
|
||||
// We also need to add an implicit def of this register for the later
|
||||
// use to read from.
|
||||
// For the register allocator to have allocated a register clobbered
|
||||
// by the call which is used later, it must be the case that
|
||||
// the call doesn't return.
|
||||
MIB.addReg(Reg.first, RegState::Implicit | RegState::Define);
|
||||
MIB.addReg(Reg, RegState::Implicit | RegState::Define);
|
||||
continue;
|
||||
}
|
||||
assert(Op.isReg() && "Register operand required");
|
||||
@ -1136,8 +1137,8 @@ static void UpdatePredRedefs(MachineInstr &MI, LivePhysRegs &Redefs) {
|
||||
if (Redefs.contains(Op.getReg()))
|
||||
Op.setIsDead(false);
|
||||
}
|
||||
if (LiveBeforeMI.count(Reg.first))
|
||||
MIB.addReg(Reg.first, RegState::Implicit);
|
||||
if (LiveBeforeMI.count(Reg))
|
||||
MIB.addReg(Reg, RegState::Implicit);
|
||||
}
|
||||
}
|
||||
|
||||
@ -1172,15 +1173,17 @@ bool IfConverter::IfConvertSimple(BBInfo &BBI, IfcvtKind Kind) {
|
||||
if (Kind == ICSimpleFalse)
|
||||
std::swap(CvtBBI, NextBBI);
|
||||
|
||||
MachineBasicBlock &CvtMBB = *CvtBBI->BB;
|
||||
MachineBasicBlock &NextMBB = *NextBBI->BB;
|
||||
if (CvtBBI->IsDone ||
|
||||
(CvtBBI->CannotBeCopied && CvtBBI->BB->pred_size() > 1)) {
|
||||
(CvtBBI->CannotBeCopied && CvtMBB.pred_size() > 1)) {
|
||||
// Something has changed. It's no longer safe to predicate this block.
|
||||
BBI.IsAnalyzed = false;
|
||||
CvtBBI->IsAnalyzed = false;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (CvtBBI->BB->hasAddressTaken())
|
||||
if (CvtMBB.hasAddressTaken())
|
||||
// Conservatively abort if-conversion if BB's address is taken.
|
||||
return false;
|
||||
|
||||
@ -1191,15 +1194,15 @@ bool IfConverter::IfConvertSimple(BBInfo &BBI, IfcvtKind Kind) {
|
||||
// Initialize liveins to the first BB. These are potentiall redefined by
|
||||
// predicated instructions.
|
||||
Redefs.init(TRI);
|
||||
Redefs.addLiveIns(*CvtBBI->BB);
|
||||
Redefs.addLiveIns(*NextBBI->BB);
|
||||
Redefs.addLiveIns(CvtMBB);
|
||||
Redefs.addLiveIns(NextMBB);
|
||||
|
||||
// Compute a set of registers which must not be killed by instructions in
|
||||
// BB1: This is everything live-in to BB2.
|
||||
DontKill.init(TRI);
|
||||
DontKill.addLiveIns(*NextBBI->BB);
|
||||
DontKill.addLiveIns(NextMBB);
|
||||
|
||||
if (CvtBBI->BB->pred_size() > 1) {
|
||||
if (CvtMBB.pred_size() > 1) {
|
||||
BBI.NonPredSize -= TII->RemoveBranch(*BBI.BB);
|
||||
// Copy instructions in the true block, predicate them, and add them to
|
||||
// the entry block.
|
||||
@ -1207,10 +1210,10 @@ bool IfConverter::IfConvertSimple(BBInfo &BBI, IfcvtKind Kind) {
|
||||
|
||||
// RemoveExtraEdges won't work if the block has an unanalyzable branch, so
|
||||
// explicitly remove CvtBBI as a successor.
|
||||
BBI.BB->removeSuccessor(CvtBBI->BB, true);
|
||||
BBI.BB->removeSuccessor(&CvtMBB, true);
|
||||
} else {
|
||||
RemoveKills(CvtBBI->BB->begin(), CvtBBI->BB->end(), DontKill, *TRI);
|
||||
PredicateBlock(*CvtBBI, CvtBBI->BB->end(), Cond);
|
||||
RemoveKills(CvtMBB.begin(), CvtMBB.end(), DontKill, *TRI);
|
||||
PredicateBlock(*CvtBBI, CvtMBB.end(), Cond);
|
||||
|
||||
// Merge converted block into entry block.
|
||||
BBI.NonPredSize -= TII->RemoveBranch(*BBI.BB);
|
||||
@ -1218,8 +1221,8 @@ bool IfConverter::IfConvertSimple(BBInfo &BBI, IfcvtKind Kind) {
|
||||
}
|
||||
|
||||
bool IterIfcvt = true;
|
||||
if (!canFallThroughTo(BBI.BB, NextBBI->BB)) {
|
||||
InsertUncondBranch(BBI.BB, NextBBI->BB, TII);
|
||||
if (!canFallThroughTo(*BBI.BB, NextMBB)) {
|
||||
InsertUncondBranch(*BBI.BB, NextMBB, TII);
|
||||
BBI.HasFallThrough = false;
|
||||
// Now ifcvt'd block will look like this:
|
||||
// BB:
|
||||
@ -1239,7 +1242,7 @@ bool IfConverter::IfConvertSimple(BBInfo &BBI, IfcvtKind Kind) {
|
||||
// Update block info. BB can be iteratively if-converted.
|
||||
if (!IterIfcvt)
|
||||
BBI.IsDone = true;
|
||||
InvalidatePreds(BBI.BB);
|
||||
InvalidatePreds(*BBI.BB);
|
||||
CvtBBI->IsDone = true;
|
||||
|
||||
// FIXME: Must maintain LiveIns.
|
||||
@ -1258,15 +1261,17 @@ bool IfConverter::IfConvertTriangle(BBInfo &BBI, IfcvtKind Kind) {
|
||||
if (Kind == ICTriangleFalse || Kind == ICTriangleFRev)
|
||||
std::swap(CvtBBI, NextBBI);
|
||||
|
||||
MachineBasicBlock &CvtMBB = *CvtBBI->BB;
|
||||
MachineBasicBlock &NextMBB = *NextBBI->BB;
|
||||
if (CvtBBI->IsDone ||
|
||||
(CvtBBI->CannotBeCopied && CvtBBI->BB->pred_size() > 1)) {
|
||||
(CvtBBI->CannotBeCopied && CvtMBB.pred_size() > 1)) {
|
||||
// Something has changed. It's no longer safe to predicate this block.
|
||||
BBI.IsAnalyzed = false;
|
||||
CvtBBI->IsAnalyzed = false;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (CvtBBI->BB->hasAddressTaken())
|
||||
if (CvtMBB.hasAddressTaken())
|
||||
// Conservatively abort if-conversion if BB's address is taken.
|
||||
return false;
|
||||
|
||||
@ -1278,7 +1283,7 @@ bool IfConverter::IfConvertTriangle(BBInfo &BBI, IfcvtKind Kind) {
|
||||
if (ReverseBranchCondition(*CvtBBI)) {
|
||||
// BB has been changed, modify its predecessors (except for this
|
||||
// one) so they don't get ifcvt'ed based on bad intel.
|
||||
for (MachineBasicBlock *PBB : CvtBBI->BB->predecessors()) {
|
||||
for (MachineBasicBlock *PBB : CvtMBB.predecessors()) {
|
||||
if (PBB == BBI.BB)
|
||||
continue;
|
||||
BBInfo &PBBI = BBAnalysis[PBB->getNumber()];
|
||||
@ -1293,8 +1298,8 @@ bool IfConverter::IfConvertTriangle(BBInfo &BBI, IfcvtKind Kind) {
|
||||
// Initialize liveins to the first BB. These are potentially redefined by
|
||||
// predicated instructions.
|
||||
Redefs.init(TRI);
|
||||
Redefs.addLiveIns(*CvtBBI->BB);
|
||||
Redefs.addLiveIns(*NextBBI->BB);
|
||||
Redefs.addLiveIns(CvtMBB);
|
||||
Redefs.addLiveIns(NextMBB);
|
||||
|
||||
DontKill.clear();
|
||||
|
||||
@ -1302,14 +1307,14 @@ bool IfConverter::IfConvertTriangle(BBInfo &BBI, IfcvtKind Kind) {
|
||||
BranchProbability CvtNext, CvtFalse, BBNext, BBCvt;
|
||||
|
||||
if (HasEarlyExit) {
|
||||
// Get probabilities before modifying CvtBBI->BB and BBI.BB.
|
||||
CvtNext = MBPI->getEdgeProbability(CvtBBI->BB, NextBBI->BB);
|
||||
CvtFalse = MBPI->getEdgeProbability(CvtBBI->BB, CvtBBI->FalseBB);
|
||||
BBNext = MBPI->getEdgeProbability(BBI.BB, NextBBI->BB);
|
||||
BBCvt = MBPI->getEdgeProbability(BBI.BB, CvtBBI->BB);
|
||||
// Get probabilities before modifying CvtMBB and BBI.BB.
|
||||
CvtNext = MBPI->getEdgeProbability(&CvtMBB, &NextMBB);
|
||||
CvtFalse = MBPI->getEdgeProbability(&CvtMBB, CvtBBI->FalseBB);
|
||||
BBNext = MBPI->getEdgeProbability(BBI.BB, &NextMBB);
|
||||
BBCvt = MBPI->getEdgeProbability(BBI.BB, &CvtMBB);
|
||||
}
|
||||
|
||||
if (CvtBBI->BB->pred_size() > 1) {
|
||||
if (CvtMBB.pred_size() > 1) {
|
||||
BBI.NonPredSize -= TII->RemoveBranch(*BBI.BB);
|
||||
// Copy instructions in the true block, predicate them, and add them to
|
||||
// the entry block.
|
||||
@ -1317,11 +1322,11 @@ bool IfConverter::IfConvertTriangle(BBInfo &BBI, IfcvtKind Kind) {
|
||||
|
||||
// RemoveExtraEdges won't work if the block has an unanalyzable branch, so
|
||||
// explicitly remove CvtBBI as a successor.
|
||||
BBI.BB->removeSuccessor(CvtBBI->BB, true);
|
||||
BBI.BB->removeSuccessor(&CvtMBB, true);
|
||||
} else {
|
||||
// Predicate the 'true' block after removing its branch.
|
||||
CvtBBI->NonPredSize -= TII->RemoveBranch(*CvtBBI->BB);
|
||||
PredicateBlock(*CvtBBI, CvtBBI->BB->end(), Cond);
|
||||
CvtBBI->NonPredSize -= TII->RemoveBranch(CvtMBB);
|
||||
PredicateBlock(*CvtBBI, CvtMBB.end(), Cond);
|
||||
|
||||
// Now merge the entry of the triangle with the true block.
|
||||
BBI.NonPredSize -= TII->RemoveBranch(*BBI.BB);
|
||||
@ -1336,12 +1341,12 @@ bool IfConverter::IfConvertTriangle(BBInfo &BBI, IfcvtKind Kind) {
|
||||
llvm_unreachable("Unable to reverse branch condition!");
|
||||
|
||||
// Update the edge probability for both CvtBBI->FalseBB and NextBBI.
|
||||
// NewNext = New_Prob(BBI.BB, NextBBI->BB) =
|
||||
// Prob(BBI.BB, NextBBI->BB) +
|
||||
// Prob(BBI.BB, CvtBBI->BB) * Prob(CvtBBI->BB, NextBBI->BB)
|
||||
// NewNext = New_Prob(BBI.BB, NextMBB) =
|
||||
// Prob(BBI.BB, NextMBB) +
|
||||
// Prob(BBI.BB, CvtMBB) * Prob(CvtMBB, NextMBB)
|
||||
// NewFalse = New_Prob(BBI.BB, CvtBBI->FalseBB) =
|
||||
// Prob(BBI.BB, CvtBBI->BB) * Prob(CvtBBI->BB, CvtBBI->FalseBB)
|
||||
auto NewTrueBB = getNextBlock(BBI.BB);
|
||||
// Prob(BBI.BB, CvtMBB) * Prob(CvtMBB, CvtBBI->FalseBB)
|
||||
auto NewTrueBB = getNextBlock(*BBI.BB);
|
||||
auto NewNext = BBNext + BBCvt * CvtNext;
|
||||
auto NewTrueBBIter = find(BBI.BB->successors(), NewTrueBB);
|
||||
if (NewTrueBBIter != BBI.BB->succ_end())
|
||||
@ -1356,18 +1361,18 @@ bool IfConverter::IfConvertTriangle(BBInfo &BBI, IfcvtKind Kind) {
|
||||
// predecessors. Otherwise, add an unconditional branch to 'false'.
|
||||
bool FalseBBDead = false;
|
||||
bool IterIfcvt = true;
|
||||
bool isFallThrough = canFallThroughTo(BBI.BB, NextBBI->BB);
|
||||
bool isFallThrough = canFallThroughTo(*BBI.BB, NextMBB);
|
||||
if (!isFallThrough) {
|
||||
// Only merge them if the true block does not fallthrough to the false
|
||||
// block. By not merging them, we make it possible to iteratively
|
||||
// ifcvt the blocks.
|
||||
if (!HasEarlyExit &&
|
||||
NextBBI->BB->pred_size() == 1 && !NextBBI->HasFallThrough &&
|
||||
!NextBBI->BB->hasAddressTaken()) {
|
||||
NextMBB.pred_size() == 1 && !NextBBI->HasFallThrough &&
|
||||
!NextMBB.hasAddressTaken()) {
|
||||
MergeBlocks(BBI, *NextBBI);
|
||||
FalseBBDead = true;
|
||||
} else {
|
||||
InsertUncondBranch(BBI.BB, NextBBI->BB, TII);
|
||||
InsertUncondBranch(*BBI.BB, NextMBB, TII);
|
||||
BBI.HasFallThrough = false;
|
||||
}
|
||||
// Mixed predicated and unpredicated code. This cannot be iteratively
|
||||
@ -1380,7 +1385,7 @@ bool IfConverter::IfConvertTriangle(BBInfo &BBI, IfcvtKind Kind) {
|
||||
// Update block info. BB can be iteratively if-converted.
|
||||
if (!IterIfcvt)
|
||||
BBI.IsDone = true;
|
||||
InvalidatePreds(BBI.BB);
|
||||
InvalidatePreds(*BBI.BB);
|
||||
CvtBBI->IsDone = true;
|
||||
if (FalseBBDead)
|
||||
NextBBI->IsDone = true;
|
||||
@ -1443,6 +1448,9 @@ bool IfConverter::IfConvertDiamond(BBInfo &BBI, IfcvtKind Kind,
|
||||
// Remove the conditional branch from entry to the blocks.
|
||||
BBI.NonPredSize -= TII->RemoveBranch(*BBI.BB);
|
||||
|
||||
MachineBasicBlock &MBB1 = *BBI1->BB;
|
||||
MachineBasicBlock &MBB2 = *BBI2->BB;
|
||||
|
||||
// Initialize the Redefs:
|
||||
// - BB2 live-in regs need implicit uses before being redefined by BB1
|
||||
// instructions.
|
||||
@ -1450,13 +1458,13 @@ bool IfConverter::IfConvertDiamond(BBInfo &BBI, IfcvtKind Kind,
|
||||
// instructions. We start with BB1 live-ins so we have the live-out regs
|
||||
// after tracking the BB1 instructions.
|
||||
Redefs.init(TRI);
|
||||
Redefs.addLiveIns(*BBI1->BB);
|
||||
Redefs.addLiveIns(*BBI2->BB);
|
||||
Redefs.addLiveIns(MBB1);
|
||||
Redefs.addLiveIns(MBB2);
|
||||
|
||||
// Remove the duplicated instructions at the beginnings of both paths.
|
||||
// Skip dbg_value instructions
|
||||
MachineBasicBlock::iterator DI1 = BBI1->BB->getFirstNonDebugInstr();
|
||||
MachineBasicBlock::iterator DI2 = BBI2->BB->getFirstNonDebugInstr();
|
||||
MachineBasicBlock::iterator DI1 = MBB1.getFirstNonDebugInstr();
|
||||
MachineBasicBlock::iterator DI2 = MBB2.getFirstNonDebugInstr();
|
||||
BBI1->NonPredSize -= NumDups1;
|
||||
BBI2->NonPredSize -= NumDups1;
|
||||
|
||||
@ -1476,49 +1484,49 @@ bool IfConverter::IfConvertDiamond(BBInfo &BBI, IfcvtKind Kind,
|
||||
// This is everything used+live in BB2 after the duplicated instructions. We
|
||||
// can compute this set by simulating liveness backwards from the end of BB2.
|
||||
DontKill.init(TRI);
|
||||
for (const MachineInstr &MI : make_range(BBI2->BB->rbegin(),
|
||||
MachineBasicBlock::reverse_iterator(DI2)))
|
||||
for (const MachineInstr &MI :
|
||||
make_range(MBB2.rbegin(), MachineBasicBlock::reverse_iterator(DI2)))
|
||||
DontKill.stepBackward(MI);
|
||||
|
||||
for (const MachineInstr &MI : make_range(BBI1->BB->begin(), DI1)) {
|
||||
for (const MachineInstr &MI : make_range(MBB1.begin(), DI1)) {
|
||||
SmallVector<std::pair<unsigned, const MachineOperand*>, 4> IgnoredClobbers;
|
||||
Redefs.stepForward(MI, IgnoredClobbers);
|
||||
}
|
||||
BBI.BB->splice(BBI.BB->end(), BBI1->BB, BBI1->BB->begin(), DI1);
|
||||
BBI2->BB->erase(BBI2->BB->begin(), DI2);
|
||||
BBI.BB->splice(BBI.BB->end(), &MBB1, MBB1.begin(), DI1);
|
||||
MBB2.erase(MBB2.begin(), DI2);
|
||||
|
||||
// Remove branch from the 'true' block, unless it was not analyzable.
|
||||
// Non-analyzable branches need to be preserved, since in such cases,
|
||||
// the CFG structure is not an actual diamond (the join block may not
|
||||
// be present).
|
||||
if (BBI1->IsBrAnalyzable)
|
||||
BBI1->NonPredSize -= TII->RemoveBranch(*BBI1->BB);
|
||||
BBI1->NonPredSize -= TII->RemoveBranch(MBB1);
|
||||
// Remove duplicated instructions.
|
||||
DI1 = BBI1->BB->end();
|
||||
DI1 = MBB1.end();
|
||||
for (unsigned i = 0; i != NumDups2; ) {
|
||||
// NumDups2 only counted non-dbg_value instructions, so this won't
|
||||
// run off the head of the list.
|
||||
assert (DI1 != BBI1->BB->begin());
|
||||
assert(DI1 != MBB1.begin());
|
||||
--DI1;
|
||||
// skip dbg_value instructions
|
||||
if (!DI1->isDebugValue())
|
||||
++i;
|
||||
}
|
||||
BBI1->BB->erase(DI1, BBI1->BB->end());
|
||||
MBB1.erase(DI1, MBB1.end());
|
||||
|
||||
// Kill flags in the true block for registers living into the false block
|
||||
// must be removed.
|
||||
RemoveKills(BBI1->BB->begin(), BBI1->BB->end(), DontKill, *TRI);
|
||||
RemoveKills(MBB1.begin(), MBB1.end(), DontKill, *TRI);
|
||||
|
||||
// Remove 'false' block branch (unless it was not analyzable), and find
|
||||
// the last instruction to predicate.
|
||||
if (BBI2->IsBrAnalyzable)
|
||||
BBI2->NonPredSize -= TII->RemoveBranch(*BBI2->BB);
|
||||
DI2 = BBI2->BB->end();
|
||||
BBI2->NonPredSize -= TII->RemoveBranch(MBB2);
|
||||
DI2 = MBB2.end();
|
||||
while (NumDups2 != 0) {
|
||||
// NumDups2 only counted non-dbg_value instructions, so this won't
|
||||
// run off the head of the list.
|
||||
assert (DI2 != BBI2->BB->begin());
|
||||
assert(DI2 != MBB2.begin());
|
||||
--DI2;
|
||||
// skip dbg_value instructions
|
||||
if (!DI2->isDebugValue())
|
||||
@ -1535,8 +1543,8 @@ bool IfConverter::IfConvertDiamond(BBInfo &BBI, IfcvtKind Kind,
|
||||
// addne r0, r1, #1
|
||||
SmallSet<unsigned, 4> RedefsByFalse;
|
||||
SmallSet<unsigned, 4> ExtUses;
|
||||
if (TII->isProfitableToUnpredicate(*BBI1->BB, *BBI2->BB)) {
|
||||
for (const MachineInstr &FI : make_range(BBI2->BB->begin(), DI2)) {
|
||||
if (TII->isProfitableToUnpredicate(MBB1, MBB2)) {
|
||||
for (const MachineInstr &FI : make_range(MBB2.begin(), DI2)) {
|
||||
if (FI.isDebugValue())
|
||||
continue;
|
||||
SmallVector<unsigned, 4> Defs;
|
||||
@ -1568,17 +1576,17 @@ bool IfConverter::IfConvertDiamond(BBInfo &BBI, IfcvtKind Kind,
|
||||
}
|
||||
|
||||
// Predicate the 'true' block.
|
||||
PredicateBlock(*BBI1, BBI1->BB->end(), *Cond1, &RedefsByFalse);
|
||||
PredicateBlock(*BBI1, MBB1.end(), *Cond1, &RedefsByFalse);
|
||||
|
||||
// After predicating BBI1, if there is a predicated terminator in BBI1 and
|
||||
// a non-predicated in BBI2, then we don't want to predicate the one from
|
||||
// BBI2. The reason is that if we merged these blocks, we would end up with
|
||||
// two predicated terminators in the same block.
|
||||
if (!BBI2->BB->empty() && (DI2 == BBI2->BB->end())) {
|
||||
MachineBasicBlock::iterator BBI1T = BBI1->BB->getFirstTerminator();
|
||||
MachineBasicBlock::iterator BBI2T = BBI2->BB->getFirstTerminator();
|
||||
if (BBI1T != BBI1->BB->end() && TII->isPredicated(*BBI1T) &&
|
||||
BBI2T != BBI2->BB->end() && !TII->isPredicated(*BBI2T))
|
||||
if (!MBB2.empty() && (DI2 == MBB2.end())) {
|
||||
MachineBasicBlock::iterator BBI1T = MBB1.getFirstTerminator();
|
||||
MachineBasicBlock::iterator BBI2T = MBB2.getFirstTerminator();
|
||||
if (BBI1T != MBB1.end() && TII->isPredicated(*BBI1T) &&
|
||||
BBI2T != MBB2.end() && !TII->isPredicated(*BBI2T))
|
||||
--DI2;
|
||||
}
|
||||
|
||||
@ -1610,7 +1618,7 @@ bool IfConverter::IfConvertDiamond(BBInfo &BBI, IfcvtKind Kind,
|
||||
CanMergeTail = false;
|
||||
else if (NumPreds == 1 && CanMergeTail) {
|
||||
MachineBasicBlock::pred_iterator PI = TailBB->pred_begin();
|
||||
if (*PI != BBI1->BB && *PI != BBI2->BB)
|
||||
if (*PI != &MBB1 && *PI != &MBB2)
|
||||
CanMergeTail = false;
|
||||
}
|
||||
if (CanMergeTail) {
|
||||
@ -1618,7 +1626,7 @@ bool IfConverter::IfConvertDiamond(BBInfo &BBI, IfcvtKind Kind,
|
||||
TailBBI.IsDone = true;
|
||||
} else {
|
||||
BBI.BB->addSuccessor(TailBB, BranchProbability::getOne());
|
||||
InsertUncondBranch(BBI.BB, TailBB, TII);
|
||||
InsertUncondBranch(*BBI.BB, *TailBB, TII);
|
||||
BBI.HasFallThrough = false;
|
||||
}
|
||||
}
|
||||
@ -1626,13 +1634,13 @@ bool IfConverter::IfConvertDiamond(BBInfo &BBI, IfcvtKind Kind,
|
||||
// RemoveExtraEdges won't work if the block has an unanalyzable branch,
|
||||
// which can happen here if TailBB is unanalyzable and is merged, so
|
||||
// explicitly remove BBI1 and BBI2 as successors.
|
||||
BBI.BB->removeSuccessor(BBI1->BB);
|
||||
BBI.BB->removeSuccessor(BBI2->BB, true);
|
||||
BBI.BB->removeSuccessor(&MBB1);
|
||||
BBI.BB->removeSuccessor(&MBB2, true);
|
||||
RemoveExtraEdges(BBI);
|
||||
|
||||
// Update block info.
|
||||
BBI.IsDone = TrueBBI.IsDone = FalseBBI.IsDone = true;
|
||||
InvalidatePreds(BBI.BB);
|
||||
InvalidatePreds(*BBI.BB);
|
||||
|
||||
// FIXME: Must maintain LiveIns.
|
||||
return true;
|
||||
@ -1707,7 +1715,8 @@ void IfConverter::CopyAndPredicateBlock(BBInfo &ToBBI, BBInfo &FromBBI,
|
||||
bool IgnoreBr) {
|
||||
MachineFunction &MF = *ToBBI.BB->getParent();
|
||||
|
||||
for (MachineInstr &I : *FromBBI.BB) {
|
||||
MachineBasicBlock &FromMBB = *FromBBI.BB;
|
||||
for (MachineInstr &I : FromMBB) {
|
||||
// Do not copy the end of the block branches.
|
||||
if (IgnoreBr && I.isBranch())
|
||||
break;
|
||||
@ -1740,9 +1749,9 @@ void IfConverter::CopyAndPredicateBlock(BBInfo &ToBBI, BBInfo &FromBBI,
|
||||
}
|
||||
|
||||
if (!IgnoreBr) {
|
||||
std::vector<MachineBasicBlock *> Succs(FromBBI.BB->succ_begin(),
|
||||
FromBBI.BB->succ_end());
|
||||
MachineBasicBlock *NBB = getNextBlock(FromBBI.BB);
|
||||
std::vector<MachineBasicBlock *> Succs(FromMBB.succ_begin(),
|
||||
FromMBB.succ_end());
|
||||
MachineBasicBlock *NBB = getNextBlock(FromMBB);
|
||||
MachineBasicBlock *FallThrough = FromBBI.HasFallThrough ? NBB : nullptr;
|
||||
|
||||
for (MachineBasicBlock *Succ : Succs) {
|
||||
@ -1767,19 +1776,20 @@ void IfConverter::CopyAndPredicateBlock(BBInfo &ToBBI, BBInfo &FromBBI,
|
||||
/// the fall-through edge. If AddEdges is true, i.e., when FromBBI's branch is
|
||||
/// being moved, add those successor edges to ToBBI.
|
||||
void IfConverter::MergeBlocks(BBInfo &ToBBI, BBInfo &FromBBI, bool AddEdges) {
|
||||
assert(!FromBBI.BB->hasAddressTaken() &&
|
||||
MachineBasicBlock &FromMBB = *FromBBI.BB;
|
||||
assert(!FromMBB.hasAddressTaken() &&
|
||||
"Removing a BB whose address is taken!");
|
||||
|
||||
// In case FromBBI.BB contains terminators (e.g. return instruction),
|
||||
// In case FromMBB contains terminators (e.g. return instruction),
|
||||
// first move the non-terminator instructions, then the terminators.
|
||||
MachineBasicBlock::iterator FromTI = FromBBI.BB->getFirstTerminator();
|
||||
MachineBasicBlock::iterator FromTI = FromMBB.getFirstTerminator();
|
||||
MachineBasicBlock::iterator ToTI = ToBBI.BB->getFirstTerminator();
|
||||
ToBBI.BB->splice(ToTI, FromBBI.BB, FromBBI.BB->begin(), FromTI);
|
||||
ToBBI.BB->splice(ToTI, &FromMBB, FromMBB.begin(), FromTI);
|
||||
|
||||
// If FromBB has non-predicated terminator we should copy it at the end.
|
||||
if (FromTI != FromBBI.BB->end() && !TII->isPredicated(*FromTI))
|
||||
if (FromTI != FromMBB.end() && !TII->isPredicated(*FromTI))
|
||||
ToTI = ToBBI.BB->end();
|
||||
ToBBI.BB->splice(ToTI, FromBBI.BB, FromTI, FromBBI.BB->end());
|
||||
ToBBI.BB->splice(ToTI, &FromMBB, FromTI, FromMBB.end());
|
||||
|
||||
// Force normalizing the successors' probabilities of ToBBI.BB to convert all
|
||||
// unknown probabilities into known ones.
|
||||
@ -1787,19 +1797,19 @@ void IfConverter::MergeBlocks(BBInfo &ToBBI, BBInfo &FromBBI, bool AddEdges) {
|
||||
// eliminate all unknown probabilities in MBB.
|
||||
ToBBI.BB->normalizeSuccProbs();
|
||||
|
||||
SmallVector<MachineBasicBlock *, 4> FromSuccs(FromBBI.BB->succ_begin(),
|
||||
FromBBI.BB->succ_end());
|
||||
MachineBasicBlock *NBB = getNextBlock(FromBBI.BB);
|
||||
SmallVector<MachineBasicBlock *, 4> FromSuccs(FromMBB.succ_begin(),
|
||||
FromMBB.succ_end());
|
||||
MachineBasicBlock *NBB = getNextBlock(FromMBB);
|
||||
MachineBasicBlock *FallThrough = FromBBI.HasFallThrough ? NBB : nullptr;
|
||||
// The edge probability from ToBBI.BB to FromBBI.BB, which is only needed when
|
||||
// AddEdges is true and FromBBI.BB is a successor of ToBBI.BB.
|
||||
// The edge probability from ToBBI.BB to FromMBB, which is only needed when
|
||||
// AddEdges is true and FromMBB is a successor of ToBBI.BB.
|
||||
auto To2FromProb = BranchProbability::getZero();
|
||||
if (AddEdges && ToBBI.BB->isSuccessor(FromBBI.BB)) {
|
||||
To2FromProb = MBPI->getEdgeProbability(ToBBI.BB, FromBBI.BB);
|
||||
// Set the edge probability from ToBBI.BB to FromBBI.BB to zero to avoid the
|
||||
if (AddEdges && ToBBI.BB->isSuccessor(&FromMBB)) {
|
||||
To2FromProb = MBPI->getEdgeProbability(ToBBI.BB, &FromMBB);
|
||||
// Set the edge probability from ToBBI.BB to FromMBB to zero to avoid the
|
||||
// edge probability being merged to other edges when this edge is removed
|
||||
// later.
|
||||
ToBBI.BB->setSuccProbability(find(ToBBI.BB->successors(), FromBBI.BB),
|
||||
ToBBI.BB->setSuccProbability(find(ToBBI.BB->successors(), &FromMBB),
|
||||
BranchProbability::getZero());
|
||||
}
|
||||
|
||||
@ -1811,26 +1821,26 @@ void IfConverter::MergeBlocks(BBInfo &ToBBI, BBInfo &FromBBI, bool AddEdges) {
|
||||
auto NewProb = BranchProbability::getZero();
|
||||
if (AddEdges) {
|
||||
// Calculate the edge probability for the edge from ToBBI.BB to Succ,
|
||||
// which is a portion of the edge probability from FromBBI.BB to Succ. The
|
||||
// portion ratio is the edge probability from ToBBI.BB to FromBBI.BB (if
|
||||
// which is a portion of the edge probability from FromMBB to Succ. The
|
||||
// portion ratio is the edge probability from ToBBI.BB to FromMBB (if
|
||||
// FromBBI is a successor of ToBBI.BB. See comment below for excepion).
|
||||
NewProb = MBPI->getEdgeProbability(FromBBI.BB, Succ);
|
||||
NewProb = MBPI->getEdgeProbability(&FromMBB, Succ);
|
||||
|
||||
// To2FromProb is 0 when FromBBI.BB is not a successor of ToBBI.BB. This
|
||||
// only happens when if-converting a diamond CFG and FromBBI.BB is the
|
||||
// tail BB. In this case FromBBI.BB post-dominates ToBBI.BB and hence we
|
||||
// could just use the probabilities on FromBBI.BB's out-edges when adding
|
||||
// To2FromProb is 0 when FromMBB is not a successor of ToBBI.BB. This
|
||||
// only happens when if-converting a diamond CFG and FromMBB is the
|
||||
// tail BB. In this case FromMBB post-dominates ToBBI.BB and hence we
|
||||
// could just use the probabilities on FromMBB's out-edges when adding
|
||||
// new successors.
|
||||
if (!To2FromProb.isZero())
|
||||
NewProb *= To2FromProb;
|
||||
}
|
||||
|
||||
FromBBI.BB->removeSuccessor(Succ);
|
||||
FromMBB.removeSuccessor(Succ);
|
||||
|
||||
if (AddEdges) {
|
||||
// If the edge from ToBBI.BB to Succ already exists, update the
|
||||
// probability of this edge by adding NewProb to it. An example is shown
|
||||
// below, in which A is ToBBI.BB and B is FromBBI.BB. In this case we
|
||||
// below, in which A is ToBBI.BB and B is FromMBB. In this case we
|
||||
// don't have to set C as A's successor as it already is. We only need to
|
||||
// update the edge probability on A->C. Note that B will not be
|
||||
// immediately removed from A's successors. It is possible that B->D is
|
||||
@ -1860,8 +1870,8 @@ void IfConverter::MergeBlocks(BBInfo &ToBBI, BBInfo &FromBBI, bool AddEdges) {
|
||||
}
|
||||
|
||||
// Now FromBBI always falls through to the next block!
|
||||
if (NBB && !FromBBI.BB->isSuccessor(NBB))
|
||||
FromBBI.BB->addSuccessor(NBB);
|
||||
if (NBB && !FromMBB.isSuccessor(NBB))
|
||||
FromMBB.addSuccessor(NBB);
|
||||
|
||||
// Normalize the probabilities of ToBBI.BB's successors with all adjustment
|
||||
// we've done above.
|
||||
|
Loading…
Reference in New Issue
Block a user