Skip to content

Commit

Permalink
[CodeGen][NewPM] Port LiveVariables to new pass manager (#97880)
Browse files Browse the repository at this point in the history
- Port `LiveVariables` to new pass manager.
- Convert to `LiveVariablesWrapperPass` in legacy pass manager.
  • Loading branch information
paperchalice committed Jul 9, 2024
1 parent 366eb8f commit ac0b281
Show file tree
Hide file tree
Showing 16 changed files with 202 additions and 92 deletions.
69 changes: 56 additions & 13 deletions llvm/include/llvm/CodeGen/LiveVariables.h
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@
#include "llvm/ADT/SparseBitVector.h"
#include "llvm/CodeGen/MachineFunctionPass.h"
#include "llvm/CodeGen/MachineInstr.h"
#include "llvm/CodeGen/MachinePassManager.h"
#include "llvm/CodeGen/TargetRegisterInfo.h"
#include "llvm/InitializePasses.h"
#include "llvm/PassRegistry.h"
Expand All @@ -44,13 +45,10 @@ namespace llvm {
class MachineBasicBlock;
class MachineRegisterInfo;

class LiveVariables : public MachineFunctionPass {
public:
static char ID; // Pass identification, replacement for typeid
LiveVariables() : MachineFunctionPass(ID) {
initializeLiveVariablesPass(*PassRegistry::getPassRegistry());
}
class LiveVariables {
friend class LiveVariablesWrapperPass;

public:
/// VarInfo - This represents the regions where a virtual register is live in
/// the program. We represent this with three different pieces of
/// information: the set of blocks in which the instruction is live
Expand Down Expand Up @@ -109,6 +107,8 @@ class LiveVariables : public MachineFunctionPass {
bool isLiveIn(const MachineBasicBlock &MBB, Register Reg,
MachineRegisterInfo &MRI);

void print(raw_ostream &OS) const;

void dump() const;
};

Expand Down Expand Up @@ -141,6 +141,11 @@ class LiveVariables : public MachineFunctionPass {
// current basic block.
DenseMap<MachineInstr*, unsigned> DistanceMap;

// For legacy pass.
LiveVariables() = default;

void analyze(MachineFunction &MF);

/// HandlePhysRegKill - Add kills of Reg and its sub-registers to the
/// uses. Pay special attention to the sub-register uses which may come below
/// the last use of the whole register.
Expand Down Expand Up @@ -174,9 +179,11 @@ class LiveVariables : public MachineFunctionPass {
unsigned NumRegs);

void runOnBlock(MachineBasicBlock *MBB, unsigned NumRegs);

public:
LiveVariables(MachineFunction &MF);

bool runOnMachineFunction(MachineFunction &MF) override;
void print(raw_ostream &OS) const;

//===--------------------------------------------------------------------===//
// API to update live variable information
Expand Down Expand Up @@ -258,12 +265,6 @@ class LiveVariables : public MachineFunctionPass {
return true;
}

void getAnalysisUsage(AnalysisUsage &AU) const override;

void releaseMemory() override {
VirtRegInfo.clear();
}

/// getVarInfo - Return the VarInfo structure for the specified VIRTUAL
/// register.
VarInfo &getVarInfo(Register Reg);
Expand Down Expand Up @@ -300,6 +301,48 @@ class LiveVariables : public MachineFunctionPass {
std::vector<SparseBitVector<>> &LiveInSets);
};

class LiveVariablesAnalysis : public AnalysisInfoMixin<LiveVariablesAnalysis> {
friend AnalysisInfoMixin<LiveVariablesAnalysis>;
static AnalysisKey Key;

public:
using Result = LiveVariables;
Result run(MachineFunction &MF, MachineFunctionAnalysisManager &);
};

class LiveVariablesPrinterPass
: public PassInfoMixin<LiveVariablesPrinterPass> {
raw_ostream &OS;

public:
explicit LiveVariablesPrinterPass(raw_ostream &OS) : OS(OS) {}
PreservedAnalyses run(MachineFunction &MF,
MachineFunctionAnalysisManager &MFAM);
static bool isRequired() { return true; }
};

class LiveVariablesWrapperPass : public MachineFunctionPass {
LiveVariables LV;

public:
static char ID; // Pass identification, replacement for typeid

LiveVariablesWrapperPass() : MachineFunctionPass(ID) {
initializeLiveVariablesWrapperPassPass(*PassRegistry::getPassRegistry());
}

bool runOnMachineFunction(MachineFunction &MF) override {
LV.analyze(MF);
return false;
}

void getAnalysisUsage(AnalysisUsage &AU) const override;

void releaseMemory() override { LV.VirtRegInfo.clear(); }

LiveVariables &getLV() { return LV; }
};

} // End llvm namespace

#endif
2 changes: 1 addition & 1 deletion llvm/include/llvm/InitializePasses.h
Original file line number Diff line number Diff line change
Expand Up @@ -155,7 +155,7 @@ void initializeLiveIntervalsPass(PassRegistry&);
void initializeLiveRangeShrinkPass(PassRegistry&);
void initializeLiveRegMatrixPass(PassRegistry&);
void initializeLiveStacksPass(PassRegistry&);
void initializeLiveVariablesPass(PassRegistry &);
void initializeLiveVariablesWrapperPassPass(PassRegistry &);
void initializeLoadStoreOptPass(PassRegistry &);
void initializeLoadStoreVectorizerLegacyPassPass(PassRegistry&);
void initializeLocalStackSlotPassPass(PassRegistry&);
Expand Down
14 changes: 7 additions & 7 deletions llvm/include/llvm/Passes/MachinePassRegistry.def
Original file line number Diff line number Diff line change
Expand Up @@ -89,20 +89,19 @@ LOOP_PASS("loop-reduce", LoopStrengthReducePass())
#ifndef MACHINE_FUNCTION_ANALYSIS
#define MACHINE_FUNCTION_ANALYSIS(NAME, CREATE_PASS)
#endif
// LiveVariables currently requires pure SSA form.
// FIXME: Once TwoAddressInstruction pass no longer uses kill flags,
// LiveVariables can be removed completely, and LiveIntervals can be directly
// computed. (We still either need to regenerate kill flags after regalloc, or
// preferably fix the scavenger to not depend on them).
MACHINE_FUNCTION_ANALYSIS("live-vars", LiveVariablesAnalysis())
MACHINE_FUNCTION_ANALYSIS("machine-branch-prob",
MachineBranchProbabilityAnalysis())
MACHINE_FUNCTION_ANALYSIS("machine-dom-tree", MachineDominatorTreeAnalysis())
MACHINE_FUNCTION_ANALYSIS("machine-loops", MachineLoopAnalysis())
MACHINE_FUNCTION_ANALYSIS("machine-post-dom-tree",
MachinePostDominatorTreeAnalysis())
MACHINE_FUNCTION_ANALYSIS("pass-instrumentation", PassInstrumentationAnalysis(PIC))
// LiveVariables currently requires pure SSA form.
// FIXME: Once TwoAddressInstruction pass no longer uses kill flags,
// LiveVariables can be removed completely, and LiveIntervals can be directly
// computed. (We still either need to regenerate kill flags after regalloc, or
// preferably fix the scavenger to not depend on them).
// MACHINE_FUNCTION_ANALYSIS("live-vars", LiveVariablesAnalysis())

// MACHINE_FUNCTION_ANALYSIS("live-stacks", LiveStacksPass())
// MACHINE_FUNCTION_ANALYSIS("slot-indexes", SlotIndexesAnalysis())
// MACHINE_FUNCTION_ANALYSIS("edge-bundles", EdgeBundlesAnalysis())
Expand Down Expand Up @@ -133,6 +132,7 @@ MACHINE_FUNCTION_PASS("finalize-isel", FinalizeISelPass())
MACHINE_FUNCTION_PASS("localstackalloc", LocalStackSlotAllocationPass())
MACHINE_FUNCTION_PASS("no-op-machine-function", NoOpMachineFunctionPass())
MACHINE_FUNCTION_PASS("print", PrintMIRPass())
MACHINE_FUNCTION_PASS("print<live-vars>", LiveVariablesPrinterPass(dbgs()))
MACHINE_FUNCTION_PASS("print<machine-branch-prob>",
MachineBranchProbabilityPrinterPass(dbgs()))
MACHINE_FUNCTION_PASS("print<machine-dom-tree>",
Expand Down
2 changes: 1 addition & 1 deletion llvm/lib/CodeGen/CodeGen.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,7 @@ void llvm::initializeCodeGen(PassRegistry &Registry) {
initializeLiveIntervalsPass(Registry);
initializeLiveRangeShrinkPass(Registry);
initializeLiveStacksPass(Registry);
initializeLiveVariablesPass(Registry);
initializeLiveVariablesWrapperPassPass(Registry);
initializeLocalStackSlotPassPass(Registry);
initializeLowerGlobalDtorsLegacyPassPass(Registry);
initializeLowerIntrinsicsPass(Registry);
Expand Down
2 changes: 1 addition & 1 deletion llvm/lib/CodeGen/LiveIntervals.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,7 @@ cl::opt<bool> UseSegmentSetForPhysRegs(

void LiveIntervals::getAnalysisUsage(AnalysisUsage &AU) const {
AU.setPreservesCFG();
AU.addPreserved<LiveVariables>();
AU.addPreserved<LiveVariablesWrapperPass>();
AU.addPreservedID(MachineLoopInfoID);
AU.addRequiredTransitiveID(MachineDominatorsID);
AU.addPreservedID(MachineDominatorsID);
Expand Down
66 changes: 47 additions & 19 deletions llvm/lib/CodeGen/LiveVariables.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -41,21 +41,49 @@
#include <algorithm>
using namespace llvm;

char LiveVariables::ID = 0;
char &llvm::LiveVariablesID = LiveVariables::ID;
INITIALIZE_PASS_BEGIN(LiveVariables, "livevars",
"Live Variable Analysis", false, false)
INITIALIZE_PASS_DEPENDENCY(UnreachableMachineBlockElim)
INITIALIZE_PASS_END(LiveVariables, "livevars",
"Live Variable Analysis", false, false)
AnalysisKey LiveVariablesAnalysis::Key;

LiveVariablesAnalysis::Result
LiveVariablesAnalysis::run(MachineFunction &MF,
MachineFunctionAnalysisManager &) {
return Result(MF);
}

PreservedAnalyses
LiveVariablesPrinterPass::run(MachineFunction &MF,
MachineFunctionAnalysisManager &MFAM) {
OS << "Live variables in machine function: " << MF.getName() << '\n';
MFAM.getResult<LiveVariablesAnalysis>(MF).print(OS);
return PreservedAnalyses::all();
}

char LiveVariablesWrapperPass::ID = 0;
char &llvm::LiveVariablesID = LiveVariablesWrapperPass::ID;
INITIALIZE_PASS_BEGIN(LiveVariablesWrapperPass, "livevars",
"Live Variable Analysis", false, false)
INITIALIZE_PASS_DEPENDENCY(UnreachableMachineBlockElim)
INITIALIZE_PASS_END(LiveVariablesWrapperPass, "livevars",
"Live Variable Analysis", false, false)

void LiveVariables::getAnalysisUsage(AnalysisUsage &AU) const {
void LiveVariablesWrapperPass::getAnalysisUsage(AnalysisUsage &AU) const {
AU.addRequiredID(UnreachableMachineBlockElimID);
AU.setPreservesAll();
MachineFunctionPass::getAnalysisUsage(AU);
}

LiveVariables::LiveVariables(MachineFunction &MF)
: MF(&MF), MRI(&MF.getRegInfo()), TRI(MF.getSubtarget().getRegisterInfo()) {
analyze(MF);
}

void LiveVariables::print(raw_ostream &OS) const {
for (size_t I = 0, E = VirtRegInfo.size(); I != E; ++I) {
const Register Reg = Register::index2VirtReg(I);
OS << "Virtual register '%" << I << "':\n";
VirtRegInfo[Reg].print(OS);
}
}

MachineInstr *
LiveVariables::VarInfo::findKill(const MachineBasicBlock *MBB) const {
for (MachineInstr *MI : Kills)
Expand All @@ -64,20 +92,22 @@ LiveVariables::VarInfo::findKill(const MachineBasicBlock *MBB) const {
return nullptr;
}

#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP)
LLVM_DUMP_METHOD void LiveVariables::VarInfo::dump() const {
dbgs() << " Alive in blocks: ";
void LiveVariables::VarInfo::print(raw_ostream &OS) const {
OS << " Alive in blocks: ";
for (unsigned AB : AliveBlocks)
dbgs() << AB << ", ";
dbgs() << "\n Killed by:";
OS << AB << ", ";
OS << "\n Killed by:";
if (Kills.empty())
dbgs() << " No instructions.\n";
OS << " No instructions.\n\n";
else {
for (unsigned i = 0, e = Kills.size(); i != e; ++i)
dbgs() << "\n #" << i << ": " << *Kills[i];
dbgs() << "\n";
OS << "\n #" << i << ": " << *Kills[i];
OS << "\n";
}
}

#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP)
LLVM_DUMP_METHOD void LiveVariables::VarInfo::dump() const { print(dbgs()); }
#endif

/// getVarInfo - Get (possibly creating) a VarInfo object for the given vreg.
Expand Down Expand Up @@ -595,7 +625,7 @@ void LiveVariables::runOnBlock(MachineBasicBlock *MBB, unsigned NumRegs) {
HandlePhysRegDef(i, nullptr, Defs);
}

bool LiveVariables::runOnMachineFunction(MachineFunction &mf) {
void LiveVariables::analyze(MachineFunction &mf) {
MF = &mf;
MRI = &mf.getRegInfo();
TRI = MF->getSubtarget().getRegisterInfo();
Expand Down Expand Up @@ -649,8 +679,6 @@ bool LiveVariables::runOnMachineFunction(MachineFunction &mf) {
PhysRegDef.clear();
PhysRegUse.clear();
PHIVarInfo.clear();

return false;
}

void LiveVariables::recomputeForSingleDefVirtReg(Register Reg) {
Expand Down
3 changes: 2 additions & 1 deletion llvm/lib/CodeGen/MachineBasicBlock.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1171,7 +1171,8 @@ MachineBasicBlock *MachineBasicBlock::SplitCriticalEdge(
// On some targets like Mips, branches may kill virtual registers. Make sure
// that LiveVariables is properly updated after updateTerminator replaces the
// terminators.
LiveVariables *LV = P.getAnalysisIfAvailable<LiveVariables>();
auto *LVWrapper = P.getAnalysisIfAvailable<LiveVariablesWrapperPass>();
LiveVariables *LV = LVWrapper ? &LVWrapper->getLV() : nullptr;

// Collect a list of virtual registers killed by the terminators.
SmallVector<Register, 4> KilledRegs;
Expand Down
5 changes: 3 additions & 2 deletions llvm/lib/CodeGen/MachineVerifier.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -314,7 +314,7 @@ namespace {

void getAnalysisUsage(AnalysisUsage &AU) const override {
AU.addUsedIfAvailable<LiveStacks>();
AU.addUsedIfAvailable<LiveVariables>();
AU.addUsedIfAvailable<LiveVariablesWrapperPass>();
AU.addUsedIfAvailable<SlotIndexes>();
AU.addUsedIfAvailable<LiveIntervals>();
AU.setPreservesAll();
Expand Down Expand Up @@ -430,8 +430,9 @@ unsigned MachineVerifier::verify(const MachineFunction &MF) {
if (PASS) {
LiveInts = PASS->getAnalysisIfAvailable<LiveIntervals>();
// We don't want to verify LiveVariables if LiveIntervals is available.
auto *LVWrapper = PASS->getAnalysisIfAvailable<LiveVariablesWrapperPass>();
if (!LiveInts)
LiveVars = PASS->getAnalysisIfAvailable<LiveVariables>();
LiveVars = LVWrapper ? &LVWrapper->getLV() : nullptr;
LiveStks = PASS->getAnalysisIfAvailable<LiveStacks>();
Indexes = PASS->getAnalysisIfAvailable<SlotIndexes>();
}
Expand Down
9 changes: 5 additions & 4 deletions llvm/lib/CodeGen/PHIElimination.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -131,13 +131,13 @@ char& llvm::PHIEliminationID = PHIElimination::ID;
INITIALIZE_PASS_BEGIN(PHIElimination, DEBUG_TYPE,
"Eliminate PHI nodes for register allocation",
false, false)
INITIALIZE_PASS_DEPENDENCY(LiveVariables)
INITIALIZE_PASS_DEPENDENCY(LiveVariablesWrapperPass)
INITIALIZE_PASS_END(PHIElimination, DEBUG_TYPE,
"Eliminate PHI nodes for register allocation", false, false)

void PHIElimination::getAnalysisUsage(AnalysisUsage &AU) const {
AU.addUsedIfAvailable<LiveVariables>();
AU.addPreserved<LiveVariables>();
AU.addUsedIfAvailable<LiveVariablesWrapperPass>();
AU.addPreserved<LiveVariablesWrapperPass>();
AU.addPreserved<SlotIndexes>();
AU.addPreserved<LiveIntervals>();
AU.addPreserved<MachineDominatorTreeWrapperPass>();
Expand All @@ -147,7 +147,8 @@ void PHIElimination::getAnalysisUsage(AnalysisUsage &AU) const {

bool PHIElimination::runOnMachineFunction(MachineFunction &MF) {
MRI = &MF.getRegInfo();
LV = getAnalysisIfAvailable<LiveVariables>();
auto *LVWrapper = getAnalysisIfAvailable<LiveVariablesWrapperPass>();
LV = LVWrapper ? &LVWrapper->getLV() : nullptr;
LIS = getAnalysisIfAvailable<LiveIntervals>();

bool Changed = false;
Expand Down
7 changes: 4 additions & 3 deletions llvm/lib/CodeGen/TwoAddressInstructionPass.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -195,8 +195,8 @@ class TwoAddressInstructionPass : public MachineFunctionPass {
void getAnalysisUsage(AnalysisUsage &AU) const override {
AU.setPreservesCFG();
AU.addUsedIfAvailable<AAResultsWrapperPass>();
AU.addUsedIfAvailable<LiveVariables>();
AU.addPreserved<LiveVariables>();
AU.addUsedIfAvailable<LiveVariablesWrapperPass>();
AU.addPreserved<LiveVariablesWrapperPass>();
AU.addPreserved<SlotIndexes>();
AU.addPreserved<LiveIntervals>();
AU.addPreservedID(MachineLoopInfoID);
Expand Down Expand Up @@ -1762,7 +1762,8 @@ bool TwoAddressInstructionPass::runOnMachineFunction(MachineFunction &Func) {
TII = MF->getSubtarget().getInstrInfo();
TRI = MF->getSubtarget().getRegisterInfo();
InstrItins = MF->getSubtarget().getInstrItineraryData();
LV = getAnalysisIfAvailable<LiveVariables>();
auto *LVWrapper = getAnalysisIfAvailable<LiveVariablesWrapperPass>();
LV = LVWrapper ? &LVWrapper->getLV() : nullptr;
LIS = getAnalysisIfAvailable<LiveIntervals>();
if (auto *AAPass = getAnalysisIfAvailable<AAResultsWrapperPass>())
AA = &AAPass->getAAResults();
Expand Down
1 change: 1 addition & 0 deletions llvm/lib/Passes/PassBuilder.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -90,6 +90,7 @@
#include "llvm/CodeGen/InterleavedAccess.h"
#include "llvm/CodeGen/InterleavedLoadCombine.h"
#include "llvm/CodeGen/JMCInstrumenter.h"
#include "llvm/CodeGen/LiveVariables.h"
#include "llvm/CodeGen/LocalStackSlotAllocation.h"
#include "llvm/CodeGen/LowerEmuTLS.h"
#include "llvm/CodeGen/MIRPrinter.h"
Expand Down
3 changes: 2 additions & 1 deletion llvm/lib/Target/AMDGPU/SILowerControlFlow.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -763,7 +763,8 @@ bool SILowerControlFlow::runOnMachineFunction(MachineFunction &MF) {
// This doesn't actually need LiveIntervals, but we can preserve them.
LIS = getAnalysisIfAvailable<LiveIntervals>();
// This doesn't actually need LiveVariables, but we can preserve them.
LV = getAnalysisIfAvailable<LiveVariables>();
auto *LVWrapper = getAnalysisIfAvailable<LiveVariablesWrapperPass>();
LV = LVWrapper ? &LVWrapper->getLV() : nullptr;
auto *MDTWrapper = getAnalysisIfAvailable<MachineDominatorTreeWrapperPass>();
MDT = MDTWrapper ? &MDTWrapper->getDomTree() : nullptr;
MRI = &MF.getRegInfo();
Expand Down
Loading

0 comments on commit ac0b281

Please sign in to comment.