Skip to content

Commit 5e3864a

Browse files
committed
Add TargetPassBuilder.
1 parent 4cc152c commit 5e3864a

File tree

9 files changed

+1375
-0
lines changed

9 files changed

+1375
-0
lines changed

llvm/include/llvm/Passes/MachinePassRegistry.def

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -288,11 +288,13 @@ DUMMY_MACHINE_MODULE_PASS("pseudo-probe-inserter", PseudoProbeInserterPass)
288288
DUMMY_MACHINE_MODULE_PASS("mir-debugify", DebugifyMachineModule)
289289
DUMMY_MACHINE_MODULE_PASS("mir-check-debugify", CheckDebugMachineModulePass)
290290
DUMMY_MACHINE_MODULE_PASS("mir-strip-debug", StripDebugMachineModulePass)
291+
DUMMY_MACHINE_MODULE_PASS("static-data-annotator", StaticDataAnnotatorPass)
291292
#undef DUMMY_MACHINE_MODULE_PASS
292293

293294
#ifndef DUMMY_MACHINE_FUNCTION_PASS
294295
#define DUMMY_MACHINE_FUNCTION_PASS(NAME, PASS_NAME)
295296
#endif
297+
DUMMY_MACHINE_FUNCTION_PASS("bb-path-cloning", BasicBlockPathCloningPass)
296298
DUMMY_MACHINE_FUNCTION_PASS("bbsections-prepare", BasicBlockSectionsPass)
297299
DUMMY_MACHINE_FUNCTION_PASS("bbsections-profile-reader", BasicBlockSectionsProfileReaderPass)
298300
DUMMY_MACHINE_FUNCTION_PASS("break-false-deps", BreakFalseDepsPass)
@@ -325,5 +327,6 @@ DUMMY_MACHINE_FUNCTION_PASS("regallocscoringpass", RegAllocScoringPass)
325327
DUMMY_MACHINE_FUNCTION_PASS("regbankselect", RegBankSelectPass)
326328
DUMMY_MACHINE_FUNCTION_PASS("reset-machine-function", ResetMachineFunctionPass)
327329
DUMMY_MACHINE_FUNCTION_PASS("stackmap-liveness", StackMapLivenessPass)
330+
DUMMY_MACHINE_FUNCTION_PASS("static-data-splitter", StaticDataSplitterPass)
328331
DUMMY_MACHINE_FUNCTION_PASS("unpack-mi-bundles", UnpackMachineBundlesPass)
329332
#undef DUMMY_MACHINE_FUNCTION_PASS

