[MachineScheduler] Fix physreg dependencies of ExitSU (#123541)
[llvm-project.git] / llvm / lib / CodeGen / RegAllocPriorityAdvisor.cpp
blob4525b8fc5a383f4a9c5acd6bd229053fd5764daa
1 //===- RegAllocPriorityAdvisor.cpp - live ranges priority advisor ---------===//
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 // Implementation of the default priority advisor and of the Analysis pass.
11 //===----------------------------------------------------------------------===//
13 #include "RegAllocPriorityAdvisor.h"
14 #include "RegAllocGreedy.h"
15 #include "llvm/CodeGen/MachineFunction.h"
16 #include "llvm/CodeGen/VirtRegMap.h"
17 #include "llvm/IR/Module.h"
18 #include "llvm/InitializePasses.h"
19 #include "llvm/Pass.h"
21 using namespace llvm;
23 static cl::opt<RegAllocPriorityAdvisorAnalysis::AdvisorMode> Mode(
24 "regalloc-enable-priority-advisor", cl::Hidden,
25 cl::init(RegAllocPriorityAdvisorAnalysis::AdvisorMode::Default),
26 cl::desc("Enable regalloc advisor mode"),
27 cl::values(
28 clEnumValN(RegAllocPriorityAdvisorAnalysis::AdvisorMode::Default,
29 "default", "Default"),
30 clEnumValN(RegAllocPriorityAdvisorAnalysis::AdvisorMode::Release,
31 "release", "precompiled"),
32 clEnumValN(RegAllocPriorityAdvisorAnalysis::AdvisorMode::Development,
33 "development", "for training"),
34 clEnumValN(
35 RegAllocPriorityAdvisorAnalysis::AdvisorMode::Dummy, "dummy",
36 "prioritize low virtual register numbers for test and debug")));
38 char RegAllocPriorityAdvisorAnalysis::ID = 0;
39 INITIALIZE_PASS(RegAllocPriorityAdvisorAnalysis, "regalloc-priority",
40 "Regalloc priority policy", false, true)
42 namespace {
43 class DefaultPriorityAdvisorAnalysis final
44 : public RegAllocPriorityAdvisorAnalysis {
45 public:
46 DefaultPriorityAdvisorAnalysis(bool NotAsRequested)
47 : RegAllocPriorityAdvisorAnalysis(AdvisorMode::Default),
48 NotAsRequested(NotAsRequested) {}
50 // support for isa<> and dyn_cast.
51 static bool classof(const RegAllocPriorityAdvisorAnalysis *R) {
52 return R->getAdvisorMode() == AdvisorMode::Default;
55 private:
56 void getAnalysisUsage(AnalysisUsage &AU) const override {
57 AU.addRequired<SlotIndexesWrapperPass>();
58 RegAllocPriorityAdvisorAnalysis::getAnalysisUsage(AU);
60 std::unique_ptr<RegAllocPriorityAdvisor>
61 getAdvisor(const MachineFunction &MF, const RAGreedy &RA) override {
62 return std::make_unique<DefaultPriorityAdvisor>(
63 MF, RA, &getAnalysis<SlotIndexesWrapperPass>().getSI());
65 bool doInitialization(Module &M) override {
66 if (NotAsRequested)
67 M.getContext().emitError("Requested regalloc priority advisor analysis "
68 "could be created. Using default");
69 return RegAllocPriorityAdvisorAnalysis::doInitialization(M);
71 const bool NotAsRequested;
74 class DummyPriorityAdvisorAnalysis final
75 : public RegAllocPriorityAdvisorAnalysis {
76 public:
77 DummyPriorityAdvisorAnalysis()
78 : RegAllocPriorityAdvisorAnalysis(AdvisorMode::Dummy) {}
80 // support for isa<> and dyn_cast.
81 static bool classof(const RegAllocPriorityAdvisorAnalysis *R) {
82 return R->getAdvisorMode() == AdvisorMode::Dummy;
85 private:
86 void getAnalysisUsage(AnalysisUsage &AU) const override {
87 AU.addRequired<SlotIndexesWrapperPass>();
88 RegAllocPriorityAdvisorAnalysis::getAnalysisUsage(AU);
91 std::unique_ptr<RegAllocPriorityAdvisor>
92 getAdvisor(const MachineFunction &MF, const RAGreedy &RA) override {
93 return std::make_unique<DummyPriorityAdvisor>(
94 MF, RA, &getAnalysis<SlotIndexesWrapperPass>().getSI());
98 } // namespace
100 template <> Pass *llvm::callDefaultCtor<RegAllocPriorityAdvisorAnalysis>() {
101 Pass *Ret = nullptr;
102 switch (Mode) {
103 case RegAllocPriorityAdvisorAnalysis::AdvisorMode::Default:
104 Ret = new DefaultPriorityAdvisorAnalysis(/*NotAsRequested*/ false);
105 break;
106 case RegAllocPriorityAdvisorAnalysis::AdvisorMode::Dummy:
107 Ret = new DummyPriorityAdvisorAnalysis();
108 break;
109 case RegAllocPriorityAdvisorAnalysis::AdvisorMode::Development:
110 #if defined(LLVM_HAVE_TFLITE)
111 Ret = createDevelopmentModePriorityAdvisor();
112 #endif
113 break;
114 case RegAllocPriorityAdvisorAnalysis::AdvisorMode::Release:
115 Ret = createReleaseModePriorityAdvisor();
116 break;
118 if (Ret)
119 return Ret;
120 return new DefaultPriorityAdvisorAnalysis(/*NotAsRequested*/ true);
123 StringRef RegAllocPriorityAdvisorAnalysis::getPassName() const {
124 switch (getAdvisorMode()) {
125 case AdvisorMode::Default:
126 return "Default Regalloc Priority Advisor";
127 case AdvisorMode::Release:
128 return "Release mode Regalloc Priority Advisor";
129 case AdvisorMode::Development:
130 return "Development mode Regalloc Priority Advisor";
131 case AdvisorMode::Dummy:
132 return "Dummy Regalloc Priority Advisor";
134 llvm_unreachable("Unknown advisor kind");
137 RegAllocPriorityAdvisor::RegAllocPriorityAdvisor(const MachineFunction &MF,
138 const RAGreedy &RA,
139 SlotIndexes *const Indexes)
140 : RA(RA), LIS(RA.getLiveIntervals()), VRM(RA.getVirtRegMap()),
141 MRI(&VRM->getRegInfo()), TRI(MF.getSubtarget().getRegisterInfo()),
142 RegClassInfo(RA.getRegClassInfo()), Indexes(Indexes),
143 RegClassPriorityTrumpsGlobalness(
144 RA.getRegClassPriorityTrumpsGlobalness()),
145 ReverseLocalAssignment(RA.getReverseLocalAssignment()) {}