Joos1W Compiler Framework
All Classes Functions Typedefs Pages
utils::PassManager Class Referencefinal

Public Member Functions

 PassManager (CLI::App &app)
 
bool Run ()
 Runs all the passes in the pass manager. More...
 
void Reset ()
 Resets the pass manager and frees all resources.
 
Pass const * LastRun () const
 
void SetHeapReuse (bool reuse)
 Sets whether the pass manager should reuse heaps.
 
 PassManager (PassManager const &)=delete
 
 PassManager (PassManager &&)=delete
 
PassManageroperator= (PassManager const &)=delete
 
PassManageroperator= (PassManager &&)=delete
 
template<typename T , typename... Args>
requires PassType< T > TAddPass (Args &&... args)
 Adds a pass to the pass manager. More...
 
diagnostics::DiagnosticEngineDiag ()
 Gets a reference to the diagnostic engine.
 
PassOptionsPO ()
 Gets the pass options.
 
template<typename T >
requires PassType< T > TFindPass ()
 Outside method to get a pass by type.
 
template<typename T >
requires PassType< T > void PreserveAnalysis ()
 Declare an analysis to be preserved forever.
 

Friends

class Pass
 
class HeapRef
 

Detailed Description

Definition at line 196 of file PassManager.h.

Member Function Documentation

◆ AddPass()

template<typename T , typename... Args>
requires PassType<T> T& utils::PassManager::AddPass ( Args &&...  args)
inline

Adds a pass to the pass manager.

Template Parameters
TThe type of the passr
Parameters
...argsThe remaining arguments to pass to the pass constructor. The pass manager will be passed to the pass as the first argument.

Definition at line 244 of file PassManager.h.

244  {
245  passes_.emplace_back(new T(*this, std::forward<Args>(args)...));
246  T& result = *cast<T*>(passes_.back().get());
247  // If the pass has a name, register it as constructible from the command
248  // line options
249  if(!result.Name().empty()) result.RegisterCLI();
250  return result;
251  }
Wraps a value for expression evaluation. This distinguishes an LValue from an RValue,...
Definition: CGExpr.h:24

◆ LastRun()

Pass const* utils::PassManager::LastRun ( ) const
inline
Returns
The last pass that was run by the pass manager

Definition at line 221 of file PassManager.h.

221 { return lastRun_; }

◆ Run()

bool utils::PassManager::Run ( )

Runs all the passes in the pass manager.

Returns
True if all passes ran successfully

Definition at line 123 of file PassManager.cc.

123  {
124  std::vector<Pass*> S;
125  std::vector<Pass*> L;
126  // 1a Propagate the enabled state
127  for(auto& pass : passes_) {
128  pass->state = Pass::PropagateEnabled;
129  pass->computeDependencies();
130  }
131  // 1b Acquire resources for the passes
132  for(auto& pass : passes_) {
133  // If the pass is disabled, then we skip it
134  if(PO().IsPassDisabled(pass.get())) continue;
135  pass->state = Pass::AcquireResources;
136  pass->Init();
137  }
138  // 1c Propagate the heap refcounts
139  for(auto& pass : passes_) {
140  if(PO().IsPassDisabled(pass.get())) continue;
141  pass->computeDependencies();
142  }
143  if(Diag().Verbose(2)) {
144  for(auto& heap : heaps_) {
145  Diag().ReportDebug(2) << "[=>] Heap Owner: \"" << heap.owner->Desc()
146  << "\" RefCount: " << heap.refCount;
147  }
148  }
149  // 2. Build the dependency graph of passes
150  size_t NumEnabledPasses = 0;
151  for(auto& pass : passes_) {
152  if(PO().IsPassDisabled(pass.get())) continue;
153  NumEnabledPasses++;
154  passDeps_[pass.get()] = 0;
155  pass->state = Pass::RegisterDependencies;
156  pass->computeDependencies();
157  // Mark the pass in the graph
158  if(passDeps_[pass.get()] == 0) S.push_back(pass.get());
159  }
160  // 3. Run topological sort on the dependency graph
161  while(!S.empty()) {
162  auto* n = *S.begin();
163  S.erase(S.begin());
164  L.push_back(n);
165  for(auto* m : depgraph_[n]) {
166  if(--passDeps_[m] == 0) S.push_back(m);
167  }
168  depgraph_[n].clear();
169  }
170  // 4. Check for cycles
171  if(L.size() != NumEnabledPasses)
172  throw utils::FatalError("Cyclic pass dependency detected");
173  // 5. Run the passes in topological order
174  for(auto& pass : L) {
175  assert(pass->state != Pass::Valid && "Pass already run");
176  pass->state = Pass::Running;
177  if(Diag().Verbose()) {
178  Diag().ReportDebug() << "[=>] Running " << pass->Desc() << " Pass";
179  }
180  pass->Run();
181  lastRun_ = pass;
182  if(Diag().hasErrors()) {
183  pass->state = Pass::Invalid;
184  return false;
185  } else if(Diag().hasWarnings()) {
186  pass->state = Pass::Invalid;
187  return false;
188  }
189  // If the pass is running, we can free the heaps by calling
190  // computeDependencies again
191  pass->state = Pass::Cleanup;
192  pass->computeDependencies();
193  // Update the pass state
194  pass->state = Pass::Valid;
195  }
196  return true;
197 }
diagnostics::DiagnosticEngine & Diag()
Gets a reference to the diagnostic engine.
Definition: PassManager.h:254
PassOptions & PO()
Gets the pass options.
Definition: PassManager.h:257

The documentation for this class was generated from the following files: