1 | //===-- mlir-c/Pass.h - C API to Pass Management ------------------*- C -*-===// |
2 | // |
3 | // Part of the LLVM Project, under the Apache License v2.0 with LLVM |
4 | // Exceptions. |
5 | // See https://llvm.org/LICENSE.txt for license information. |
6 | // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception |
7 | // |
8 | //===----------------------------------------------------------------------===// |
9 | // |
10 | // This header declares the C interface to MLIR pass manager. |
11 | // |
12 | //===----------------------------------------------------------------------===// |
13 | |
14 | #ifndef MLIR_C_PASS_H |
15 | #define MLIR_C_PASS_H |
16 | |
17 | #include "mlir-c/IR.h" |
18 | #include "mlir-c/Support.h" |
19 | |
20 | #ifdef __cplusplus |
21 | extern "C" { |
22 | #endif |
23 | |
24 | //===----------------------------------------------------------------------===// |
25 | // Opaque type declarations. |
26 | // |
27 | // Types are exposed to C bindings as structs containing opaque pointers. They |
28 | // are not supposed to be inspected from C. This allows the underlying |
29 | // representation to change without affecting the API users. The use of structs |
30 | // instead of typedefs enables some type safety as structs are not implicitly |
31 | // convertible to each other. |
32 | // |
33 | // Instances of these types may or may not own the underlying object. The |
34 | // ownership semantics is defined by how an instance of the type was obtained. |
35 | //===----------------------------------------------------------------------===// |
36 | |
37 | #define DEFINE_C_API_STRUCT(name, storage) \ |
38 | struct name { \ |
39 | storage *ptr; \ |
40 | }; \ |
41 | typedef struct name name |
42 | |
43 | DEFINE_C_API_STRUCT(MlirPass, void); |
44 | DEFINE_C_API_STRUCT(MlirExternalPass, void); |
45 | DEFINE_C_API_STRUCT(MlirPassManager, void); |
46 | DEFINE_C_API_STRUCT(MlirOpPassManager, void); |
47 | |
48 | #undef DEFINE_C_API_STRUCT |
49 | |
50 | //===----------------------------------------------------------------------===// |
51 | // PassManager/OpPassManager APIs. |
52 | //===----------------------------------------------------------------------===// |
53 | |
54 | /// Create a new top-level PassManager with the default anchor. |
55 | MLIR_CAPI_EXPORTED MlirPassManager mlirPassManagerCreate(MlirContext ctx); |
56 | |
57 | /// Create a new top-level PassManager anchored on `anchorOp`. |
58 | MLIR_CAPI_EXPORTED MlirPassManager |
59 | mlirPassManagerCreateOnOperation(MlirContext ctx, MlirStringRef anchorOp); |
60 | |
61 | /// Destroy the provided PassManager. |
62 | MLIR_CAPI_EXPORTED void mlirPassManagerDestroy(MlirPassManager passManager); |
63 | |
64 | /// Checks if a PassManager is null. |
65 | static inline bool mlirPassManagerIsNull(MlirPassManager passManager) { |
66 | return !passManager.ptr; |
67 | } |
68 | |
69 | /// Cast a top-level PassManager to a generic OpPassManager. |
70 | MLIR_CAPI_EXPORTED MlirOpPassManager |
71 | mlirPassManagerGetAsOpPassManager(MlirPassManager passManager); |
72 | |
73 | /// Run the provided `passManager` on the given `op`. |
74 | MLIR_CAPI_EXPORTED MlirLogicalResult |
75 | mlirPassManagerRunOnOp(MlirPassManager passManager, MlirOperation op); |
76 | |
77 | /// Enable mlir-print-ir-after-all. |
78 | MLIR_CAPI_EXPORTED void |
79 | mlirPassManagerEnableIRPrinting(MlirPassManager passManager); |
80 | |
81 | /// Enable / disable verify-each. |
82 | MLIR_CAPI_EXPORTED void |
83 | mlirPassManagerEnableVerifier(MlirPassManager passManager, bool enable); |
84 | |
85 | /// Nest an OpPassManager under the top-level PassManager, the nested |
86 | /// passmanager will only run on operations matching the provided name. |
87 | /// The returned OpPassManager will be destroyed when the parent is destroyed. |
88 | /// To further nest more OpPassManager under the newly returned one, see |
89 | /// `mlirOpPassManagerNest` below. |
90 | MLIR_CAPI_EXPORTED MlirOpPassManager mlirPassManagerGetNestedUnder( |
91 | MlirPassManager passManager, MlirStringRef operationName); |
92 | |
93 | /// Nest an OpPassManager under the provided OpPassManager, the nested |
94 | /// passmanager will only run on operations matching the provided name. |
95 | /// The returned OpPassManager will be destroyed when the parent is destroyed. |
96 | MLIR_CAPI_EXPORTED MlirOpPassManager mlirOpPassManagerGetNestedUnder( |
97 | MlirOpPassManager passManager, MlirStringRef operationName); |
98 | |
99 | /// Add a pass and transfer ownership to the provided top-level mlirPassManager. |
100 | /// If the pass is not a generic operation pass or a ModulePass, a new |
101 | /// OpPassManager is implicitly nested under the provided PassManager. |
102 | MLIR_CAPI_EXPORTED void mlirPassManagerAddOwnedPass(MlirPassManager passManager, |
103 | MlirPass pass); |
104 | |
105 | /// Add a pass and transfer ownership to the provided mlirOpPassManager. If the |
106 | /// pass is not a generic operation pass or matching the type of the provided |
107 | /// PassManager, a new OpPassManager is implicitly nested under the provided |
108 | /// PassManager. |
109 | MLIR_CAPI_EXPORTED void |
110 | mlirOpPassManagerAddOwnedPass(MlirOpPassManager passManager, MlirPass pass); |
111 | |
112 | /// Parse a sequence of textual MLIR pass pipeline elements and add them to the |
113 | /// provided OpPassManager. If parsing fails an error message is reported using |
114 | /// the provided callback. |
115 | MLIR_CAPI_EXPORTED MlirLogicalResult mlirOpPassManagerAddPipeline( |
116 | MlirOpPassManager passManager, MlirStringRef pipelineElements, |
117 | MlirStringCallback callback, void *userData); |
118 | |
119 | /// Print a textual MLIR pass pipeline by sending chunks of the string |
120 | /// representation and forwarding `userData to `callback`. Note that the |
121 | /// callback may be called several times with consecutive chunks of the string. |
122 | MLIR_CAPI_EXPORTED void mlirPrintPassPipeline(MlirOpPassManager passManager, |
123 | MlirStringCallback callback, |
124 | void *userData); |
125 | |
126 | /// Parse a textual MLIR pass pipeline and assign it to the provided |
127 | /// OpPassManager. If parsing fails an error message is reported using the |
128 | /// provided callback. |
129 | MLIR_CAPI_EXPORTED MlirLogicalResult |
130 | mlirParsePassPipeline(MlirOpPassManager passManager, MlirStringRef pipeline, |
131 | MlirStringCallback callback, void *userData); |
132 | |
133 | //===----------------------------------------------------------------------===// |
134 | // External Pass API. |
135 | // |
136 | // This API allows to define passes outside of MLIR, not necessarily in |
137 | // C++, and register them with the MLIR pass management infrastructure. |
138 | // |
139 | //===----------------------------------------------------------------------===// |
140 | |
141 | /// Structure of external `MlirPass` callbacks. |
142 | /// All callbacks are required to be set unless otherwise specified. |
143 | struct MlirExternalPassCallbacks { |
144 | /// This callback is called from the pass is created. |
145 | /// This is analogous to a C++ pass constructor. |
146 | void (*construct)(void *userData); |
147 | |
148 | /// This callback is called when the pass is destroyed |
149 | /// This is analogous to a C++ pass destructor. |
150 | void (*destruct)(void *userData); |
151 | |
152 | /// This callback is optional. |
153 | /// The callback is called before the pass is run, allowing a chance to |
154 | /// initialize any complex state necessary for running the pass. |
155 | /// See Pass::initialize(MLIRContext *). |
156 | MlirLogicalResult (*initialize)(MlirContext ctx, void *userData); |
157 | |
158 | /// This callback is called when the pass is cloned. |
159 | /// See Pass::clonePass(). |
160 | void *(*clone)(void *userData); |
161 | |
162 | /// This callback is called when the pass is run. |
163 | /// See Pass::runOnOperation(). |
164 | void (*run)(MlirOperation op, MlirExternalPass pass, void *userData); |
165 | }; |
166 | typedef struct MlirExternalPassCallbacks MlirExternalPassCallbacks; |
167 | |
168 | /// Creates an external `MlirPass` that calls the supplied `callbacks` using the |
169 | /// supplied `userData`. If `opName` is empty, the pass is a generic operation |
170 | /// pass. Otherwise it is an operation pass specific to the specified pass name. |
171 | MLIR_CAPI_EXPORTED MlirPass mlirCreateExternalPass( |
172 | MlirTypeID passID, MlirStringRef name, MlirStringRef argument, |
173 | MlirStringRef description, MlirStringRef opName, |
174 | intptr_t nDependentDialects, MlirDialectHandle *dependentDialects, |
175 | MlirExternalPassCallbacks callbacks, void *userData); |
176 | |
177 | /// This signals that the pass has failed. This is only valid to call during |
178 | /// the `run` callback of `MlirExternalPassCallbacks`. |
179 | /// See Pass::signalPassFailure(). |
180 | MLIR_CAPI_EXPORTED void mlirExternalPassSignalFailure(MlirExternalPass pass); |
181 | |
182 | #ifdef __cplusplus |
183 | } |
184 | #endif |
185 | |
186 | #endif // MLIR_C_PASS_H |
187 | |