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_PASSBUILDER_H 16#define LLVM_PASSES_PASSBUILDER_H 17 18#include "llvm/Analysis/CGSCCPassManager.h" 19#include "llvm/CodeGen/MachinePassManager.h" 20#include "llvm/IR/PassManager.h" 21#include "llvm/Passes/OptimizationLevel.h" 22#include "llvm/Support/Error.h" 23#include "llvm/Support/PGOOptions.h" 24#include "llvm/Support/raw_ostream.h" 25#include "llvm/Transforms/IPO/Inliner.h" 26#include "llvm/Transforms/IPO/ModuleInliner.h" 27#include "llvm/Transforms/Instrumentation.h" 28#include "llvm/Transforms/Scalar/LoopPassManager.h" 29#include <vector> 30 31namespace llvm { 32class StringRef; 33class AAManager; 34class TargetMachine; 35class ModuleSummaryIndex; 36template <typename T> class IntrusiveRefCntPtr; 37namespace vfs { 38class FileSystem; 39} // namespace vfs 40 41/// Tunable parameters for passes in the default pipelines. 42class PipelineTuningOptions { 43public: 44 /// Constructor sets pipeline tuning defaults based on cl::opts. Each option 45 /// can be set in the PassBuilder when using a LLVM as a library. 46 PipelineTuningOptions(); 47 48 /// Tuning option to set loop interleaving on/off, set based on opt level. 49 bool LoopInterleaving; 50 51 /// Tuning option to enable/disable loop vectorization, set based on opt 52 /// level. 53 bool LoopVectorization; 54 55 /// Tuning option to enable/disable slp loop vectorization, set based on opt 56 /// level. 57 bool SLPVectorization; 58 59 /// Tuning option to enable/disable loop unrolling. Its default value is true. 60 bool LoopUnrolling; 61 62 /// Tuning option to forget all SCEV loops in LoopUnroll. Its default value 63 /// is that of the flag: `-forget-scev-loop-unroll`. 64 bool ForgetAllSCEVInLoopUnroll; 65 66 /// Tuning option to cap the number of calls to retrive clobbering accesses in 67 /// MemorySSA, in LICM. 68 unsigned LicmMssaOptCap; 69 70 /// Tuning option to disable promotion to scalars in LICM with MemorySSA, if 71 /// the number of access is too large. 72 unsigned LicmMssaNoAccForPromotionCap; 73 74 /// Tuning option to enable/disable call graph profile. Its default value is 75 /// that of the flag: `-enable-npm-call-graph-profile`. 76 bool CallGraphProfile; 77 78 // Add LTO pipeline tuning option to enable the unified LTO pipeline. 79 bool UnifiedLTO; 80 81 /// Tuning option to enable/disable function merging. Its default value is 82 /// false. 83 bool MergeFunctions; 84 85 /// Tuning option to override the default inliner threshold. 86 int InlinerThreshold; 87 88 // Experimental option to eagerly invalidate more analyses. This has the 89 // potential to decrease max memory usage in exchange for more compile time. 90 // This may affect codegen due to either passes using analyses only when 91 // cached, or invalidating and recalculating an analysis that was 92 // stale/imprecise but still valid. Currently this invalidates all function 93 // analyses after various module->function or cgscc->function adaptors in the 94 // default pipelines. 95 bool EagerlyInvalidateAnalyses; 96}; 97 98/// This class provides access to building LLVM's passes. 99/// 100/// Its members provide the baseline state available to passes during their 101/// construction. The \c PassRegistry.def file specifies how to construct all 102/// of the built-in passes, and those may reference these members during 103/// construction. 104class PassBuilder { 105 TargetMachine *TM; 106 PipelineTuningOptions PTO; 107 std::optional<PGOOptions> PGOOpt; 108 PassInstrumentationCallbacks *PIC; 109 110public: 111 /// A struct to capture parsed pass pipeline names. 112 /// 113 /// A pipeline is defined as a series of names, each of which may in itself 114 /// recursively contain a nested pipeline. A name is either the name of a pass 115 /// (e.g. "instcombine") or the name of a pipeline type (e.g. "cgscc"). If the 116 /// name is the name of a pass, the InnerPipeline is empty, since passes 117 /// cannot contain inner pipelines. See parsePassPipeline() for a more 118 /// detailed description of the textual pipeline format. 119 struct PipelineElement { 120 StringRef Name; 121 std::vector<PipelineElement> InnerPipeline; 122 }; 123 124 explicit PassBuilder(TargetMachine *TM = nullptr, 125 PipelineTuningOptions PTO = PipelineTuningOptions(), 126 std::optional<PGOOptions> PGOOpt = std::nullopt, 127 PassInstrumentationCallbacks *PIC = nullptr); 128 129 /// Cross register the analysis managers through their proxies. 130 /// 131 /// This is an interface that can be used to cross register each 132 /// AnalysisManager with all the others analysis managers. 133 void crossRegisterProxies(LoopAnalysisManager &LAM, 134 FunctionAnalysisManager &FAM, 135 CGSCCAnalysisManager &CGAM, 136 ModuleAnalysisManager &MAM); 137 138 /// Registers all available module analysis passes. 139 /// 140 /// This is an interface that can be used to populate a \c 141 /// ModuleAnalysisManager with all registered module analyses. Callers can 142 /// still manually register any additional analyses. Callers can also 143 /// pre-register analyses and this will not override those. 144 void registerModuleAnalyses(ModuleAnalysisManager &MAM); 145 146 /// Registers all available CGSCC analysis passes. 147 /// 148 /// This is an interface that can be used to populate a \c CGSCCAnalysisManager 149 /// with all registered CGSCC analyses. Callers can still manually register any 150 /// additional analyses. Callers can also pre-register analyses and this will 151 /// not override those. 152 void registerCGSCCAnalyses(CGSCCAnalysisManager &CGAM); 153 154 /// Registers all available function analysis passes. 155 /// 156 /// This is an interface that can be used to populate a \c 157 /// FunctionAnalysisManager with all registered function analyses. Callers can 158 /// still manually register any additional analyses. Callers can also 159 /// pre-register analyses and this will not override those. 160 void registerFunctionAnalyses(FunctionAnalysisManager &FAM); 161 162 /// Registers all available loop analysis passes. 163 /// 164 /// This is an interface that can be used to populate a \c LoopAnalysisManager 165 /// with all registered loop analyses. Callers can still manually register any 166 /// additional analyses. 167 void registerLoopAnalyses(LoopAnalysisManager &LAM); 168 169 /// Registers all available machine function analysis passes. 170 /// 171 /// This is an interface that can be used to populate a \c 172 /// MachineFunctionAnalysisManager with all registered function analyses. 173 /// Callers can still manually register any additional analyses. Callers can 174 /// also pre-register analyses and this will not override those. 175 void registerMachineFunctionAnalyses(MachineFunctionAnalysisManager &MFAM); 176 177 /// Construct the core LLVM function canonicalization and simplification 178 /// pipeline. 179 /// 180 /// This is a long pipeline and uses most of the per-function optimization 181 /// passes in LLVM to canonicalize and simplify the IR. It is suitable to run 182 /// repeatedly over the IR and is not expected to destroy important 183 /// information about the semantics of the IR. 184 /// 185 /// Note that \p Level cannot be `O0` here. The pipelines produced are 186 /// only intended for use when attempting to optimize code. If frontends 187 /// require some transformations for semantic reasons, they should explicitly 188 /// build them. 189 /// 190 /// \p Phase indicates the current ThinLTO phase. 191 FunctionPassManager 192 buildFunctionSimplificationPipeline(OptimizationLevel Level, 193 ThinOrFullLTOPhase Phase); 194 195 /// Construct the core LLVM module canonicalization and simplification 196 /// pipeline. 197 /// 198 /// This pipeline focuses on canonicalizing and simplifying the entire module 199 /// of IR. Much like the function simplification pipeline above, it is 200 /// suitable to run repeatedly over the IR and is not expected to destroy 201 /// important information. It does, however, perform inlining and other 202 /// heuristic based simplifications that are not strictly reversible. 203 /// 204 /// Note that \p Level cannot be `O0` here. The pipelines produced are 205 /// only intended for use when attempting to optimize code. If frontends 206 /// require some transformations for semantic reasons, they should explicitly 207 /// build them. 208 /// 209 /// \p Phase indicates the current ThinLTO phase. 210 ModulePassManager buildModuleSimplificationPipeline(OptimizationLevel Level, 211 ThinOrFullLTOPhase Phase); 212 213 /// Construct the module pipeline that performs inlining as well as 214 /// the inlining-driven cleanups. 215 ModuleInlinerWrapperPass buildInlinerPipeline(OptimizationLevel Level, 216 ThinOrFullLTOPhase Phase); 217 218 /// Construct the module pipeline that performs inlining with 219 /// module inliner pass. 220 ModulePassManager buildModuleInlinerPipeline(OptimizationLevel Level, 221 ThinOrFullLTOPhase Phase); 222 223 /// Construct the core LLVM module optimization pipeline. 224 /// 225 /// This pipeline focuses on optimizing the execution speed of the IR. It 226 /// uses cost modeling and thresholds to balance code growth against runtime 227 /// improvements. It includes vectorization and other information destroying 228 /// transformations. It also cannot generally be run repeatedly on a module 229 /// without potentially seriously regressing either runtime performance of 230 /// the code or serious code size growth. 231 /// 232 /// Note that \p Level cannot be `O0` here. The pipelines produced are 233 /// only intended for use when attempting to optimize code. If frontends 234 /// require some transformations for semantic reasons, they should explicitly 235 /// build them. 236 ModulePassManager 237 buildModuleOptimizationPipeline(OptimizationLevel Level, 238 ThinOrFullLTOPhase LTOPhase); 239 240 /// Build a per-module default optimization pipeline. 241 /// 242 /// This provides a good default optimization pipeline for per-module 243 /// optimization and code generation without any link-time optimization. It 244 /// typically correspond to frontend "-O[123]" options for optimization 245 /// levels \c O1, \c O2 and \c O3 resp. 246 ModulePassManager buildPerModuleDefaultPipeline(OptimizationLevel Level, 247 bool LTOPreLink = false); 248 249 /// Build a fat object default optimization pipeline. 250 /// 251 /// This builds a pipeline that runs the LTO/ThinLTO pre-link pipeline, and 252 /// emits a section containing the pre-link bitcode along side the object code 253 /// generated in non-LTO compilation. 254 ModulePassManager buildFatLTODefaultPipeline(OptimizationLevel Level, 255 bool ThinLTO, bool EmitSummary); 256 257 /// Build a pre-link, ThinLTO-targeting default optimization pipeline to 258 /// a pass manager. 259 /// 260 /// This adds the pre-link optimizations tuned to prepare a module for 261 /// a ThinLTO run. It works to minimize the IR which needs to be analyzed 262 /// without making irreversible decisions which could be made better during 263 /// the LTO run. 264 ModulePassManager buildThinLTOPreLinkDefaultPipeline(OptimizationLevel Level); 265 266 /// Build an ThinLTO default optimization pipeline to a pass manager. 267 /// 268 /// This provides a good default optimization pipeline for link-time 269 /// optimization and code generation. It is particularly tuned to fit well 270 /// when IR coming into the LTO phase was first run through \c 271 /// addPreLinkLTODefaultPipeline, and the two coordinate closely. 272 ModulePassManager 273 buildThinLTODefaultPipeline(OptimizationLevel Level, 274 const ModuleSummaryIndex *ImportSummary); 275 276 /// Build a pre-link, LTO-targeting default optimization pipeline to a pass 277 /// manager. 278 /// 279 /// This adds the pre-link optimizations tuned to work well with a later LTO 280 /// run. It works to minimize the IR which needs to be analyzed without 281 /// making irreversible decisions which could be made better during the LTO 282 /// run. 283 ModulePassManager buildLTOPreLinkDefaultPipeline(OptimizationLevel Level); 284 285 /// Build an LTO default optimization pipeline to a pass manager. 286 /// 287 /// This provides a good default optimization pipeline for link-time 288 /// optimization and code generation. It is particularly tuned to fit well 289 /// when IR coming into the LTO phase was first run through \c 290 /// addPreLinkLTODefaultPipeline, and the two coordinate closely. 291 ModulePassManager buildLTODefaultPipeline(OptimizationLevel Level, 292 ModuleSummaryIndex *ExportSummary); 293 294 /// Build an O0 pipeline with the minimal semantically required passes. 295 /// 296 /// This should only be used for non-LTO and LTO pre-link pipelines. 297 ModulePassManager buildO0DefaultPipeline(OptimizationLevel Level, 298 bool LTOPreLink = false); 299 300 /// Build the default `AAManager` with the default alias analysis pipeline 301 /// registered. 302 /// 303 /// This also adds target-specific alias analyses registered via 304 /// TargetMachine::registerDefaultAliasAnalyses(). 305 AAManager buildDefaultAAPipeline(); 306 307 /// Parse a textual pass pipeline description into a \c 308 /// ModulePassManager. 309 /// 310 /// The format of the textual pass pipeline description looks something like: 311 /// 312 /// module(function(instcombine,sroa),dce,cgscc(inliner,function(...)),...) 313 /// 314 /// Pass managers have ()s describing the nest structure of passes. All passes 315 /// are comma separated. As a special shortcut, if the very first pass is not 316 /// a module pass (as a module pass manager is), this will automatically form 317 /// the shortest stack of pass managers that allow inserting that first pass. 318 /// So, assuming function passes 'fpassN', CGSCC passes 'cgpassN', and loop 319 /// passes 'lpassN', all of these are valid: 320 /// 321 /// fpass1,fpass2,fpass3 322 /// cgpass1,cgpass2,cgpass3 323 /// lpass1,lpass2,lpass3 324 /// 325 /// And they are equivalent to the following (resp.): 326 /// 327 /// module(function(fpass1,fpass2,fpass3)) 328 /// module(cgscc(cgpass1,cgpass2,cgpass3)) 329 /// module(function(loop(lpass1,lpass2,lpass3))) 330 /// 331 /// This shortcut is especially useful for debugging and testing small pass 332 /// combinations. 333 /// 334 /// The sequence of passes aren't necessarily the exact same kind of pass. 335 /// You can mix different levels implicitly if adaptor passes are defined to 336 /// make them work. For example, 337 /// 338 /// mpass1,fpass1,fpass2,mpass2,lpass1 339 /// 340 /// This pipeline uses only one pass manager: the top-level module manager. 341 /// fpass1,fpass2 and lpass1 are added into the top-level module manager 342 /// using only adaptor passes. No nested function/loop pass managers are 343 /// added. The purpose is to allow easy pass testing when the user 344 /// specifically want the pass to run under a adaptor directly. This is 345 /// preferred when a pipeline is largely of one type, but one or just a few 346 /// passes are of different types(See PassBuilder.cpp for examples). 347 Error parsePassPipeline(ModulePassManager &MPM, StringRef PipelineText); 348 349 /// {{@ Parse a textual pass pipeline description into a specific PassManager 350 /// 351 /// Automatic deduction of an appropriate pass manager stack is not supported. 352 /// For example, to insert a loop pass 'lpass' into a FunctionPassManager, 353 /// this is the valid pipeline text: 354 /// 355 /// function(lpass) 356 Error parsePassPipeline(CGSCCPassManager &CGPM, StringRef PipelineText); 357 Error parsePassPipeline(FunctionPassManager &FPM, StringRef PipelineText); 358 Error parsePassPipeline(LoopPassManager &LPM, StringRef PipelineText); 359 /// @}} 360 361 /// Parse a textual MIR pipeline into the provided \c MachineFunctionPass 362 /// manager. 363 /// The format of the textual machine pipeline is a comma separated list of 364 /// machine pass names: 365 /// 366 /// machine-funciton-pass,machine-module-pass,... 367 /// 368 /// There is no need to specify the pass nesting, and this function 369 /// currently cannot handle the pass nesting. 370 Error parsePassPipeline(MachineFunctionPassManager &MFPM, 371 StringRef PipelineText); 372 373 /// Parse a textual alias analysis pipeline into the provided AA manager. 374 /// 375 /// The format of the textual AA pipeline is a comma separated list of AA 376 /// pass names: 377 /// 378 /// basic-aa,globals-aa,... 379 /// 380 /// The AA manager is set up such that the provided alias analyses are tried 381 /// in the order specified. See the \c AAManaager documentation for details 382 /// about the logic used. This routine just provides the textual mapping 383 /// between AA names and the analyses to register with the manager. 384 /// 385 /// Returns false if the text cannot be parsed cleanly. The specific state of 386 /// the \p AA manager is unspecified if such an error is encountered and this 387 /// returns false. 388 Error parseAAPipeline(AAManager &AA, StringRef PipelineText); 389 390 /// Print pass names. 391 void printPassNames(raw_ostream &OS); 392 393 /// Register a callback for a default optimizer pipeline extension 394 /// point 395 /// 396 /// This extension point allows adding passes that perform peephole 397 /// optimizations similar to the instruction combiner. These passes will be 398 /// inserted after each instance of the instruction combiner pass. 399 void registerPeepholeEPCallback( 400 const std::function<void(FunctionPassManager &, OptimizationLevel)> &C) { 401 PeepholeEPCallbacks.push_back(C); 402 } 403 404 /// Register a callback for a default optimizer pipeline extension 405 /// point 406 /// 407 /// This extension point allows adding late loop canonicalization and 408 /// simplification passes. This is the last point in the loop optimization 409 /// pipeline before loop deletion. Each pass added 410 /// here must be an instance of LoopPass. 411 /// This is the place to add passes that can remove loops, such as target- 412 /// specific loop idiom recognition. 413 void registerLateLoopOptimizationsEPCallback( 414 const std::function<void(LoopPassManager &, OptimizationLevel)> &C) { 415 LateLoopOptimizationsEPCallbacks.push_back(C); 416 } 417 418 /// Register a callback for a default optimizer pipeline extension 419 /// point 420 /// 421 /// This extension point allows adding loop passes to the end of the loop 422 /// optimizer. 423 void registerLoopOptimizerEndEPCallback( 424 const std::function<void(LoopPassManager &, OptimizationLevel)> &C) { 425 LoopOptimizerEndEPCallbacks.push_back(C); 426 } 427 428 /// Register a callback for a default optimizer pipeline extension 429 /// point 430 /// 431 /// This extension point allows adding optimization passes after most of the 432 /// main optimizations, but before the last cleanup-ish optimizations. 433 void registerScalarOptimizerLateEPCallback( 434 const std::function<void(FunctionPassManager &, OptimizationLevel)> &C) { 435 ScalarOptimizerLateEPCallbacks.push_back(C); 436 } 437 438 /// Register a callback for a default optimizer pipeline extension 439 /// point 440 /// 441 /// This extension point allows adding CallGraphSCC passes at the end of the 442 /// main CallGraphSCC passes and before any function simplification passes run 443 /// by CGPassManager. 444 void registerCGSCCOptimizerLateEPCallback( 445 const std::function<void(CGSCCPassManager &, OptimizationLevel)> &C) { 446 CGSCCOptimizerLateEPCallbacks.push_back(C); 447 } 448 449 /// Register a callback for a default optimizer pipeline extension 450 /// point 451 /// 452 /// This extension point allows adding optimization passes before the 453 /// vectorizer and other highly target specific optimization passes are 454 /// executed. 455 void registerVectorizerStartEPCallback( 456 const std::function<void(FunctionPassManager &, OptimizationLevel)> &C) { 457 VectorizerStartEPCallbacks.push_back(C); 458 } 459 460 /// Register a callback for a default optimizer pipeline extension point. 461 /// 462 /// This extension point allows adding optimization once at the start of the 463 /// pipeline. This does not apply to 'backend' compiles (LTO and ThinLTO 464 /// link-time pipelines). 465 void registerPipelineStartEPCallback( 466 const std::function<void(ModulePassManager &, OptimizationLevel)> &C) { 467 PipelineStartEPCallbacks.push_back(C); 468 } 469 470 /// Register a callback for a default optimizer pipeline extension point. 471 /// 472 /// This extension point allows adding optimization right after passes that do 473 /// basic simplification of the input IR. 474 void registerPipelineEarlySimplificationEPCallback( 475 const std::function<void(ModulePassManager &, OptimizationLevel)> &C) { 476 PipelineEarlySimplificationEPCallbacks.push_back(C); 477 } 478 479 /// Register a callback for a default optimizer pipeline extension point 480 /// 481 /// This extension point allows adding optimizations before the function 482 /// optimization pipeline. 483 void registerOptimizerEarlyEPCallback( 484 const std::function<void(ModulePassManager &, OptimizationLevel)> &C) { 485 OptimizerEarlyEPCallbacks.push_back(C); 486 } 487 488 /// Register a callback for a default optimizer pipeline extension point 489 /// 490 /// This extension point allows adding optimizations at the very end of the 491 /// function optimization pipeline. 492 void registerOptimizerLastEPCallback( 493 const std::function<void(ModulePassManager &, OptimizationLevel)> &C) { 494 OptimizerLastEPCallbacks.push_back(C); 495 } 496 497 /// Register a callback for a default optimizer pipeline extension point 498 /// 499 /// This extension point allows adding optimizations at the start of the full 500 /// LTO pipeline. 501 void registerFullLinkTimeOptimizationEarlyEPCallback( 502 const std::function<void(ModulePassManager &, OptimizationLevel)> &C) { 503 FullLinkTimeOptimizationEarlyEPCallbacks.push_back(C); 504 } 505 506 /// Register a callback for a default optimizer pipeline extension point 507 /// 508 /// This extension point allows adding optimizations at the end of the full 509 /// LTO pipeline. 510 void registerFullLinkTimeOptimizationLastEPCallback( 511 const std::function<void(ModulePassManager &, OptimizationLevel)> &C) { 512 FullLinkTimeOptimizationLastEPCallbacks.push_back(C); 513 } 514 515 /// Register a callback for parsing an AliasAnalysis Name to populate 516 /// the given AAManager \p AA 517 void registerParseAACallback( 518 const std::function<bool(StringRef Name, AAManager &AA)> &C) { 519 AAParsingCallbacks.push_back(C); 520 } 521 522 /// {{@ Register callbacks for analysis registration with this PassBuilder 523 /// instance. 524 /// Callees register their analyses with the given AnalysisManager objects. 525 void registerAnalysisRegistrationCallback( 526 const std::function<void(CGSCCAnalysisManager &)> &C) { 527 CGSCCAnalysisRegistrationCallbacks.push_back(C); 528 } 529 void registerAnalysisRegistrationCallback( 530 const std::function<void(FunctionAnalysisManager &)> &C) { 531 FunctionAnalysisRegistrationCallbacks.push_back(C); 532 } 533 void registerAnalysisRegistrationCallback( 534 const std::function<void(LoopAnalysisManager &)> &C) { 535 LoopAnalysisRegistrationCallbacks.push_back(C); 536 } 537 void registerAnalysisRegistrationCallback( 538 const std::function<void(ModuleAnalysisManager &)> &C) { 539 ModuleAnalysisRegistrationCallbacks.push_back(C); 540 } 541 void registerAnalysisRegistrationCallback( 542 const std::function<void(MachineFunctionAnalysisManager &)> &C) { 543 MachineFunctionAnalysisRegistrationCallbacks.push_back(C); 544 } 545 /// @}} 546 547 /// {{@ Register pipeline parsing callbacks with this pass builder instance. 548 /// Using these callbacks, callers can parse both a single pass name, as well 549 /// as entire sub-pipelines, and populate the PassManager instance 550 /// accordingly. 551 void registerPipelineParsingCallback( 552 const std::function<bool(StringRef Name, CGSCCPassManager &, 553 ArrayRef<PipelineElement>)> &C) { 554 CGSCCPipelineParsingCallbacks.push_back(C); 555 } 556 void registerPipelineParsingCallback( 557 const std::function<bool(StringRef Name, FunctionPassManager &, 558 ArrayRef<PipelineElement>)> &C) { 559 FunctionPipelineParsingCallbacks.push_back(C); 560 } 561 void registerPipelineParsingCallback( 562 const std::function<bool(StringRef Name, LoopPassManager &, 563 ArrayRef<PipelineElement>)> &C) { 564 LoopPipelineParsingCallbacks.push_back(C); 565 } 566 void registerPipelineParsingCallback( 567 const std::function<bool(StringRef Name, ModulePassManager &, 568 ArrayRef<PipelineElement>)> &C) { 569 ModulePipelineParsingCallbacks.push_back(C); 570 } 571 void registerPipelineParsingCallback( 572 const std::function<bool(StringRef Name, MachineFunctionPassManager &)> 573 &C) { 574 MachinePipelineParsingCallbacks.push_back(C); 575 } 576 /// @}} 577 578 /// Register a callback for a top-level pipeline entry. 579 /// 580 /// If the PassManager type is not given at the top level of the pipeline 581 /// text, this Callback should be used to determine the appropriate stack of 582 /// PassManagers and populate the passed ModulePassManager. 583 void registerParseTopLevelPipelineCallback( 584 const std::function<bool(ModulePassManager &, ArrayRef<PipelineElement>)> 585 &C); 586 587 /// Add PGOInstrumenation passes for O0 only. 588 void addPGOInstrPassesForO0(ModulePassManager &MPM, bool RunProfileGen, 589 bool IsCS, bool AtomicCounterUpdate, 590 std::string ProfileFile, 591 std::string ProfileRemappingFile, 592 IntrusiveRefCntPtr<vfs::FileSystem> FS); 593 594 /// Returns PIC. External libraries can use this to register pass 595 /// instrumentation callbacks. 596 PassInstrumentationCallbacks *getPassInstrumentationCallbacks() const { 597 return PIC; 598 } 599 600 // Invoke the callbacks registered for the various extension points. 601 // Custom pipelines should use these to invoke the callbacks registered 602 // by TargetMachines and other clients. 603 void invokePeepholeEPCallbacks(FunctionPassManager &FPM, 604 OptimizationLevel Level); 605 void invokeLateLoopOptimizationsEPCallbacks(LoopPassManager &LPM, 606 OptimizationLevel Level); 607 void invokeLoopOptimizerEndEPCallbacks(LoopPassManager &LPM, 608 OptimizationLevel Level); 609 void invokeScalarOptimizerLateEPCallbacks(FunctionPassManager &FPM, 610 OptimizationLevel Level); 611 void invokeCGSCCOptimizerLateEPCallbacks(CGSCCPassManager &CGPM, 612 OptimizationLevel Level); 613 void invokeVectorizerStartEPCallbacks(FunctionPassManager &FPM, 614 OptimizationLevel Level); 615 void invokeOptimizerEarlyEPCallbacks(ModulePassManager &MPM, 616 OptimizationLevel Level); 617 void invokeOptimizerLastEPCallbacks(ModulePassManager &MPM, 618 OptimizationLevel Level); 619 void invokeFullLinkTimeOptimizationEarlyEPCallbacks(ModulePassManager &MPM, 620 OptimizationLevel Level); 621 void invokeFullLinkTimeOptimizationLastEPCallbacks(ModulePassManager &MPM, 622 OptimizationLevel Level); 623 void invokePipelineStartEPCallbacks(ModulePassManager &MPM, 624 OptimizationLevel Level); 625 void invokePipelineEarlySimplificationEPCallbacks(ModulePassManager &MPM, 626 OptimizationLevel Level); 627 628private: 629 // O1 pass pipeline 630 FunctionPassManager 631 buildO1FunctionSimplificationPipeline(OptimizationLevel Level, 632 ThinOrFullLTOPhase Phase); 633 634 void addRequiredLTOPreLinkPasses(ModulePassManager &MPM); 635 636 void addVectorPasses(OptimizationLevel Level, FunctionPassManager &FPM, 637 bool IsFullLTO); 638 639 static std::optional<std::vector<PipelineElement>> 640 parsePipelineText(StringRef Text); 641 642 Error parseModulePass(ModulePassManager &MPM, const PipelineElement &E); 643 Error parseCGSCCPass(CGSCCPassManager &CGPM, const PipelineElement &E); 644 Error parseFunctionPass(FunctionPassManager &FPM, const PipelineElement &E); 645 Error parseLoopPass(LoopPassManager &LPM, const PipelineElement &E); 646 Error parseMachinePass(MachineFunctionPassManager &MFPM, 647 const PipelineElement &E); 648 bool parseAAPassName(AAManager &AA, StringRef Name); 649 650 Error parseMachinePassPipeline(MachineFunctionPassManager &MFPM, 651 ArrayRef<PipelineElement> Pipeline); 652 Error parseLoopPassPipeline(LoopPassManager &LPM, 653 ArrayRef<PipelineElement> Pipeline); 654 Error parseFunctionPassPipeline(FunctionPassManager &FPM, 655 ArrayRef<PipelineElement> Pipeline); 656 Error parseCGSCCPassPipeline(CGSCCPassManager &CGPM, 657 ArrayRef<PipelineElement> Pipeline); 658 Error parseModulePassPipeline(ModulePassManager &MPM, 659 ArrayRef<PipelineElement> Pipeline); 660 661 // Adds passes to do pre-inlining and related cleanup passes before 662 // profile instrumentation/matching (to enable better context sensitivity), 663 // and for memprof to enable better matching with missing debug frames. 664 void addPreInlinerPasses(ModulePassManager &MPM, OptimizationLevel Level, 665 ThinOrFullLTOPhase LTOPhase); 666 667 void addPGOInstrPasses(ModulePassManager &MPM, OptimizationLevel Level, 668 bool RunProfileGen, bool IsCS, 669 bool AtomicCounterUpdate, std::string ProfileFile, 670 std::string ProfileRemappingFile, 671 IntrusiveRefCntPtr<vfs::FileSystem> FS); 672 673 // Extension Point callbacks 674 SmallVector<std::function<void(FunctionPassManager &, OptimizationLevel)>, 2> 675 PeepholeEPCallbacks; 676 SmallVector<std::function<void(LoopPassManager &, OptimizationLevel)>, 2> 677 LateLoopOptimizationsEPCallbacks; 678 SmallVector<std::function<void(LoopPassManager &, OptimizationLevel)>, 2> 679 LoopOptimizerEndEPCallbacks; 680 SmallVector<std::function<void(FunctionPassManager &, OptimizationLevel)>, 2> 681 ScalarOptimizerLateEPCallbacks; 682 SmallVector<std::function<void(CGSCCPassManager &, OptimizationLevel)>, 2> 683 CGSCCOptimizerLateEPCallbacks; 684 SmallVector<std::function<void(FunctionPassManager &, OptimizationLevel)>, 2> 685 VectorizerStartEPCallbacks; 686 // Module callbacks 687 SmallVector<std::function<void(ModulePassManager &, OptimizationLevel)>, 2> 688 OptimizerEarlyEPCallbacks; 689 SmallVector<std::function<void(ModulePassManager &, OptimizationLevel)>, 2> 690 OptimizerLastEPCallbacks; 691 SmallVector<std::function<void(ModulePassManager &, OptimizationLevel)>, 2> 692 FullLinkTimeOptimizationEarlyEPCallbacks; 693 SmallVector<std::function<void(ModulePassManager &, OptimizationLevel)>, 2> 694 FullLinkTimeOptimizationLastEPCallbacks; 695 SmallVector<std::function<void(ModulePassManager &, OptimizationLevel)>, 2> 696 PipelineStartEPCallbacks; 697 SmallVector<std::function<void(ModulePassManager &, OptimizationLevel)>, 2> 698 PipelineEarlySimplificationEPCallbacks; 699 700 SmallVector<std::function<void(ModuleAnalysisManager &)>, 2> 701 ModuleAnalysisRegistrationCallbacks; 702 SmallVector<std::function<bool(StringRef, ModulePassManager &, 703 ArrayRef<PipelineElement>)>, 704 2> 705 ModulePipelineParsingCallbacks; 706 SmallVector< 707 std::function<bool(ModulePassManager &, ArrayRef<PipelineElement>)>, 2> 708 TopLevelPipelineParsingCallbacks; 709 // CGSCC callbacks 710 SmallVector<std::function<void(CGSCCAnalysisManager &)>, 2> 711 CGSCCAnalysisRegistrationCallbacks; 712 SmallVector<std::function<bool(StringRef, CGSCCPassManager &, 713 ArrayRef<PipelineElement>)>, 714 2> 715 CGSCCPipelineParsingCallbacks; 716 // Function callbacks 717 SmallVector<std::function<void(FunctionAnalysisManager &)>, 2> 718 FunctionAnalysisRegistrationCallbacks; 719 SmallVector<std::function<bool(StringRef, FunctionPassManager &, 720 ArrayRef<PipelineElement>)>, 721 2> 722 FunctionPipelineParsingCallbacks; 723 // Loop callbacks 724 SmallVector<std::function<void(LoopAnalysisManager &)>, 2> 725 LoopAnalysisRegistrationCallbacks; 726 SmallVector<std::function<bool(StringRef, LoopPassManager &, 727 ArrayRef<PipelineElement>)>, 728 2> 729 LoopPipelineParsingCallbacks; 730 // AA callbacks 731 SmallVector<std::function<bool(StringRef Name, AAManager &AA)>, 2> 732 AAParsingCallbacks; 733 // Machine pass callbackcs 734 SmallVector<std::function<void(MachineFunctionAnalysisManager &)>, 2> 735 MachineFunctionAnalysisRegistrationCallbacks; 736 SmallVector<std::function<bool(StringRef, MachineFunctionPassManager &)>, 2> 737 MachinePipelineParsingCallbacks; 738}; 739 740/// This utility template takes care of adding require<> and invalidate<> 741/// passes for an analysis to a given \c PassManager. It is intended to be used 742/// during parsing of a pass pipeline when parsing a single PipelineName. 743/// When registering a new function analysis FancyAnalysis with the pass 744/// pipeline name "fancy-analysis", a matching ParsePipelineCallback could look 745/// like this: 746/// 747/// static bool parseFunctionPipeline(StringRef Name, FunctionPassManager &FPM, 748/// ArrayRef<PipelineElement> P) { 749/// if (parseAnalysisUtilityPasses<FancyAnalysis>("fancy-analysis", Name, 750/// FPM)) 751/// return true; 752/// return false; 753/// } 754template <typename AnalysisT, typename IRUnitT, typename AnalysisManagerT, 755 typename... ExtraArgTs> 756bool parseAnalysisUtilityPasses( 757 StringRef AnalysisName, StringRef PipelineName, 758 PassManager<IRUnitT, AnalysisManagerT, ExtraArgTs...> &PM) { 759 if (!PipelineName.ends_with(">")) 760 return false; 761 // See if this is an invalidate<> pass name 762 if (PipelineName.starts_with("invalidate<")) { 763 PipelineName = PipelineName.substr(11, PipelineName.size() - 12); 764 if (PipelineName != AnalysisName) 765 return false; 766 PM.addPass(InvalidateAnalysisPass<AnalysisT>()); 767 return true; 768 } 769 770 // See if this is a require<> pass name 771 if (PipelineName.starts_with("require<")) { 772 PipelineName = PipelineName.substr(8, PipelineName.size() - 9); 773 if (PipelineName != AnalysisName) 774 return false; 775 PM.addPass(RequireAnalysisPass<AnalysisT, IRUnitT, AnalysisManagerT, 776 ExtraArgTs...>()); 777 return true; 778 } 779 780 return false; 781} 782 783// These are special since they are only for testing purposes. 784 785/// No-op module pass which does nothing. 786struct NoOpModulePass : PassInfoMixin<NoOpModulePass> { 787 PreservedAnalyses run(Module &M, ModuleAnalysisManager &) { 788 return PreservedAnalyses::all(); 789 } 790}; 791 792/// No-op module analysis. 793class NoOpModuleAnalysis : public AnalysisInfoMixin<NoOpModuleAnalysis> { 794 friend AnalysisInfoMixin<NoOpModuleAnalysis>; 795 static AnalysisKey Key; 796 797public: 798 struct Result {}; 799 Result run(Module &, ModuleAnalysisManager &) { return Result(); } 800}; 801 802/// No-op CGSCC pass which does nothing. 803struct NoOpCGSCCPass : PassInfoMixin<NoOpCGSCCPass> { 804 PreservedAnalyses run(LazyCallGraph::SCC &C, CGSCCAnalysisManager &, 805 LazyCallGraph &, CGSCCUpdateResult &UR) { 806 return PreservedAnalyses::all(); 807 } 808}; 809 810/// No-op CGSCC analysis. 811class NoOpCGSCCAnalysis : public AnalysisInfoMixin<NoOpCGSCCAnalysis> { 812 friend AnalysisInfoMixin<NoOpCGSCCAnalysis>; 813 static AnalysisKey Key; 814 815public: 816 struct Result {}; 817 Result run(LazyCallGraph::SCC &, CGSCCAnalysisManager &, LazyCallGraph &G) { 818 return Result(); 819 } 820}; 821 822/// No-op function pass which does nothing. 823struct NoOpFunctionPass : PassInfoMixin<NoOpFunctionPass> { 824 PreservedAnalyses run(Function &F, FunctionAnalysisManager &) { 825 return PreservedAnalyses::all(); 826 } 827}; 828 829/// No-op function analysis. 830class NoOpFunctionAnalysis : public AnalysisInfoMixin<NoOpFunctionAnalysis> { 831 friend AnalysisInfoMixin<NoOpFunctionAnalysis>; 832 static AnalysisKey Key; 833 834public: 835 struct Result {}; 836 Result run(Function &, FunctionAnalysisManager &) { return Result(); } 837}; 838 839/// No-op loop nest pass which does nothing. 840struct NoOpLoopNestPass : PassInfoMixin<NoOpLoopNestPass> { 841 PreservedAnalyses run(LoopNest &L, LoopAnalysisManager &, 842 LoopStandardAnalysisResults &, LPMUpdater &) { 843 return PreservedAnalyses::all(); 844 } 845}; 846 847/// No-op loop pass which does nothing. 848struct NoOpLoopPass : PassInfoMixin<NoOpLoopPass> { 849 PreservedAnalyses run(Loop &L, LoopAnalysisManager &, 850 LoopStandardAnalysisResults &, LPMUpdater &) { 851 return PreservedAnalyses::all(); 852 } 853}; 854 855/// No-op loop analysis. 856class NoOpLoopAnalysis : public AnalysisInfoMixin<NoOpLoopAnalysis> { 857 friend AnalysisInfoMixin<NoOpLoopAnalysis>; 858 static AnalysisKey Key; 859 860public: 861 struct Result {}; 862 Result run(Loop &, LoopAnalysisManager &, LoopStandardAnalysisResults &) { 863 return Result(); 864 } 865}; 866} 867 868#endif 869