99#ifndef LLVM_CODEGEN_REGALLOCEVICTIONADVISOR_H
1010#define LLVM_CODEGEN_REGALLOCEVICTIONADVISOR_H
1111
12+ #include " llvm/ADT/Any.h"
1213#include " llvm/ADT/ArrayRef.h"
1314#include " llvm/ADT/SmallSet.h"
1415#include " llvm/ADT/StringRef.h"
1516#include " llvm/CodeGen/Register.h"
1617#include " llvm/Config/llvm-config.h"
18+ #include " llvm/IR/PassManager.h"
1719#include " llvm/MC/MCRegister.h"
1820#include " llvm/Pass.h"
1921
@@ -164,20 +166,20 @@ class RegAllocEvictionAdvisor {
164166// /
165167// / Because we need to offer additional services in 'development' mode, the
166168// / implementations of this analysis need to implement RTTI support.
167- class RegAllocEvictionAdvisorAnalysis : public ImmutablePass {
169+ class RegAllocEvictionAdvisorAnalysisLegacy : public ImmutablePass {
168170public:
169171 enum class AdvisorMode : int { Default, Release, Development };
170172
171- RegAllocEvictionAdvisorAnalysis (AdvisorMode Mode)
172- : ImmutablePass(ID), Mode(Mode){};
173+ RegAllocEvictionAdvisorAnalysisLegacy (AdvisorMode Mode)
174+ : ImmutablePass(ID), Mode(Mode) {};
173175 static char ID;
174176
175177 // / Get an advisor for the given context (i.e. machine function, etc)
176178 virtual std::unique_ptr<RegAllocEvictionAdvisor>
177179 getAdvisor (const MachineFunction &MF, const RAGreedy &RA) = 0 ;
178180 AdvisorMode getAdvisorMode () const { return Mode; }
179181 virtual void logRewardIfNeeded (const MachineFunction &MF,
180- llvm::function_ref<float ()> GetReward){};
182+ llvm::function_ref<float ()> GetReward) {};
181183
182184protected:
183185 // This analysis preserves everything, and subclasses may have additional
@@ -191,13 +193,66 @@ class RegAllocEvictionAdvisorAnalysis : public ImmutablePass {
191193 const AdvisorMode Mode;
192194};
193195
196+ // / Common provider for legacy and new pass managers.
197+ // / This keeps the state for logging, and sets up and holds the provider.
198+ // / The legacy pass itself used to keep the logging state and provider,
199+ // / so this extraction helps the NPM analysis to reuse the logic.
200+ class RegAllocEvictionAdvisorProvider {
201+ public:
202+ enum class AdvisorMode : int { Default, Release, Development };
203+ RegAllocEvictionAdvisorProvider (AdvisorMode Mode) : Mode(Mode) {}
204+
205+ virtual ~RegAllocEvictionAdvisorProvider () = default ;
206+
207+ virtual bool doInitialization (Module &M) { return false ; }
208+
209+ virtual void logRewardIfNeeded (const MachineFunction &MF,
210+ llvm::function_ref<float ()> GetReward) {}
211+
212+ virtual std::unique_ptr<RegAllocEvictionAdvisor>
213+ getAdvisor (const MachineFunction &MF, const RAGreedy &RA) = 0 ;
214+
215+ // / Set the analyses that the advisor needs to use as they might not be
216+ // / available before the advisor is created.
217+ virtual void setAnalyses (std::initializer_list<llvm::Any> AnalysisP) {}
218+
219+ AdvisorMode getAdvisorMode () const { return Mode; }
220+
221+ private:
222+ const AdvisorMode Mode;
223+ };
224+
225+ RegAllocEvictionAdvisorProvider *createReleaseModeAdvisorProvider ();
226+ RegAllocEvictionAdvisorProvider *createDevelopmentModeAdvisorProvider ();
227+
228+ // / A Module analysis for fetching the Eviction Advisor. This is not a
229+ // / MachineFunction analysis for two reasons:
230+ // / - in the ML implementation case, the evaluator is stateless but (especially
231+ // / in the development mode) expensive to set up. With a Module Analysis, we
232+ // / `require` it and set it up once.
233+ // / - in the 'development' mode ML case, we want to capture the training log
234+ // / during allocation (this is a log of features encountered and decisions
235+ // / made), and then measure a score, potentially a few steps after allocation
236+ // / completes. So we need a Module analysis to keep the logger state around
237+ // / until we can make that measurement.
238+ class RegAllocEvictionAdvisorAnalysis
239+ : public AnalysisInfoMixin<RegAllocEvictionAdvisorAnalysis> {
240+ static AnalysisKey Key;
241+ friend AnalysisInfoMixin<RegAllocEvictionAdvisorAnalysis>;
242+
243+ public:
244+ using Result = std::unique_ptr<RegAllocEvictionAdvisorProvider>;
245+ Result run (Module &MF, ModuleAnalysisManager &MAM);
246+ };
247+
194248// / Specialization for the API used by the analysis infrastructure to create
195249// / an instance of the eviction advisor.
196- template <> Pass *callDefaultCtor<RegAllocEvictionAdvisorAnalysis >();
250+ template <> Pass *callDefaultCtor<RegAllocEvictionAdvisorAnalysisLegacy >();
197251
198- RegAllocEvictionAdvisorAnalysis * createReleaseModeAdvisor ();
252+ RegAllocEvictionAdvisorAnalysisLegacy * createReleaseModeAdvisorAnalysisLegacy ();
199253
200- RegAllocEvictionAdvisorAnalysis *createDevelopmentModeAdvisor ();
254+ RegAllocEvictionAdvisorAnalysisLegacy *
255+ createDevelopmentModeAdvisorAnalysisLegacy ();
201256
202257// TODO: move to RegAllocEvictionAdvisor.cpp when we move implementation
203258// out of RegAllocGreedy.cpp
0 commit comments