Skip to content

Commit ddf6d01

Browse files
paperchaliceyuxuanchen1997
authored andcommitted
[CodeGen][NewPM] Port phi-node-elimination to new pass manager (#98867)
Summary: - Add `PHIEliminationPass `. - Support new pass manager in `MachineBasicBlock:: SplitCriticalEdge ` Test Plan: Reviewers: Subscribers: Tasks: Tags: Differential Revision: https://phabricator.intern.facebook.com/D60251632
1 parent 6959adc commit ddf6d01

21 files changed

+168
-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: 82 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"
@@ -64,22 +65,13 @@ static cl::opt<bool> NoPhiElimLiveOutEarlyExit(
6465

6566
namespace {
6667

67-
class PHIElimination : public MachineFunctionPass {
68+
class PHIEliminationImpl {
6869
MachineRegisterInfo *MRI = nullptr; // Machine register information
6970
LiveVariables *LV = nullptr;
7071
LiveIntervals *LIS = nullptr;
72+
MachineLoopInfo *MLI = nullptr;
73+
MachineDominatorTree *MDT = nullptr;
7174

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:
8375
/// EliminatePHINodes - Eliminate phi nodes by inserting copy instructions
8476
/// in predecessor basic blocks.
8577
bool EliminatePHINodes(MachineFunction &MF, MachineBasicBlock &MBB);
@@ -118,10 +110,71 @@ class PHIElimination : public MachineFunctionPass {
118110
using LoweredPHIMap =
119111
DenseMap<MachineInstr *, unsigned, MachineInstrExpressionTrait>;
120112
LoweredPHIMap LoweredPHIs;
113+
114+
MachineFunctionPass *P = nullptr;
115+
MachineFunctionAnalysisManager *MFAM = nullptr;
116+
117+
public:
118+
PHIEliminationImpl(MachineFunctionPass *P) : P(P) {
119+
auto *LVWrapper = P->getAnalysisIfAvailable<LiveVariablesWrapperPass>();
120+
auto *LISWrapper = P->getAnalysisIfAvailable<LiveIntervalsWrapperPass>();
121+
auto *MLIWrapper = P->getAnalysisIfAvailable<MachineLoopInfoWrapperPass>();
122+
auto *MDTWrapper =
123+
P->getAnalysisIfAvailable<MachineDominatorTreeWrapperPass>();
124+
LV = LVWrapper ? &LVWrapper->getLV() : nullptr;
125+
LIS = LISWrapper ? &LISWrapper->getLIS() : nullptr;
126+
MLI = MLIWrapper ? &MLIWrapper->getLI() : nullptr;
127+
MDT = MDTWrapper ? &MDTWrapper->getDomTree() : nullptr;
128+
}
129+
130+
PHIEliminationImpl(MachineFunction &MF, MachineFunctionAnalysisManager &AM)
131+
: LV(AM.getCachedResult<LiveVariablesAnalysis>(MF)),
132+
LIS(AM.getCachedResult<LiveIntervalsAnalysis>(MF)),
133+
MLI(AM.getCachedResult<MachineLoopAnalysis>(MF)),
134+
MDT(AM.getCachedResult<MachineDominatorTreeAnalysis>(MF)), MFAM(&AM) {}
135+
136+
bool run(MachineFunction &MF);
137+
};
138+
139+
class PHIElimination : public MachineFunctionPass {
140+
public:
141+
static char ID; // Pass identification, replacement for typeid
142+
143+
PHIElimination() : MachineFunctionPass(ID) {
144+
initializePHIEliminationPass(*PassRegistry::getPassRegistry());
145+
}
146+
147+
bool runOnMachineFunction(MachineFunction &MF) override {
148+
PHIEliminationImpl Impl(this);
149+
return Impl.run(MF);
150+
}
151+
152+
MachineFunctionProperties getSetProperties() const override {
153+
return MachineFunctionProperties().set(
154+
MachineFunctionProperties::Property::NoPHIs);
155+
}
156+
157+
void getAnalysisUsage(AnalysisUsage &AU) const override;
121158
};
122159

123160
} // end anonymous namespace
124161

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

150-
bool PHIElimination::runOnMachineFunction(MachineFunction &MF) {
203+
bool PHIEliminationImpl::run(MachineFunction &MF) {
151204
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;
156205

157206
bool Changed = false;
158207

@@ -187,9 +236,6 @@ bool PHIElimination::runOnMachineFunction(MachineFunction &MF) {
187236
}
188237
}
189238

190-
MachineLoopInfoWrapperPass *MLIWrapper =
191-
getAnalysisIfAvailable<MachineLoopInfoWrapperPass>();
192-
MachineLoopInfo *MLI = MLIWrapper ? &MLIWrapper->getLI() : nullptr;
193239
for (auto &MBB : MF)
194240
Changed |= SplitPHIEdges(MF, MBB, MLI, (LV ? &LiveInSets : nullptr));
195241
}
@@ -223,9 +269,8 @@ bool PHIElimination::runOnMachineFunction(MachineFunction &MF) {
223269
}
224270

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

230275
LoweredPHIs.clear();
231276
ImpDefs.clear();
@@ -238,8 +283,8 @@ bool PHIElimination::runOnMachineFunction(MachineFunction &MF) {
238283

239284
/// EliminatePHINodes - Eliminate phi nodes by inserting copy instructions in
240285
/// predecessor basic blocks.
241-
bool PHIElimination::EliminatePHINodes(MachineFunction &MF,
242-
MachineBasicBlock &MBB) {
286+
bool PHIEliminationImpl::EliminatePHINodes(MachineFunction &MF,
287+
MachineBasicBlock &MBB) {
243288
if (MBB.empty() || !MBB.front().isPHI())
244289
return false; // Quick exit for basic blocks without PHIs.
245290

@@ -286,9 +331,9 @@ static bool allPhiOperandsUndefined(const MachineInstr &MPhi,
286331
return true;
287332
}
288333
/// 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) {
334+
void PHIEliminationImpl::LowerPHINode(MachineBasicBlock &MBB,
335+
MachineBasicBlock::iterator LastPHIIt,
336+
bool AllEdgesCritical) {
292337
++NumLowered;
293338

294339
MachineBasicBlock::iterator AfterPHIsIt = std::next(LastPHIIt);
@@ -689,7 +734,7 @@ void PHIElimination::LowerPHINode(MachineBasicBlock &MBB,
689734
/// particular, we want to map the number of uses of a virtual register which is
690735
/// used in a PHI node. We map that to the BB the vreg is coming from. This is
691736
/// used later to determine when the vreg is killed in the BB.
692-
void PHIElimination::analyzePHINodes(const MachineFunction &MF) {
737+
void PHIEliminationImpl::analyzePHINodes(const MachineFunction &MF) {
693738
for (const auto &MBB : MF) {
694739
for (const auto &BBI : MBB) {
695740
if (!BBI.isPHI())
@@ -705,9 +750,9 @@ void PHIElimination::analyzePHINodes(const MachineFunction &MF) {
705750
}
706751
}
707752

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

@@ -774,7 +819,8 @@ bool PHIElimination::SplitPHIEdges(MachineFunction &MF, MachineBasicBlock &MBB,
774819
}
775820
if (!ShouldSplit && !SplitAllCriticalEdges)
776821
continue;
777-
if (!PreMBB->SplitCriticalEdge(&MBB, *this, LiveInSets)) {
822+
if (!(P ? PreMBB->SplitCriticalEdge(&MBB, *P, LiveInSets)
823+
: PreMBB->SplitCriticalEdge(&MBB, *MFAM, LiveInSets))) {
778824
LLVM_DEBUG(dbgs() << "Failed to split critical edge.\n");
779825
continue;
780826
}
@@ -785,7 +831,7 @@ bool PHIElimination::SplitPHIEdges(MachineFunction &MF, MachineBasicBlock &MBB,
785831
return Changed;
786832
}
787833

788-
bool PHIElimination::isLiveIn(Register Reg, const MachineBasicBlock *MBB) {
834+
bool PHIEliminationImpl::isLiveIn(Register Reg, const MachineBasicBlock *MBB) {
789835
assert((LV || LIS) &&
790836
"isLiveIn() requires either LiveVariables or LiveIntervals");
791837
if (LIS)
@@ -794,8 +840,8 @@ bool PHIElimination::isLiveIn(Register Reg, const MachineBasicBlock *MBB) {
794840
return LV->isLiveIn(Reg, *MBB);
795841
}
796842

797-
bool PHIElimination::isLiveOutPastPHIs(Register Reg,
798-
const MachineBasicBlock *MBB) {
843+
bool PHIEliminationImpl::isLiveOutPastPHIs(Register Reg,
844+
const MachineBasicBlock *MBB) {
799845
assert((LV || LIS) &&
800846
"isLiveOutPastPHIs() requires either LiveVariables or LiveIntervals");
801847
// 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
#

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

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,10 @@
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 \
44
# RUN: | FileCheck %s
5+
# RUN: llc -mtriple=aarch64-linux-gnu -verify-machineinstrs -o - %s \
6+
# RUN: --passes='require<live-vars>,phi-node-elimination,two-address-instruction' \
7+
# RUN: -no-phi-elim-live-out-early-exit=1 -phi-elim-split-all-critical-edges=1 \
8+
# RUN: | FileCheck %s
59

610
--- |
711
define void @test() !dbg !7 {

0 commit comments

Comments
 (0)