MachineBasicBlock *DomBB,
MachineBasicBlock *SuccBB);
+ void addNewBlock(MachineBasicBlock *BB,
+ MachineBasicBlock *DomBB,
+ MachineBasicBlock *SuccBB,
+ std::vector<SparseBitVector<>> &LiveInSets);
+
/// isPHIJoin - Return true if Reg is a phi join register.
bool isPHIJoin(unsigned Reg) { return PHIJoins.test(Reg); }
#include "llvm/ADT/ilist_node.h"
#include "llvm/ADT/iterator_range.h"
#include "llvm/ADT/simple_ilist.h"
+#include "llvm/ADT/SparseBitVector.h"
#include "llvm/CodeGen/MachineInstr.h"
#include "llvm/CodeGen/MachineInstrBundleIterator.h"
#include "llvm/IR/DebugLoc.h"
///
/// This function updates LiveVariables, MachineDominatorTree, and
/// MachineLoopInfo, as applicable.
- MachineBasicBlock *SplitCriticalEdge(MachineBasicBlock *Succ, Pass &P);
+ MachineBasicBlock *
+ SplitCriticalEdge(MachineBasicBlock *Succ, Pass &P,
+ std::vector<SparseBitVector<>> *LiveInSets = nullptr);
/// Check if the edge between this block and the given successor \p
/// Succ, can be split. If this returns true a subsequent call to
VI.AliveBlocks.set(NumNew);
}
}
+
+/// addNewBlock - Add a new basic block BB as an empty succcessor to DomBB. All
+/// variables that are live out of DomBB will be marked as passing live through
+/// BB. LiveInSets[BB] is *not* updated (because it is not needed during
+/// PHIElimination).
+void LiveVariables::addNewBlock(MachineBasicBlock *BB,
+ MachineBasicBlock *DomBB,
+ MachineBasicBlock *SuccBB,
+ std::vector<SparseBitVector<>> &LiveInSets) {
+ const unsigned NumNew = BB->getNumber();
+
+ SparseBitVector<> &BV = LiveInSets[SuccBB->getNumber()];
+ for (auto R = BV.begin(), E = BV.end(); R != E; R++) {
+ unsigned VirtReg = Register::index2VirtReg(*R);
+ LiveVariables::VarInfo &VI = getVarInfo(VirtReg);
+ VI.AliveBlocks.set(NumNew);
+ }
+ // All registers used by PHI nodes in SuccBB must be live through BB.
+ for (MachineBasicBlock::iterator BBI = SuccBB->begin(),
+ BBE = SuccBB->end();
+ BBI != BBE && BBI->isPHI(); ++BBI) {
+ for (unsigned i = 1, e = BBI->getNumOperands(); i != e; i += 2)
+ if (BBI->getOperand(i + 1).getMBB() == BB)
+ getVarInfo(BBI->getOperand(i).getReg())
+ .AliveBlocks.set(NumNew);
+ }
+}
return getFallThrough() != nullptr;
}
-MachineBasicBlock *MachineBasicBlock::SplitCriticalEdge(MachineBasicBlock *Succ,
- Pass &P) {
+MachineBasicBlock *MachineBasicBlock::SplitCriticalEdge(
+ MachineBasicBlock *Succ, Pass &P,
+ std::vector<SparseBitVector<>> *LiveInSets) {
if (!canSplitCriticalEdge(Succ))
return nullptr;
}
}
// Update relevant live-through information.
- LV->addNewBlock(NMBB, this, Succ);
+ if (LiveInSets != nullptr)
+ LV->addNewBlock(NMBB, this, Succ, *LiveInSets);
+ else
+ LV->addNewBlock(NMBB, this, Succ);
}
if (LIS) {
/// Split critical edges where necessary for good coalescer performance.
bool SplitPHIEdges(MachineFunction &MF, MachineBasicBlock &MBB,
- MachineLoopInfo *MLI);
+ MachineLoopInfo *MLI,
+ std::vector<SparseBitVector<>> *LiveInSets);
// These functions are temporary abstractions around LiveVariables and
// LiveIntervals, so they can go away when LiveVariables does.
bool Changed = false;
- // This pass takes the function out of SSA form.
- MRI->leaveSSA();
-
// Split critical edges to help the coalescer.
if (!DisableEdgeSplitting && (LV || LIS)) {
+ // A set of live-in regs for each MBB which is used to update LV
+ // efficiently also with large functions.
+ std::vector<SparseBitVector<>> LiveInSets;
+ if (LV) {
+ LiveInSets.resize(MF.size());
+ for (unsigned Index = 0, e = MRI->getNumVirtRegs(); Index != e; ++Index) {
+ // Set the bit for this register for each MBB where it is
+ // live-through or live-in (killed).
+ unsigned VirtReg = Register::index2VirtReg(Index);
+ MachineInstr *DefMI = MRI->getVRegDef(VirtReg);
+ if (!DefMI)
+ continue;
+ LiveVariables::VarInfo &VI = LV->getVarInfo(VirtReg);
+ SparseBitVector<>::iterator AliveBlockItr = VI.AliveBlocks.begin();
+ SparseBitVector<>::iterator EndItr = VI.AliveBlocks.end();
+ while (AliveBlockItr != EndItr) {
+ unsigned BlockNum = *(AliveBlockItr++);
+ LiveInSets[BlockNum].set(Index);
+ }
+ // The register is live into an MBB in which it is killed but not
+ // defined. See comment for VarInfo in LiveVariables.h.
+ MachineBasicBlock *DefMBB = DefMI->getParent();
+ if (VI.Kills.size() > 1 ||
+ (!VI.Kills.empty() && VI.Kills.front()->getParent() != DefMBB))
+ for (auto *MI : VI.Kills)
+ LiveInSets[MI->getParent()->getNumber()].set(Index);
+ }
+ }
+
MachineLoopInfo *MLI = getAnalysisIfAvailable<MachineLoopInfo>();
for (auto &MBB : MF)
- Changed |= SplitPHIEdges(MF, MBB, MLI);
+ Changed |= SplitPHIEdges(MF, MBB, MLI, (LV ? &LiveInSets : nullptr));
}
+ // This pass takes the function out of SSA form.
+ MRI->leaveSSA();
+
// Populate VRegPHIUseCount
analyzePHINodes(MF);
bool PHIElimination::SplitPHIEdges(MachineFunction &MF,
MachineBasicBlock &MBB,
- MachineLoopInfo *MLI) {
+ MachineLoopInfo *MLI,
+ std::vector<SparseBitVector<>> *LiveInSets) {
if (MBB.empty() || !MBB.front().isPHI() || MBB.isEHPad())
return false; // Quick exit for basic blocks without PHIs.
}
if (!ShouldSplit && !SplitAllCriticalEdges)
continue;
- if (!PreMBB->SplitCriticalEdge(&MBB, *this)) {
+ if (!PreMBB->SplitCriticalEdge(&MBB, *this, LiveInSets)) {
LLVM_DEBUG(dbgs() << "Failed to split critical edge.\n");
continue;
}