28#include <mlir/Dialect/ControlFlow/IR/ControlFlowOps.h>
29#include <mlir/Transforms/InliningUtils.h>
36template <
typename InlinerImpl,
typename DialectImpl,
typename... RequiredDialects>
39struct BaseInlinerInterface :
public DialectInlinerInterface {
41 using DialectInlinerInterface::DialectInlinerInterface;
44 static void registrationHook(MLIRContext *ctx, DialectImpl *dialect) {
45 dialect->template addInterfaces<InlinerImpl>();
46 if constexpr (
sizeof...(RequiredDialects) != 0) {
47 ctx->loadDialect<RequiredDialects...>();
53struct FuncInlinerInterface
54 :
public BaseInlinerInterface<
55 FuncInlinerInterface, function::FunctionDialect, cf::ControlFlowDialect> {
56 using BaseInlinerInterface::BaseInlinerInterface;
59 bool isLegalToInline(Operation *, Operation *,
bool)
const final {
return true; }
60 bool isLegalToInline(Operation *, Region *,
bool, IRMapping &)
const final {
return true; }
61 bool isLegalToInline(Region *, Region *,
bool, IRMapping &)
const final {
return true; }
63 void handleTerminator(Operation *op, Block *newDest)
const final {
69 if (
auto returnOp = llvm::dyn_cast<function::ReturnOp>(op)) {
70 OpBuilder builder(op);
71 cf::BranchOp::create(builder, op->getLoc(), newDest, returnOp.getOperands());
76 void handleTerminator(Operation *op, ValueRange valuesToRepl)
const final {
78 assert(llvm::isa<function::ReturnOp>(op));
81 auto returnOp = llvm::cast<function::ReturnOp>(op);
82 assert(returnOp.getNumOperands() == valuesToRepl.size());
83 for (
const auto &it : llvm::enumerate(returnOp.getOperands())) {
84 valuesToRepl[it.index()].replaceAllUsesWith(it.value());
89template <
typename DialectImpl>
90struct FullyLegalForInlining
91 :
public BaseInlinerInterface<FullyLegalForInlining<DialectImpl>, DialectImpl> {
92 using BaseInlinerInterface<FullyLegalForInlining<DialectImpl>, DialectImpl>::BaseInlinerInterface;
94 bool isLegalToInline(Operation *, Operation *,
bool)
const override {
return true; }
95 bool isLegalToInline(Region *, Region *,
bool, IRMapping &)
const override {
return true; }
96 bool isLegalToInline(Operation *, Region *,
bool, IRMapping &)
const override {
return true; }
104 registry.addExtension(FullyLegalForInlining<array::ArrayDialect>::registrationHook);
105 registry.addExtension(FullyLegalForInlining<boolean::BoolDialect>::registrationHook);
106 registry.addExtension(FullyLegalForInlining<cast::CastDialect>::registrationHook);
107 registry.addExtension(FullyLegalForInlining<component::StructDialect>::registrationHook);
108 registry.addExtension(FullyLegalForInlining<constrain::ConstrainDialect>::registrationHook);
109 registry.addExtension(FullyLegalForInlining<felt::FeltDialect>::registrationHook);
110 registry.addExtension(FullyLegalForInlining<global::GlobalDialect>::registrationHook);
111 registry.addExtension(FullyLegalForInlining<include::IncludeDialect>::registrationHook);
112 registry.addExtension(FullyLegalForInlining<llzk::LLZKDialect>::registrationHook);
113 registry.addExtension(FullyLegalForInlining<pod::PODDialect>::registrationHook);
114 registry.addExtension(FullyLegalForInlining<polymorphic::PolymorphicDialect>::registrationHook);
115 registry.addExtension(FullyLegalForInlining<ram::RAMDialect>::registrationHook);
116 registry.addExtension(FullyLegalForInlining<smt_info::SMTInfoDialect>::registrationHook);
117 registry.addExtension(FullyLegalForInlining<string::StringDialect>::registrationHook);
118 registry.addExtension(FullyLegalForInlining<verif::VerifDialect>::registrationHook);
119 registry.addExtension(FuncInlinerInterface::registrationHook);
void registerInliningExtensions(DialectRegistry ®istry)