Skip to content

Commit aac3574

Browse files
committed
[CodeGen][NewPM] Port phi-node-elimination to new pass manager
1 parent 0d74031 commit aac3574

21 files changed

+170
-50
lines changed

llvm/include/llvm/CodeGen/MachineBasicBlock.h

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,8 @@ class raw_ostream;
4343
class LiveIntervals;
4444
class TargetRegisterClass;
4545
class TargetRegisterInfo;
46+
template <typename IRUnitT, typename... ExtraArgTs> class AnalysisManager;
47+
using MachineFunctionAnalysisManager = AnalysisManager<MachineFunction>;
4648

4749
// This structure uniquely identifies a basic block section.
4850
// Possible values are
@@ -968,7 +970,16 @@ class MachineBasicBlock
968970
/// MachineLoopInfo, as applicable.
969971
MachineBasicBlock *
970972
SplitCriticalEdge(MachineBasicBlock *Succ, Pass &P,
971-
std::vector<SparseBitVector<>> *LiveInSets = nullptr);
973+
std::vector<SparseBitVector<>> *LiveInSets = nullptr) {
974+
return SplitCriticalEdge(Succ, &P, nullptr, LiveInSets);
975+
}
976+
977+
MachineBasicBlock *
978+
SplitCriticalEdge(MachineBasicBlock *Succ,
979+
MachineFunctionAnalysisManager &MFAM,
980+
std::vector<SparseBitVector<>> *LiveInSets = nullptr) {
981+
return SplitCriticalEdge(Succ, nullptr, &MFAM, LiveInSets);
982+
}
972983

973984
/// Check if the edge between this block and the given successor \p
974985
/// Succ, can be split. If this returns true a subsequent call to
@@ -1243,6 +1254,12 @@ class MachineBasicBlock
12431254
/// unless you know what you're doing, because it doesn't update Pred's
12441255
/// successors list. Use Pred->removeSuccessor instead.
12451256
void removePredecessor(MachineBasicBlock *Pred);
1257+
1258+
// Helper method for new pass manager migration.
1259+
MachineBasicBlock *
1260+
SplitCriticalEdge(MachineBasicBlock *Succ, Pass *P,
1261+
MachineFunctionAnalysisManager *MFAM,
1262+
std::vector<SparseBitVector<>> *LiveInSets);
12461263
};
12471264

12481265
raw_ostream& operator<<(raw_ostream &OS, const MachineBasicBlock &MBB);
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
//===- llvm/CodeGen/PHIElimination.h ----------------------------*- C++ -*-===//
2+
//
3+
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4+
// See https://llvm.org/LICENSE.txt for license information.
5+
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6+
//
7+
//===----------------------------------------------------------------------===//
8+
9+
#ifndef LLVM_CODEGEN_PHIELIMINATION_H
10+
#define LLVM_CODEGEN_PHIELIMINATION_H
11+
12+
#include "llvm/CodeGen/MachinePassManager.h"
13+
14+
namespace llvm {
15+
16+
class PHIEliminationPass : public PassInfoMixin<PHIEliminationPass> {
17+
public:
18+
PreservedAnalyses run(MachineFunction &MF,
19+
MachineFunctionAnalysisManager &MFAM);
20+
};
21+
22+
} // namespace llvm
23+
24+
#endif // LLVM_CODEGEN_PHIELIMINATION_H

llvm/include/llvm/Passes/CodeGenPassBuilder.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,7 @@
4343
#include "llvm/CodeGen/MachineFunctionAnalysis.h"
4444
#include "llvm/CodeGen/MachineModuleInfo.h"
4545
#include "llvm/CodeGen/MachinePassManager.h"
46+
#include "llvm/CodeGen/PHIElimination.h"
4647
#include "llvm/CodeGen/PreISelIntrinsicLowering.h"
4748
#include "llvm/CodeGen/RegAllocFast.h"
4849
#include "llvm/CodeGen/ReplaceWithVeclib.h"