llvm/include/llvm/Passes/PassBuilder.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -112,6 +112,8 @@ class PassBuilder {
112112
std::optional<PGOOptions> PGOOpt;
113113
PassInstrumentationCallbacks *PIC;
114114

115+
friend class TargetPassBuilder;
116+
115117
public:
116118
/// A struct to capture parsed pass pipeline names.
117119
///
Lines changed: 319 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,319 @@
1+
//===- Parsing, selection, and construction of pass pipelines --*- 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+
/// \file
9+
///
10+
/// Interfaces for registering analysis passes, producing common pass manager
11+
/// configurations, and parsing of pass pipelines.
12+
///
13+
//===----------------------------------------------------------------------===//
14+
15+
#ifndef LLVM_PASSES_TARGETPASSBUILDER_H
16+
#define LLVM_PASSES_TARGETPASSBUILDER_H
17+
18+
#include "llvm/ADT/SmallVector.h"
19+
#include "llvm/ADT/StringSet.h"
20+
#include "llvm/ADT/identity.h"
21+
#include "llvm/Analysis/CGSCCPassManager.h"
22+
#include "llvm/CodeGen/MachinePassManager.h"
23+
#include "llvm/Target/CGPassBuilderOption.h"
24+
#include "llvm/Transforms/Scalar/LoopPassManager.h"
25+
#include <list>
26+
#include <type_traits>
27+
#include <unordered_set>
28+
#include <utility>
29+
#include <variant>
30+
#include <vector>
31+
32+
namespace llvm {
33+
34+
class PassBuilder;
35+
class TargetMachine;
36+
class SelectionDAGISel;
37+
38+
class TargetPassBuilder {
39+
public:
40+
TargetPassBuilder(PassBuilder &PB);
41+
42+
virtual ~TargetPassBuilder() = default;
43+
44+
// TODO: Add necessary parameters once AsmPrinter is ported to new pass
45+
// manager.
46+
llvm::ModulePassManager buildPipeline(raw_pwrite_stream &Out,
47+
raw_pwrite_stream *DwoOut,
48+
CodeGenFileType FileType,
49+
MCContext &Ctx);
50+
51+
private:
52+
struct PassWrapper {
53+
StringRef Name;
54+
std::variant<llvm::ModulePassManager, llvm::FunctionPassManager,
55+
llvm::LoopPassManager, llvm::MachineFunctionPassManager>
56+
InternalPass;
57+
bool InCGSCC = false;
58+
59+
template <typename PassManagerT>
60+
PassWrapper(StringRef Name, PassManagerT &&PM)
61+
: Name(Name), InternalPass(std::forward<PassManagerT>(PM)) {}
62+
63+
template <typename PassT> PassWrapper(PassT &&P) : Name(PassT::name()) {
64+
if constexpr (isModulePass<PassT>) {
65+
llvm::ModulePassManager MPM;
66+
MPM.addPass(std::forward<PassT>(P));
67+
InternalPass.emplace<llvm::ModulePassManager>(std::move(MPM));
68+
} else if constexpr (isFunctionPass<PassT>) {
69+
llvm::FunctionPassManager FPM;
70+
FPM.addPass(std::forward<PassT>(P));
71+
InternalPass.emplace<llvm::FunctionPassManager>(std::move(FPM));
72+
} else {
73+
static_assert(isMachineFunctionPass<PassT>, "Invalid pass type!");
74+
llvm::MachineFunctionPassManager MFPM;
75+
MFPM.addPass(std::forward<PassT>(P));
76+
InternalPass.emplace<llvm::MachineFunctionPassManager>(std::move(MFPM));
77+
}
78+
}
79+
};
80+
81+
public:
82+
using PassList = std::list<PassWrapper>;
83+
84+
private:
85+
template <typename InternalPassT> struct AdaptorWrapper : InternalPassT {
86+
using InternalPassT::Passes;
87+
};
88+
89+
template <typename PassManagerT, typename InternalPassT = void>
90+
class PassManagerWrapper {
91+
friend class TargetPassBuilder;
92+
93+
public:
94+
bool isEmpty() const { return Passes.empty(); }
95+
96+
template <typename PassT> void addPass(PassT &&P) {
97+
PassManagerT PM;
98+
PM.addPass(std::forward<PassT>(P));
99+
PassWrapper PW(PassT::name(), std::move(PM));
100+
Passes.push_back(std::move(PW));
101+
}
102+
103+
void addPass(PassManagerWrapper &&PM) {
104+
for (auto &P : PM.Passes)
105+
Passes.push_back(std::move(P));
106+
}
107+
108+
void addPass(AdaptorWrapper<InternalPassT> &&Adaptor) {
109+
for (auto &P : Adaptor.Passes)
110+
Passes.push_back(std::move(P));
111+
}
112+
113+
void addPass(llvm::ModulePassManager &&) = delete;
114+
void addPass(llvm::FunctionPassManager &&) = delete;
115+
void addPass(llvm::LoopPassManager &&) = delete;
116+
void addPass(llvm::MachineFunctionPassManager &&) = delete;
117+
118+
private:
119+
PassList Passes;
120+
};
121+
122+
template <typename NestedPassManagerT, typename PassT>
123+
AdaptorWrapper<NestedPassManagerT> createPassAdaptor(PassT &&P) {
124+
AdaptorWrapper<NestedPassManagerT> Adaptor;
125+
Adaptor.addPass(std::forward<PassT>(P));
126+
return Adaptor;
127+
}
128+
129+
private:
130+
template <typename PassT, typename IRUnitT>
131+
using HasRunOnIRUnit = decltype(std::declval<PassT>().run(
132+
std::declval<IRUnitT &>(), std::declval<AnalysisManager<IRUnitT> &>()));
133+
template <typename PassT>
134+
static constexpr bool isModulePass =
135+
is_detected<HasRunOnIRUnit, PassT, Module>::value;
136+
template <typename PassT>
137+
static constexpr bool isFunctionPass =
138+
is_detected<HasRunOnIRUnit, PassT, Function>::value;
139+
template <typename PassT>
140+
static constexpr bool isMachineFunctionPass =
141+
is_detected<HasRunOnIRUnit, PassT, MachineFunction>::value;
142+
143+
protected:
144+
// Hijack real pass managers intentionally.
145+
using MachineFunctionPassManager =
146+
PassManagerWrapper<llvm::MachineFunctionPassManager>;
147+
using FunctionPassManager =
148+
PassManagerWrapper<llvm::FunctionPassManager, MachineFunctionPassManager>;
149+
using ModulePassManager =
150+
PassManagerWrapper<llvm::ModulePassManager, FunctionPassManager>;
151+
152+
struct CGSCCAdaptorWrapper : AdaptorWrapper<FunctionPassManager> {};
153+
154+
protected:
155+
template <typename FunctionPassT>
156+
AdaptorWrapper<FunctionPassManager>
157+
createModuleToFunctionPassAdaptor(FunctionPassT &&P) {
158+
return createPassAdaptor<FunctionPassManager>(
159+
std::forward<FunctionPassT>(P));
160+
}
161+
162+
AdaptorWrapper<FunctionPassManager>
163+
createModuleToPostOrderCGSCCPassAdaptor(CGSCCAdaptorWrapper &&PM) {
164+
AdaptorWrapper<FunctionPassManager> AW;
165+
AW.Passes = std::move(PM.Passes);
166+
return AW;
167+
}
168+
169+
template <typename FunctionPassT>
170+
CGSCCAdaptorWrapper createCGSCCToFunctionPassAdaptor(FunctionPassT &&PM) {
171+
for (auto &P : PM.Passes)
172+
P.InCGSCC = true;
173+
CGSCCAdaptorWrapper AW;
174+
AW.Passes = std::move(PM.Passes);
175+
return AW;
176+
}
177+
178+
template <typename MachineFunctionPassT>
179+
AdaptorWrapper<MachineFunctionPassManager>
180+
createFunctionToMachineFunctionPassAdaptor(MachineFunctionPassT &&P) {
181+
return createPassAdaptor<MachineFunctionPassManager>(
182+
std::forward<MachineFunctionPassT>(P));
183+
}
184+
185+
protected:
186+
PassBuilder &PB;
187+
TargetMachine *TM;
188+
CodeGenOptLevel OptLevel;
189+
CGPassBuilderOption CGPBO = getCGPassBuilderOption();
190+
191+
template <typename PassT,
192+
typename PassManagerT = std::conditional_t<
193+
isModulePass<PassT>, ModulePassManager,
194+
std::conditional_t<isFunctionPass<PassT>, FunctionPassManager,
195+
MachineFunctionPassManager>>>
196+
void injectBefore(
197+
typename llvm::identity<std::function<PassManagerT()>>::argument_type F) {
198+
InjectionCallbacks.push_back(
199+
[Accessed = false, F](PassList &Passes, PassList::iterator I) mutable {
200+
if (Accessed)
201+
return I;
202+
if (PassT::name() != I->Name)
203+
return I;
204+
Accessed = true;
205+
auto PMPasses = F().Passes;
206+
return Passes.insert(I, std::make_move_iterator(PMPasses.begin()),
207+
std::make_move_iterator(PMPasses.end()));
208+
});
209+
}
210+
211+
template <typename PassTs> void disablePass() {
212+
DisabedPasses.insert(PassTs::name());
213+
}
214+
215+
void disablePass(StringRef Name) { DisabedPasses.insert(Name); }
216+
217+
template <typename PassT> bool isPassDisabled() const {
218+
return DisabedPasses.contains(PassT::name());
219+
}
220+
221+
bool isPassDisabled(StringRef Name) const {
222+
return DisabedPasses.contains(Name);
223+
}
224+
225+
template <typename PassT> bool isPassEnabled() const {
226+
return !isPassDisabled<PassT>();
227+
}
228+
229+
bool isPassEnabled(StringRef Name) const { return !isPassDisabled(Name); }
230+
231+
protected:
232+
/// @brief Set target pass hook.
233+
/// @param Hook An instance provide pass getters
234+
/// It must implement getSelectionDAGISelPass
235+
/// TODO: Add ASM printer related hooks.
236+
template <typename HookT> void setTargetHook(HookT &&Hook) {
237+
TH = std::make_unique<TargetHookModel<HookT>>(std::forward<HookT>(Hook));
238+
}
239+
240+
private:
241+
class TargetHookConcept {
242+
virtual void anchor();
243+
244+
public:
245+
virtual void addSelectionDAGISelPass(MachineFunctionPassManager &MFPM) = 0;
246+
virtual void addAsmPrinterPass(ModulePassManager &MPM) = 0;
247+
virtual ~TargetHookConcept() = default;
248+
};
249+
250+
template <typename HookT> class TargetHookModel : public TargetHookConcept {
251+
HookT Hook;
252+
253+
public:
254+
TargetHookModel(HookT &&H) : Hook(H) {}
255+
256+
void addSelectionDAGISelPass(MachineFunctionPassManager &MFPM) override {
257+
using SelectionDAGISelPassT = decltype(Hook.getSelectionDAGISelPass());
258+
static_assert(isMachineFunctionPass<SelectionDAGISelPassT>,
259+
"Add machine function pass here.");
260+
static_assert(!std::is_same_v<llvm::MachineFunctionPassManager,
261+
SelectionDAGISelPassT>,
262+
"MachineFunctionPassManager is not allowed here.");
263+
MFPM.addPass(Hook.getSelectionDAGISelPass());
264+
}
265+
266+
void addAsmPrinterPass(ModulePassManager &MPM) override {
267+
// TODO: get AsmPrinterPass here.
268+
}
269+
};
270+
271+
std::unique_ptr<TargetHookConcept> TH;
272+
273+
void buildCoreCodeGenPipeline(ModulePassManager &MPM);
274+
275+
ModulePassManager buildCodeGenIRPipeline();
276+
277+
/// Add passes that optimize machine instructions in SSA form.
278+
void addISelPasses(MachineFunctionPassManager &MFPM);
279+
void addMachineSSAOptimizationPasses(MachineFunctionPassManager &MFPM);
280+
void addRegAllocPipeline(MachineFunctionPassManager &MFPM);
281+
void addRegAllocPass(MachineFunctionPassManager &MFPM, bool Optimized);
282+
ModulePassManager buildCodeGenMIRPipeline();
283+
284+
void addExceptionHandlingPasses(FunctionPassManager &FPM);
285+
286+
void filtPassList(ModulePassManager &MPM) const;
287+
288+
void addPrinterPassesAndFreeMachineFunction(ModulePassManager &MPM,
289+
raw_pwrite_stream &Out,
290+
raw_pwrite_stream *DwoOut,
291+
CodeGenFileType FileType,
292+
MCContext &Ctx);
293+
294+
llvm::ModulePassManager constructRealPassManager(ModulePassManager &&MPMW);
295+
296+
private:
297+
virtual void anchor();
298+
299+
StringSet<> DisabedPasses;
300+
std::vector<std::function<PassList::iterator(PassList &, PassList::iterator)>>
301+
InjectionCallbacks;
302+
303+
void invokeInjectionCallbacks(ModulePassManager &MPM) const;
304+
305+
// Only Loop Strength Reduction need this, shadow LoopPassManager
306+
// in future if it is necessary.
307+
template <typename PassT>
308+
void addLoopPass(FunctionPassManager &FPM, PassT &&P) {
309+
LoopPassManager LPM;
310+
LPM.addPass(std::forward<PassT>(P));
311+
FPM.Passes.push_back(PassWrapper(PassT::name(), std::move(LPM)));
312+
}
313+
};
314+
315+
template <> struct TargetPassBuilder::AdaptorWrapper<void> {};
316+
317+
} // namespace llvm
318+
319+
#endif

llvm/include/llvm/Target/CGPassBuilderOption.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,9 +51,11 @@ struct CGPassBuilderOption {
5151
bool EnableMachineFunctionSplitter = false;
5252
bool EnableSinkAndFold = false;
5353
bool EnableTailMerge = true;
54+
bool EnableLoopTermFold = false;
5455
bool MISchedPostRA = false;
5556
bool EarlyLiveIntervals = false;
5657
bool GCEmptyBlocks = false;
58+
bool SplitStaticData = false;
5759

5860
bool DisableLSR = false;
5961
bool DisableCGP = false;
@@ -65,6 +67,9 @@ struct CGPassBuilderOption {
6567
bool DisableExpandReductions = false;
6668
bool DisableRAFSProfileLoader = false;
6769
bool DisableCFIFixup = false;
70+
bool DisableReplaceWithVecLib = false;
71+
bool DisableLayoutFSProfileLoader = false;
72+
bool DisablePrologEpilogInserterPass = false;
6873
bool PrintAfterISel = false;
6974
bool PrintISelInput = false;
7075
bool RequiresCodeGenSCCOrder = false;

llvm/lib/CodeGen/TargetPassConfig.cpp

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -506,12 +506,15 @@ CGPassBuilderOption llvm::getCGPassBuilderOption() {
506506
SET_BOOLEAN_OPTION(DisableCGP)
507507
SET_BOOLEAN_OPTION(DisablePartialLibcallInlining)
508508
SET_BOOLEAN_OPTION(DisableSelectOptimize)
509+
SET_BOOLEAN_OPTION(DisableReplaceWithVecLib)
510+
SET_BOOLEAN_OPTION(DisableLayoutFSProfileLoader)
509511
SET_BOOLEAN_OPTION(PrintISelInput)
510512
SET_BOOLEAN_OPTION(DebugifyAndStripAll)
511513
SET_BOOLEAN_OPTION(DebugifyCheckAndStripAll)
512514
SET_BOOLEAN_OPTION(DisableRAFSProfileLoader)
513515
SET_BOOLEAN_OPTION(DisableCFIFixup)
514516
SET_BOOLEAN_OPTION(EnableMachineFunctionSplitter)
517+
SET_BOOLEAN_OPTION(SplitStaticData)
515518

516519
return Opt;
517520
}

llvm/lib/Passes/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ add_llvm_component_library(LLVMPasses
66
PassBuilderPipelines.cpp
77
PassPlugin.cpp
88
StandardInstrumentations.cpp
9+
TargetPassBuilder.cpp
910

1011
ADDITIONAL_HEADER_DIRS
1112
${LLVM_MAIN_INCLUDE_DIR}/llvm

0 commit comments

Comments
 (0)