Lines Matching full:pass

1 //===- Pass.cpp - Pass infrastructure implementation ----------------------===//
9 // This file implements common pass infrastructure.
13 #include "mlir/Pass/Pass.h"
40 const Pass &pass)
41 : Base(irUnits), pass(pass) {}
45 pass.getName(), getOp()->getName());
55 // Pass
60 void Pass::anchor() {}
62 /// Attempt to initialize the options of this pass from the given string.
63 LogicalResult Pass::initializeOptions(
75 /// pass.
76 void Pass::copyOptionValuesFrom(const Pass *other) {
80 /// Prints out the pass in the textual representation of pipelines. If this is
81 /// an adaptor pass, print its pass managers.
82 void Pass::printAsTextualPipeline(raw_ostream &os) {
83 // Special case for adaptors to print its pass managers.
91 // Otherwise, print the pass argument followed by its options. If the pass
92 // doesn't have an argument, print the name of the pass to give some indicator
93 // of what pass was run.
121 for (const std::unique_ptr<Pass> &pass : rhs.passes) {
122 std::unique_ptr<Pass> newPass = pass->clone();
123 newPass->threadingSibling = pass.get();
128 /// Merge the passes of this pass manager into the one provided.
131 /// Nest a new operation pass manager for the given operation kind under this
132 /// pass manager.
141 /// Nest the given pass manager under this pass manager.
144 /// Add the given pass to this pass manager. If this pass has a concrete
145 /// operation type, it must be the same type as this pass manager.
146 void addPass(std::unique_ptr<Pass> pass);
148 /// Clear the list of passes in this pass manager, other options are
152 /// Finalize the pass list in preparation for execution. This includes
153 /// coalescing adjacent pass managers when possible, verifying scheduled
157 /// Return the operation name of this pass manager.
168 /// Return the name used to anchor this pass manager. This is either the name
170 /// op-agnostic pass manager.
175 /// Indicate if the current pass manager can be scheduled on the given
179 /// The name of the operation that passes of this pass manager operate on.
183 /// operation that passes of this pass manager operate on.
186 /// The set of passes to run as part of this pass manager.
187 std::vector<std::unique_ptr<Pass>> passes;
189 /// The current initialization generation of this pass manager. This is used
190 /// to indicate when a pass manager should be reinitialized.
201 assert(name == rhs.name && "merging unrelated pass managers");
202 for (auto &pass : passes)
203 rhs.passes.push_back(std::move(pass));
209 addPass(std::unique_ptr<Pass>(adaptor));
213 void OpPassManagerImpl::addPass(std::unique_ptr<Pass> pass) {
214 // If this pass runs on a different operation than this pass manager, then
215 // implicitly nest a pass manager for this operation if enabled.
217 std::optional<StringRef> passOpName = pass->getOpName();
220 return nest(*passOpName).addPass(std::move(pass));
221 llvm::report_fatal_error(llvm::Twine("Can't add pass '") + pass->getName() +
227 passes.emplace_back(std::move(pass));
240 // Walk the pass list and merge adjacent adaptors.
242 for (auto &pass : passes) {
243 // Check to see if this pass is an adaptor.
244 if (auto *currentAdaptor = dyn_cast<OpToOpPassAdaptor>(pass.get())) {
255 pass.reset();
259 // If this pass isn't an adaptor, finalize it and forget the last adaptor.
272 llvm::erase_if(passes, std::logical_not<std::unique_ptr<Pass>>());
274 // If this is a op-agnostic pass manager, there is nothing left to do.
283 for (std::unique_ptr<Pass> &pass : passes) {
284 if (opName && !pass->canScheduleOn(*opName)) {
286 << "unable to schedule pass '" << pass->getName()
296 // If this pass manager is op-specific, we simply check if the provided
302 // Otherwise, this is an op-agnostic pass manager. Check that the operation
309 return llvm::all_of(passes, [&](const std::unique_ptr<Pass> &pass) {
310 return pass->canScheduleOn(*registeredInfo);
338 return MutableArrayRef<std::unique_ptr<Pass>>{impl->passes}.begin();
341 return MutableArrayRef<std::unique_ptr<Pass>>{impl->passes}.end();
345 return ArrayRef<std::unique_ptr<Pass>>{impl->passes}.begin();
348 return ArrayRef<std::unique_ptr<Pass>>{impl->passes}.end();
351 /// Nest a new operation pass manager for the given operation kind under this
352 /// pass manager.
361 /// Add the given pass to this pass manager. If this pass has a concrete
362 /// operation type, it must be the same type as this pass manager.
363 void OpPassManager::addPass(std::unique_ptr<Pass> pass) {
364 impl->addPass(std::move(pass));
375 /// Return the operation name that this pass manager operates on.
380 /// Return the operation name that this pass manager operates on.
390 /// Prints out the passes of the pass manager as the textual representation
397 passes, [&](mlir::Pass &pass) { pass.printAsTextualPipeline(os); },
405 {MutableArrayRef<std::unique_ptr<Pass>>{impl->passes}.begin(),
406 MutableArrayRef<std::unique_ptr<Pass>>{impl->passes}.end()});
410 llvm::errs() << "Pass Manager with " << impl->passes.size() << " passes:\n";
417 for (const Pass &pass : pm.getPasses())
418 pass.getDependentDialects(dialects);
434 for (Pass &pass : getPasses()) {
435 // If this pass isn't an adaptor, directly initialize it.
436 auto *adaptor = dyn_cast<OpToOpPassAdaptor>(&pass);
438 if (failed(pass.initialize(context)))
443 // Otherwise, initialize each of the adaptors pass managers.
453 for (Pass &pass : getPasses()) {
454 // If this pass isn't an adaptor, directly hash it.
455 auto *adaptor = dyn_cast<OpToOpPassAdaptor>(&pass);
457 hashCode = llvm::hash_combine(hashCode, &pass);
460 // Otherwise, hash recursively each of the adaptors pass managers.
472 LogicalResult OpToOpPassAdaptor::run(Pass *pass, Operation *op,
478 << "trying to schedule a pass on an unregistered operation";
480 return op->emitOpError() << "trying to schedule a pass on an operation not "
482 if (!pass->canScheduleOn(*op->getName().getRegisteredInfo()))
484 << "trying to schedule a pass on an unsupported operation";
486 // Initialize the pass state with a callback for the pass to dynamically
490 pass};
497 "nested under the current operation the pass is processing";
513 pass->passState.emplace(op, am, dynamicPipelineCallback);
515 // Instrument before the pass has run.
517 pi->runBeforePass(pass, op);
523 if (auto *adaptor = dyn_cast<OpToOpPassAdaptor>(pass))
526 pass->runOnOperation();
527 passFailed = pass->passState->irAndPassFailed.getInt();
529 {op}, *pass);
532 am.invalidate(pass->passState->preservedAnalyses);
534 // When verifyPasses is specified, we run the verifier (unless the pass
539 // If the pass is an adaptor pass, we don't run the verifier recursively
542 bool runVerifierRecursively = !isa<OpToOpPassAdaptor>(pass);
544 // Reduce compile time by avoiding running the verifier if the pass didn't
547 // 1) If the pass said that it preserved all analyses then it can't have
552 runVerifierNow = !pass->passState->preservedAnalyses.isAll();
558 // Instrument after the pass has run.
561 pi->runAfterPassFailed(pass, op);
563 pi->runAfterPass(pass, op);
566 // Return if the pass signaled a failure.
570 /// Run the given operation and analysis manager on a provided op pass manager.
591 for (Pass &pass : pm.getPasses())
592 if (failed(run(&pass, op, am, verifyPasses, parentInitGeneration)))
602 /// Find an operation pass manager with the given anchor name, or nullptr if one
611 /// Find an operation pass manager that can operate on an operation of the given
633 // Functor used to check if a pass manager is generic, i.e. op-agnostic.
636 // Functor used to detect if the given generic pass manager will have a
641 // If this is a non-generic pass manager, a conflict will arise if a
642 // non-generic pass manager's operation name can be scheduled on the
646 // Otherwise, this is a generic pass manager. We current can't determine
647 // when generic pass managers can be merged, so conservatively assume they
653 // Check that if either adaptor has a generic pass manager, that pm is
654 // compatible within any non-generic pass managers.
668 // If an existing pass manager exists, then merge the given pass manager
674 // Otherwise, add the given pass manager to the list.
680 // After coalescing, sort the pass managers within rhs by name.
682 // Order op-specific pass managers first and op-agnostic pass managers last.
694 /// Returns the adaptor pass name.
707 "Unexpected call to Pass::runOnOperation() on OpToOpPassAdaptor");
718 /// Run this pass adaptor synchronously.
741 /// Utility functor that checks if the two ranges of pass managers have a size
750 /// Run this pass adaptor synchronously.
761 // scheduled on a pass manager.
766 /// The index of the pass manager to schedule the operation on.
781 // Get the pass manager index for this operation type.
811 // Get the pass manager for this operation and execute it.
819 // Reset the active bit for this pass manager.
852 << "can't run '" << getOpAnchorName() << "' pass manager on '"
862 // Before running, make sure to finalize the pipeline pass list.
869 // Initialize all of the passes within the pass manager with a new generation.
882 // If reproducer generation is enabled, run the pass manager with crash
890 // Dump all of the pass statistics if necessary.
896 /// Add the provided instrumentation to the pass manager.
1027 void PassInstrumentor::runBeforePass(Pass *pass, Operation *op) {
1030 instr->runBeforePass(pass, op);
1034 void PassInstrumentor::runAfterPass(Pass *pass, Operation *op) {
1037 instr->runAfterPass(pass, op);
1041 void PassInstrumentor::runAfterPassFailed(Pass *pass, Operation *op) {
1044 instr->runAfterPassFailed(pass, op);