llvm/include/llvm/Passes/MachinePassRegistry.def

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -132,6 +132,7 @@ MACHINE_FUNCTION_PASS("dead-mi-elimination", DeadMachineInstructionElimPass())
132132
MACHINE_FUNCTION_PASS("finalize-isel", FinalizeISelPass())
133133
MACHINE_FUNCTION_PASS("localstackalloc", LocalStackSlotAllocationPass())
134134
MACHINE_FUNCTION_PASS("no-op-machine-function", NoOpMachineFunctionPass())
135+
MACHINE_FUNCTION_PASS("phi-node-elimination", PHIEliminationPass())
135136
MACHINE_FUNCTION_PASS("print", PrintMIRPass())
136137
MACHINE_FUNCTION_PASS("print<live-intervals>", LiveIntervalsPrinterPass(dbgs()))
137138
MACHINE_FUNCTION_PASS("print<live-vars>", LiveVariablesPrinterPass(dbgs()))
@@ -231,7 +232,6 @@ DUMMY_MACHINE_FUNCTION_PASS("mirfs-discriminators", MIRAddFSDiscriminatorsPass)
231232
DUMMY_MACHINE_FUNCTION_PASS("opt-phis", OptimizePHIsPass)
232233
DUMMY_MACHINE_FUNCTION_PASS("patchable-function", PatchableFunctionPass)
233234
DUMMY_MACHINE_FUNCTION_PASS("peephole-opt", PeepholeOptimizerPass)
234-
DUMMY_MACHINE_FUNCTION_PASS("phi-node-elimination", PHIEliminationPass)
235235
DUMMY_MACHINE_FUNCTION_PASS("post-RA-sched", PostRASchedulerPass)
236236
DUMMY_MACHINE_FUNCTION_PASS("postmisched", PostMachineSchedulerPass)
237237
DUMMY_MACHINE_FUNCTION_PASS("postra-machine-sink", PostRAMachineSinkingPass)

llvm/lib/CodeGen/MachineBasicBlock.cpp

Lines changed: 17 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1135,9 +1135,19 @@ class SlotIndexUpdateDelegate : public MachineFunction::Delegate {
11351135
}
11361136
};
11371137

1138+
#define GET_RESULT(RESULT, GETTER, INFIX) \
1139+
[MF, P, MFAM]() { \
1140+
if (P) { \
1141+
auto *Wrapper = P->getAnalysisIfAvailable<RESULT##INFIX##WrapperPass>(); \
1142+
return Wrapper ? &Wrapper->GETTER() : nullptr; \
1143+
} \
1144+
return MFAM->getCachedResult<RESULT##Analysis>(*MF); \
1145+
}()
1146+
11381147
MachineBasicBlock *MachineBasicBlock::SplitCriticalEdge(
1139-
MachineBasicBlock *Succ, Pass &P,
1148+
MachineBasicBlock *Succ, Pass *P, MachineFunctionAnalysisManager *MFAM,
11401149
std::vector<SparseBitVector<>> *LiveInSets) {
1150+
assert((P || MFAM) && "Need a way to get analysis results!");
11411151
if (!canSplitCriticalEdge(Succ))
11421152
return nullptr;
11431153

@@ -1161,10 +1171,8 @@ MachineBasicBlock *MachineBasicBlock::SplitCriticalEdge(
11611171
<< " -- " << printMBBReference(*NMBB) << " -- "
11621172
<< printMBBReference(*Succ) << '\n');
11631173

1164-
auto *LISWrapper = P.getAnalysisIfAvailable<LiveIntervalsWrapperPass>();
1165-
LiveIntervals *LIS = LISWrapper ? &LISWrapper->getLIS() : nullptr;
1166-
auto *SIWrapper = P.getAnalysisIfAvailable<SlotIndexesWrapperPass>();
1167-
SlotIndexes *Indexes = SIWrapper ? &SIWrapper->getSI() : nullptr;
1174+
LiveIntervals *LIS = GET_RESULT(LiveIntervals, getLIS, );
1175+
SlotIndexes *Indexes = GET_RESULT(SlotIndexes, getSI, );
11681176
if (LIS)
11691177
LIS->insertMBBInMaps(NMBB);
11701178
else if (Indexes)
@@ -1173,8 +1181,7 @@ MachineBasicBlock *MachineBasicBlock::SplitCriticalEdge(
11731181
// On some targets like Mips, branches may kill virtual registers. Make sure
11741182
// that LiveVariables is properly updated after updateTerminator replaces the
11751183
// terminators.
1176-
auto *LVWrapper = P.getAnalysisIfAvailable<LiveVariablesWrapperPass>();
1177-
LiveVariables *LV = LVWrapper ? &LVWrapper->getLV() : nullptr;
1184+
LiveVariables *LV = GET_RESULT(LiveVariables, getLV, );
11781185

11791186
// Collect a list of virtual registers killed by the terminators.
11801187
SmallVector<Register, 4> KilledRegs;
@@ -1339,12 +1346,10 @@ MachineBasicBlock *MachineBasicBlock::SplitCriticalEdge(
13391346
LIS->repairIntervalsInRange(this, getFirstTerminator(), end(), UsedRegs);
13401347
}
13411348

1342-
if (auto *MDTWrapper =
1343-
P.getAnalysisIfAvailable<MachineDominatorTreeWrapperPass>())
1344-
MDTWrapper->getDomTree().recordSplitCriticalEdge(this, Succ, NMBB);
1349+
if (auto *MDT = GET_RESULT(MachineDominatorTree, getDomTree, ))
1350+
MDT->recordSplitCriticalEdge(this, Succ, NMBB);
13451351

1346-
auto *MLIWrapper = P.getAnalysisIfAvailable<MachineLoopInfoWrapperPass>();
1347-
if (MachineLoopInfo *MLI = MLIWrapper ? &MLIWrapper->getLI() : nullptr)
1352+
if (MachineLoopInfo *MLI = GET_RESULT(MachineLoop, getLI, Info))
13481353
if (MachineLoop *TIL = MLI->getLoopFor(this)) {
13491354
// If one or the other blocks were not in a loop, the new block is not
13501355
// either, and thus LI doesn't need to be updated.

llvm/lib/CodeGen/PHIElimination.cpp

Lines changed: 84 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
//
1313
//===----------------------------------------------------------------------===//
1414

15+
#include "llvm/CodeGen/PHIElimination.h"
1516
#include "PHIEliminationUtils.h"
1617
#include "llvm/ADT/DenseMap.h"
1718
#include "llvm/ADT/SmallPtrSet.h"
@@ -28,6 +29,7 @@
2829
#include "llvm/CodeGen/MachineInstrBuilder.h"
2930
#include "llvm/CodeGen/MachineLoopInfo.h"
3031
#include "llvm/CodeGen/MachineOperand.h"
32+
#include "llvm/CodeGen/MachinePostDominators.h"
3133
#include "llvm/CodeGen/MachineRegisterInfo.h"
3234
#include "llvm/CodeGen/SlotIndexes.h"
3335
#include "llvm/CodeGen/TargetInstrInfo.h"
@@ -64,22 +66,13 @@ static cl::opt<bool> NoPhiElimLiveOutEarlyExit(
6466

6567
namespace {
6668

67-
class PHIElimination : public MachineFunctionPass {
69+
class PHIEliminationImpl {
6870
MachineRegisterInfo *MRI = nullptr; // Machine register information
6971
LiveVariables *LV = nullptr;
7072
LiveIntervals *LIS = nullptr;
73+
MachineLoopInfo *MLI = nullptr;
74+
MachineDominatorTree *MDT = nullptr;
7175

72-
public:
73-
static char ID; // Pass identification, replacement for typeid
74-
75-
PHIElimination() : MachineFunctionPass(ID) {
76-
initializePHIEliminationPass(*PassRegistry::getPassRegistry());
77-
}
78-
79-
bool runOnMachineFunction(MachineFunction &MF) override;
80-
void getAnalysisUsage(AnalysisUsage &AU) const override;
81-
82-
private:
8376
/// EliminatePHINodes - Eliminate phi nodes by inserting copy instructions
8477
/// in predecessor basic blocks.
8578
bool EliminatePHINodes(MachineFunction &MF, MachineBasicBlock &MBB);
@@ -118,10 +111,72 @@ class PHIElimination : public MachineFunctionPass {
118111
using LoweredPHIMap =
119112
DenseMap<MachineInstr *, unsigned, MachineInstrExpressionTrait>;
120113
LoweredPHIMap LoweredPHIs;
114+
115+
MachineFunctionPass *P;
116+
MachineFunctionAnalysisManager *MFAM;
117+
118+
public:
119+
PHIEliminationImpl(MachineFunctionPass *P) : P(P) {
120+
auto *LVWrapper = P->getAnalysisIfAvailable<LiveVariablesWrapperPass>();
121+
auto *LISWrapper = P->getAnalysisIfAvailable<LiveIntervalsWrapperPass>();
122+
auto *MLIWrapper = P->getAnalysisIfAvailable<MachineLoopInfoWrapperPass>();
123+
auto *MDTWrapper =
124+
P->getAnalysisIfAvailable<MachineDominatorTreeWrapperPass>();
125+
LV = LVWrapper ? &LVWrapper->getLV() : nullptr;
126+
LIS = LISWrapper ? &LISWrapper->getLIS() : nullptr;
127+
MLI = MLIWrapper ? &MLIWrapper->getLI() : nullptr;
128+
MDT = MDTWrapper ? &MDTWrapper->getDomTree() : nullptr;
129+
}
130+
131+
PHIEliminationImpl(MachineFunction &MF, MachineFunctionAnalysisManager &AM)
132+
: LV(AM.getCachedResult<LiveVariablesAnalysis>(MF)),
133+
LIS(AM.getCachedResult<LiveIntervalsAnalysis>(MF)),
134+
MLI(AM.getCachedResult<MachineLoopAnalysis>(MF)),
135+
MDT(AM.getCachedResult<MachineDominatorTreeAnalysis>(MF)), MFAM(&AM) {}
136+
137+
bool run(MachineFunction &MF);
138+
};
139+
140+
class PHIElimination : public MachineFunctionPass {
141+
public:
142+
static char ID; // Pass identification, replacement for typeid
143+
144+
PHIElimination() : MachineFunctionPass(ID) {
145+
initializePHIEliminationPass(*PassRegistry::getPassRegistry());
146+
}
147+
148+
bool runOnMachineFunction(MachineFunction &MF) override {
149+
PHIEliminationImpl Impl(this);
150+
return Impl.run(MF);
151+
}
152+
153+
MachineFunctionProperties getSetProperties() const override {
154+
return MachineFunctionProperties().set(
155+
MachineFunctionProperties::Property::NoPHIs);
156+
}
157+
158+
void getAnalysisUsage(AnalysisUsage &AU) const override;
121159
};
122160

123161
} // end anonymous namespace
124162

163+
PreservedAnalyses
164+
PHIEliminationPass::run(MachineFunction &MF,
165+
MachineFunctionAnalysisManager &MFAM) {
166+
PHIEliminationImpl Impl(MF, MFAM);
167+
bool Changed = Impl.run(MF);
168+
if (!Changed)
169+
return PreservedAnalyses::all();
170+
auto PA = getMachineFunctionPassPreservedAnalyses();
171+
PA.preserve<LiveIntervalsAnalysis>();
172+
PA.preserve<LiveVariablesAnalysis>();
173+
PA.preserve<SlotIndexesAnalysis>();
174+
PA.preserve<MachineDominatorTreeAnalysis>();
175+
PA.preserve<MachinePostDominatorTreeAnalysis>();
176+
PA.preserve<MachineLoopAnalysis>();
177+
return PA;
178+
}
179+
125180
STATISTIC(NumLowered, "Number of phis lowered");
126181
STATISTIC(NumCriticalEdgesSplit, "Number of critical edges split");
127182
STATISTIC(NumReused, "Number of reused lowered phis");
@@ -147,12 +202,8 @@ void PHIElimination::getAnalysisUsage(AnalysisUsage &AU) const {
147202
MachineFunctionPass::getAnalysisUsage(AU);
148203
}
149204

150-
bool PHIElimination::runOnMachineFunction(MachineFunction &MF) {
205+
bool PHIEliminationImpl::run(MachineFunction &MF) {
151206
MRI = &MF.getRegInfo();
152-
auto *LVWrapper = getAnalysisIfAvailable<LiveVariablesWrapperPass>();
153-
LV = LVWrapper ? &LVWrapper->getLV() : nullptr;
154-
auto *LISWrapper = getAnalysisIfAvailable<LiveIntervalsWrapperPass>();
155-
LIS = LISWrapper ? &LISWrapper->getLIS() : nullptr;
156207

157208
bool Changed = false;
158209

@@ -187,9 +238,6 @@ bool PHIElimination::runOnMachineFunction(MachineFunction &MF) {
187238
}
188239
}
189240

190-
MachineLoopInfoWrapperPass *MLIWrapper =
191-
getAnalysisIfAvailable<MachineLoopInfoWrapperPass>();
192-
MachineLoopInfo *MLI = MLIWrapper ? &MLIWrapper->getLI() : nullptr;
193241
for (auto &MBB : MF)
194242
Changed |= SplitPHIEdges(MF, MBB, MLI, (LV ? &LiveInSets : nullptr));
195243
}
@@ -223,9 +271,8 @@ bool PHIElimination::runOnMachineFunction(MachineFunction &MF) {
223271
}
224272

225273
// TODO: we should use the incremental DomTree updater here.
226-
if (Changed)
227-
if (auto *MDT = getAnalysisIfAvailable<MachineDominatorTreeWrapperPass>())
228-
MDT->getDomTree().getBase().recalculate(MF);
274+
if (Changed && MDT)
275+
MDT->getBase().recalculate(MF);
229276

230277
LoweredPHIs.clear();
231278
ImpDefs.clear();
@@ -238,8 +285,8 @@ bool PHIElimination::runOnMachineFunction(MachineFunction &MF) {
238285

239286
/// EliminatePHINodes - Eliminate phi nodes by inserting copy instructions in
240287
/// predecessor basic blocks.
241-
bool PHIElimination::EliminatePHINodes(MachineFunction &MF,
242-
MachineBasicBlock &MBB) {
288+
bool PHIEliminationImpl::EliminatePHINodes(MachineFunction &MF,
289+
MachineBasicBlock &MBB) {
243290
if (MBB.empty() || !MBB.front().isPHI())
244291
return false; // Quick exit for basic blocks without PHIs.
245292

@@ -286,9 +333,9 @@ static bool allPhiOperandsUndefined(const MachineInstr &MPhi,
286333
return true;
287334
}
288335
/// LowerPHINode - Lower the PHI node at the top of the specified block.
289-
void PHIElimination::LowerPHINode(MachineBasicBlock &MBB,
290-
MachineBasicBlock::iterator LastPHIIt,
291-
bool AllEdgesCritical) {
336+
void PHIEliminationImpl::LowerPHINode(MachineBasicBlock &MBB,
337+
MachineBasicBlock::iterator LastPHIIt,
338+
bool AllEdgesCritical) {
292339
++NumLowered;
293340

294341
MachineBasicBlock::iterator AfterPHIsIt = std::next(LastPHIIt);
@@ -689,7 +736,7 @@ void PHIElimination::LowerPHINode(MachineBasicBlock &MBB,
689736
/// particular, we want to map the number of uses of a virtual register which is
690737
/// used in a PHI node. We map that to the BB the vreg is coming from. This is
691738
/// used later to determine when the vreg is killed in the BB.
692-
void PHIElimination::analyzePHINodes(const MachineFunction &MF) {
739+
void PHIEliminationImpl::analyzePHINodes(const MachineFunction &MF) {
693740
for (const auto &MBB : MF) {
694741
for (const auto &BBI : MBB) {
695742
if (!BBI.isPHI())
@@ -705,9 +752,9 @@ void PHIElimination::analyzePHINodes(const MachineFunction &MF) {
705752
}
706753
}
707754

708-
bool PHIElimination::SplitPHIEdges(MachineFunction &MF, MachineBasicBlock &MBB,
709-
MachineLoopInfo *MLI,
710-
std::vector<SparseBitVector<>> *LiveInSets) {
755+
bool PHIEliminationImpl::SplitPHIEdges(
756+
MachineFunction &MF, MachineBasicBlock &MBB, MachineLoopInfo *MLI,
757+
std::vector<SparseBitVector<>> *LiveInSets) {
711758
if (MBB.empty() || !MBB.front().isPHI() || MBB.isEHPad())
712759
return false; // Quick exit for basic blocks without PHIs.
713760

@@ -774,7 +821,8 @@ bool PHIElimination::SplitPHIEdges(MachineFunction &MF, MachineBasicBlock &MBB,
774821
}
775822
if (!ShouldSplit && !SplitAllCriticalEdges)
776823
continue;
777-
if (!PreMBB->SplitCriticalEdge(&MBB, *this, LiveInSets)) {
824+
if (!(P ? PreMBB->SplitCriticalEdge(&MBB, *P, LiveInSets)
825+
: PreMBB->SplitCriticalEdge(&MBB, *MFAM, LiveInSets))) {
778826
LLVM_DEBUG(dbgs() << "Failed to split critical edge.\n");
779827
continue;
780828
}
@@ -785,7 +833,7 @@ bool PHIElimination::SplitPHIEdges(MachineFunction &MF, MachineBasicBlock &MBB,
785833
return Changed;
786834
}
787835

788-
bool PHIElimination::isLiveIn(Register Reg, const MachineBasicBlock *MBB) {
836+
bool PHIEliminationImpl::isLiveIn(Register Reg, const MachineBasicBlock *MBB) {
789837
assert((LV || LIS) &&
790838
"isLiveIn() requires either LiveVariables or LiveIntervals");
791839
if (LIS)
@@ -794,8 +842,8 @@ bool PHIElimination::isLiveIn(Register Reg, const MachineBasicBlock *MBB) {
794842
return LV->isLiveIn(Reg, *MBB);
795843
}
796844

797-
bool PHIElimination::isLiveOutPastPHIs(Register Reg,
798-
const MachineBasicBlock *MBB) {
845+
bool PHIEliminationImpl::isLiveOutPastPHIs(Register Reg,
846+
const MachineBasicBlock *MBB) {
799847
assert((LV || LIS) &&
800848
"isLiveOutPastPHIs() requires either LiveVariables or LiveIntervals");
801849
// LiveVariables considers uses in PHIs to be in the predecessor basic block,

llvm/lib/Passes/PassBuilder.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -105,6 +105,7 @@
105105
#include "llvm/CodeGen/MachinePostDominators.h"
106106
#include "llvm/CodeGen/MachineRegisterInfo.h"
107107
#include "llvm/CodeGen/MachineVerifier.h"
108+
#include "llvm/CodeGen/PHIElimination.h"
108109
#include "llvm/CodeGen/PreISelIntrinsicLowering.h"
109110
#include "llvm/CodeGen/RegAllocFast.h"
110111
#include "llvm/CodeGen/SafeStack.h"

llvm/test/CodeGen/AArch64/PHIElimination-crash.mir

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,9 @@
11
# RUN: llc -mtriple=aarch64-linux-gnu -verify-machineinstrs -o /dev/null %s \
22
# RUN: -run-pass=livevars,phi-node-elimination,twoaddressinstruction \
33
# RUN: -no-phi-elim-live-out-early-exit=1 -phi-elim-split-all-critical-edges=1
4+
# RUN: llc -mtriple=aarch64-linux-gnu -verify-machineinstrs -o /dev/null %s \
5+
# RUN: --passes='require<live-vars>,phi-node-elimination,two-address-instruction' \
6+
# RUN: -no-phi-elim-live-out-early-exit=1 -phi-elim-split-all-critical-edges=1
47

58
# Used to result in
69
#

0 commit comments

Comments
 (0)