MLIR  18.0.0git
IRModule.h
Go to the documentation of this file.
1 //===- IRModules.h - IR Submodules of pybind module -----------------------===//
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 
9 #ifndef MLIR_BINDINGS_PYTHON_IRMODULES_H
10 #define MLIR_BINDINGS_PYTHON_IRMODULES_H
11 
12 #include <optional>
13 #include <utility>
14 #include <vector>
15 
16 #include "Globals.h"
17 #include "PybindUtils.h"
18 
19 #include "mlir-c/AffineExpr.h"
20 #include "mlir-c/AffineMap.h"
21 #include "mlir-c/Diagnostics.h"
22 #include "mlir-c/IR.h"
23 #include "mlir-c/IntegerSet.h"
25 #include "llvm/ADT/DenseMap.h"
26 
27 namespace mlir {
28 namespace python {
29 
30 class PyBlock;
31 class PyDiagnostic;
32 class PyDiagnosticHandler;
33 class PyInsertionPoint;
34 class PyLocation;
35 class DefaultingPyLocation;
36 class PyMlirContext;
37 class DefaultingPyMlirContext;
38 class PyModule;
39 class PyOperation;
40 class PyType;
41 class PySymbolTable;
42 class PyValue;
43 
44 /// Template for a reference to a concrete type which captures a python
45 /// reference to its underlying python object.
46 template <typename T>
47 class PyObjectRef {
48 public:
49  PyObjectRef(T *referrent, pybind11::object object)
50  : referrent(referrent), object(std::move(object)) {
51  assert(this->referrent &&
52  "cannot construct PyObjectRef with null referrent");
53  assert(this->object && "cannot construct PyObjectRef with null object");
54  }
56  : referrent(other.referrent), object(std::move(other.object)) {
57  other.referrent = nullptr;
58  assert(!other.object);
59  }
60  PyObjectRef(const PyObjectRef &other)
61  : referrent(other.referrent), object(other.object /* copies */) {}
62  ~PyObjectRef() = default;
63 
64  int getRefCount() {
65  if (!object)
66  return 0;
67  return object.ref_count();
68  }
69 
70  /// Releases the object held by this instance, returning it.
71  /// This is the proper thing to return from a function that wants to return
72  /// the reference. Note that this does not work from initializers.
73  pybind11::object releaseObject() {
74  assert(referrent && object);
75  referrent = nullptr;
76  auto stolen = std::move(object);
77  return stolen;
78  }
79 
80  T *get() { return referrent; }
81  T *operator->() {
82  assert(referrent && object);
83  return referrent;
84  }
85  pybind11::object getObject() {
86  assert(referrent && object);
87  return object;
88  }
89  operator bool() const { return referrent && object; }
90 
91 private:
92  T *referrent;
93  pybind11::object object;
94 };
95 
96 /// Tracks an entry in the thread context stack. New entries are pushed onto
97 /// here for each with block that activates a new InsertionPoint, Context or
98 /// Location.
99 ///
100 /// Pushing either a Location or InsertionPoint also pushes its associated
101 /// Context. Pushing a Context will not modify the Location or InsertionPoint
102 /// unless if they are from a different context, in which case, they are
103 /// cleared.
105 public:
106  enum class FrameKind {
107  Context,
109  Location,
110  };
111 
112  PyThreadContextEntry(FrameKind frameKind, pybind11::object context,
113  pybind11::object insertionPoint,
114  pybind11::object location)
115  : context(std::move(context)), insertionPoint(std::move(insertionPoint)),
116  location(std::move(location)), frameKind(frameKind) {}
117 
118  /// Gets the top of stack context and return nullptr if not defined.
120 
121  /// Gets the top of stack insertion point and return nullptr if not defined.
123 
124  /// Gets the top of stack location and returns nullptr if not defined.
125  static PyLocation *getDefaultLocation();
126 
130  FrameKind getFrameKind() { return frameKind; }
131 
132  /// Stack management.
134  static pybind11::object pushContext(PyMlirContext &context);
135  static void popContext(PyMlirContext &context);
136  static pybind11::object pushInsertionPoint(PyInsertionPoint &insertionPoint);
137  static void popInsertionPoint(PyInsertionPoint &insertionPoint);
138  static pybind11::object pushLocation(PyLocation &location);
139  static void popLocation(PyLocation &location);
140 
141  /// Gets the thread local stack.
142  static std::vector<PyThreadContextEntry> &getStack();
143 
144 private:
145  static void push(FrameKind frameKind, pybind11::object context,
146  pybind11::object insertionPoint, pybind11::object location);
147 
148  /// An object reference to the PyContext.
149  pybind11::object context;
150  /// An object reference to the current insertion point.
151  pybind11::object insertionPoint;
152  /// An object reference to the current location.
153  pybind11::object location;
154  // The kind of push that was performed.
155  FrameKind frameKind;
156 };
157 
158 /// Wrapper around MlirContext.
161 public:
162  PyMlirContext() = delete;
163  PyMlirContext(const PyMlirContext &) = delete;
165 
166  /// For the case of a python __init__ (py::init) method, pybind11 is quite
167  /// strict about needing to return a pointer that is not yet associated to
168  /// an py::object. Since the forContext() method acts like a pool, possibly
169  /// returning a recycled context, it does not satisfy this need. The usual
170  /// way in python to accomplish such a thing is to override __new__, but
171  /// that is also not supported by pybind11. Instead, we use this entry
172  /// point which always constructs a fresh context (which cannot alias an
173  /// existing one because it is fresh).
175 
176  /// Returns a context reference for the singleton PyMlirContext wrapper for
177  /// the given context.
178  static PyMlirContextRef forContext(MlirContext context);
179  ~PyMlirContext();
180 
181  /// Accesses the underlying MlirContext.
182  MlirContext get() { return context; }
183 
184  /// Gets a strong reference to this context, which will ensure it is kept
185  /// alive for the life of the reference.
187  return PyMlirContextRef(this, pybind11::cast(this));
188  }
189 
190  /// Gets a capsule wrapping the void* within the MlirContext.
191  pybind11::object getCapsule();
192 
193  /// Creates a PyMlirContext from the MlirContext wrapped by a capsule.
194  /// Note that PyMlirContext instances are uniqued, so the returned object
195  /// may be a pre-existing object. Ownership of the underlying MlirContext
196  /// is taken by calling this function.
197  static pybind11::object createFromCapsule(pybind11::object capsule);
198 
199  /// Gets the count of live context objects. Used for testing.
200  static size_t getLiveCount();
201 
202  /// Gets the count of live operations associated with this context.
203  /// Used for testing.
204  size_t getLiveOperationCount();
205 
206  /// Clears the live operations map, returning the number of entries which were
207  /// invalidated. To be used as a safety mechanism so that API end-users can't
208  /// corrupt by holding references they shouldn't have accessed in the first
209  /// place.
210  size_t clearLiveOperations();
211 
212  /// Gets the count of live modules associated with this context.
213  /// Used for testing.
214  size_t getLiveModuleCount();
215 
216  /// Enter and exit the context manager.
217  pybind11::object contextEnter();
218  void contextExit(const pybind11::object &excType,
219  const pybind11::object &excVal,
220  const pybind11::object &excTb);
221 
222  /// Attaches a Python callback as a diagnostic handler, returning a
223  /// registration object (internally a PyDiagnosticHandler).
224  pybind11::object attachDiagnosticHandler(pybind11::object callback);
225 
226  /// Controls whether error diagnostics should be propagated to diagnostic
227  /// handlers, instead of being captured by `ErrorCapture`.
228  void setEmitErrorDiagnostics(bool value) { emitErrorDiagnostics = value; }
229  struct ErrorCapture;
230 
231 private:
232  PyMlirContext(MlirContext context);
233  // Interns the mapping of live MlirContext::ptr to PyMlirContext instances,
234  // preserving the relationship that an MlirContext maps to a single
235  // PyMlirContext wrapper. This could be replaced in the future with an
236  // extension mechanism on the MlirContext for stashing user pointers.
237  // Note that this holds a handle, which does not imply ownership.
238  // Mappings will be removed when the context is destructed.
239  using LiveContextMap = llvm::DenseMap<void *, PyMlirContext *>;
240  static LiveContextMap &getLiveContexts();
241 
242  // Interns all live modules associated with this context. Modules tracked
243  // in this map are valid. When a module is invalidated, it is removed
244  // from this map, and while it still exists as an instance, any
245  // attempt to access it will raise an error.
246  using LiveModuleMap =
248  LiveModuleMap liveModules;
249 
250  // Interns all live operations associated with this context. Operations
251  // tracked in this map are valid. When an operation is invalidated, it is
252  // removed from this map, and while it still exists as an instance, any
253  // attempt to access it will raise an error.
254  using LiveOperationMap =
256  LiveOperationMap liveOperations;
257 
258  bool emitErrorDiagnostics = false;
259 
260  MlirContext context;
261  friend class PyModule;
262  friend class PyOperation;
263 };
264 
265 /// Used in function arguments when None should resolve to the current context
266 /// manager set instance.
268  : public Defaulting<DefaultingPyMlirContext, PyMlirContext> {
269 public:
271  static constexpr const char kTypeDescription[] = "mlir.ir.Context";
272  static PyMlirContext &resolve();
273 };
274 
275 /// Base class for all objects that directly or indirectly depend on an
276 /// MlirContext. The lifetime of the context will extend at least to the
277 /// lifetime of these instances.
278 /// Immutable objects that depend on a context extend this directly.
280 public:
281  BaseContextObject(PyMlirContextRef ref) : contextRef(std::move(ref)) {
282  assert(this->contextRef &&
283  "context object constructed with null context ref");
284  }
285 
286  /// Accesses the context reference.
287  PyMlirContextRef &getContext() { return contextRef; }
288 
289 private:
290  PyMlirContextRef contextRef;
291 };
292 
293 /// Wrapper around an MlirLocation.
295 public:
296  PyLocation(PyMlirContextRef contextRef, MlirLocation loc)
297  : BaseContextObject(std::move(contextRef)), loc(loc) {}
298 
299  operator MlirLocation() const { return loc; }
300  MlirLocation get() const { return loc; }
301 
302  /// Enter and exit the context manager.
303  pybind11::object contextEnter();
304  void contextExit(const pybind11::object &excType,
305  const pybind11::object &excVal,
306  const pybind11::object &excTb);
307 
308  /// Gets a capsule wrapping the void* within the MlirLocation.
309  pybind11::object getCapsule();
310 
311  /// Creates a PyLocation from the MlirLocation wrapped by a capsule.
312  /// Note that PyLocation instances are uniqued, so the returned object
313  /// may be a pre-existing object. Ownership of the underlying MlirLocation
314  /// is taken by calling this function.
315  static PyLocation createFromCapsule(pybind11::object capsule);
316 
317 private:
318  MlirLocation loc;
319 };
320 
321 /// Python class mirroring the C MlirDiagnostic struct. Note that these structs
322 /// are only valid for the duration of a diagnostic callback and attempting
323 /// to access them outside of that will raise an exception. This applies to
324 /// nested diagnostics (in the notes) as well.
326 public:
327  PyDiagnostic(MlirDiagnostic diagnostic) : diagnostic(diagnostic) {}
328  void invalidate();
329  bool isValid() { return valid; }
332  pybind11::str getMessage();
333  pybind11::tuple getNotes();
334 
335  /// Materialized diagnostic information. This is safe to access outside the
336  /// diagnostic callback.
337  struct DiagnosticInfo {
340  std::string message;
341  std::vector<DiagnosticInfo> notes;
342  };
344 
345 private:
346  MlirDiagnostic diagnostic;
347 
348  void checkValid();
349  /// If notes have been materialized from the diagnostic, then this will
350  /// be populated with the corresponding objects (all castable to
351  /// PyDiagnostic).
352  std::optional<pybind11::tuple> materializedNotes;
353  bool valid = true;
354 };
355 
356 /// Represents a diagnostic handler attached to the context. The handler's
357 /// callback will be invoked with PyDiagnostic instances until the detach()
358 /// method is called or the context is destroyed. A diagnostic handler can be
359 /// the subject of a `with` block, which will detach it when the block exits.
360 ///
361 /// Since diagnostic handlers can call back into Python code which can do
362 /// unsafe things (i.e. recursively emitting diagnostics, raising exceptions,
363 /// etc), this is generally not deemed to be a great user-level API. Users
364 /// should generally use some form of DiagnosticCollector. If the handler raises
365 /// any exceptions, they will just be emitted to stderr and dropped.
366 ///
367 /// The unique usage of this class means that its lifetime management is
368 /// different from most other parts of the API. Instances are always created
369 /// in an attached state and can transition to a detached state by either:
370 /// a) The context being destroyed and unregistering all handlers.
371 /// b) An explicit call to detach().
372 /// The object may remain live from a Python perspective for an arbitrary time
373 /// after detachment, but there is nothing the user can do with it (since there
374 /// is no way to attach an existing handler object).
376 public:
377  PyDiagnosticHandler(MlirContext context, pybind11::object callback);
379 
380  bool isAttached() { return registeredID.has_value(); }
381  bool getHadError() { return hadError; }
382 
383  /// Detaches the handler. Does nothing if not attached.
384  void detach();
385 
386  pybind11::object contextEnter() { return pybind11::cast(this); }
387  void contextExit(const pybind11::object &excType,
388  const pybind11::object &excVal,
389  const pybind11::object &excTb) {
390  detach();
391  }
392 
393 private:
394  MlirContext context;
395  pybind11::object callback;
396  std::optional<MlirDiagnosticHandlerID> registeredID;
397  bool hadError = false;
398  friend class PyMlirContext;
399 };
400 
401 /// RAII object that captures any error diagnostics emitted to the provided
402 /// context.
405  : ctx(ctx), handlerID(mlirContextAttachDiagnosticHandler(
406  ctx->get(), handler, /*userData=*/this,
407  /*deleteUserData=*/nullptr)) {}
409  mlirContextDetachDiagnosticHandler(ctx->get(), handlerID);
410  assert(errors.empty() && "unhandled captured errors");
411  }
412 
413  std::vector<PyDiagnostic::DiagnosticInfo> take() {
414  return std::move(errors);
415  };
416 
417 private:
418  PyMlirContextRef ctx;
419  MlirDiagnosticHandlerID handlerID;
420  std::vector<PyDiagnostic::DiagnosticInfo> errors;
421 
422  static MlirLogicalResult handler(MlirDiagnostic diag, void *userData);
423 };
424 
425 /// Wrapper around an MlirDialect. This is exported as `DialectDescriptor` in
426 /// order to differentiate it from the `Dialect` base class which is extended by
427 /// plugins which extend dialect functionality through extension python code.
428 /// This should be seen as the "low-level" object and `Dialect` as the
429 /// high-level, user facing object.
431 public:
432  PyDialectDescriptor(PyMlirContextRef contextRef, MlirDialect dialect)
433  : BaseContextObject(std::move(contextRef)), dialect(dialect) {}
434 
435  MlirDialect get() { return dialect; }
436 
437 private:
438  MlirDialect dialect;
439 };
440 
441 /// User-level object for accessing dialects with dotted syntax such as:
442 /// ctx.dialect.std
444 public:
446  : BaseContextObject(std::move(contextRef)) {}
447 
448  MlirDialect getDialectForKey(const std::string &key, bool attrError);
449 };
450 
451 /// User-level dialect object. For dialects that have a registered extension,
452 /// this will be the base class of the extension dialect type. For un-extended,
453 /// objects of this type will be returned directly.
454 class PyDialect {
455 public:
456  PyDialect(pybind11::object descriptor) : descriptor(std::move(descriptor)) {}
457 
458  pybind11::object getDescriptor() { return descriptor; }
459 
460 private:
461  pybind11::object descriptor;
462 };
463 
464 /// Wrapper around an MlirDialectRegistry.
465 /// Upon construction, the Python wrapper takes ownership of the
466 /// underlying MlirDialectRegistry.
468 public:
470  PyDialectRegistry(MlirDialectRegistry registry) : registry(registry) {}
472  if (!mlirDialectRegistryIsNull(registry))
473  mlirDialectRegistryDestroy(registry);
474  }
476  PyDialectRegistry(PyDialectRegistry &&other) : registry(other.registry) {
477  other.registry = {nullptr};
478  }
479 
480  operator MlirDialectRegistry() const { return registry; }
481  MlirDialectRegistry get() const { return registry; }
482 
483  pybind11::object getCapsule();
484  static PyDialectRegistry createFromCapsule(pybind11::object capsule);
485 
486 private:
487  MlirDialectRegistry registry;
488 };
489 
490 /// Used in function arguments when None should resolve to the current context
491 /// manager set instance.
493  : public Defaulting<DefaultingPyLocation, PyLocation> {
494 public:
496  static constexpr const char kTypeDescription[] = "mlir.ir.Location";
497  static PyLocation &resolve();
498 
499  operator MlirLocation() const { return *get(); }
500 };
501 
502 /// Wrapper around MlirModule.
503 /// This is the top-level, user-owned object that contains regions/ops/blocks.
504 class PyModule;
506 class PyModule : public BaseContextObject {
507 public:
508  /// Returns a PyModule reference for the given MlirModule. This may return
509  /// a pre-existing or new object.
510  static PyModuleRef forModule(MlirModule module);
511  PyModule(PyModule &) = delete;
512  PyModule(PyMlirContext &&) = delete;
513  ~PyModule();
514 
515  /// Gets the backing MlirModule.
516  MlirModule get() { return module; }
517 
518  /// Gets a strong reference to this module.
520  return PyModuleRef(this,
521  pybind11::reinterpret_borrow<pybind11::object>(handle));
522  }
523 
524  /// Gets a capsule wrapping the void* within the MlirModule.
525  /// Note that the module does not (yet) provide a corresponding factory for
526  /// constructing from a capsule as that would require uniquing PyModule
527  /// instances, which is not currently done.
528  pybind11::object getCapsule();
529 
530  /// Creates a PyModule from the MlirModule wrapped by a capsule.
531  /// Note that PyModule instances are uniqued, so the returned object
532  /// may be a pre-existing object. Ownership of the underlying MlirModule
533  /// is taken by calling this function.
534  static pybind11::object createFromCapsule(pybind11::object capsule);
535 
536 private:
537  PyModule(PyMlirContextRef contextRef, MlirModule module);
538  MlirModule module;
539  pybind11::handle handle;
540 };
541 
542 /// Base class for PyOperation and PyOpView which exposes the primary, user
543 /// visible methods for manipulating it.
545 public:
546  virtual ~PyOperationBase() = default;
547  /// Implements the bound 'print' method and helps with others.
548  void print(pybind11::object fileObject, bool binary,
549  std::optional<int64_t> largeElementsLimit, bool enableDebugInfo,
550  bool prettyDebugInfo, bool printGenericOpForm, bool useLocalScope,
551  bool assumeVerified);
552  pybind11::object getAsm(bool binary,
553  std::optional<int64_t> largeElementsLimit,
554  bool enableDebugInfo, bool prettyDebugInfo,
555  bool printGenericOpForm, bool useLocalScope,
556  bool assumeVerified);
557 
558  // Implement the bound 'writeBytecode' method.
559  void writeBytecode(const pybind11::object &fileObject,
560  std::optional<int64_t> bytecodeVersion);
561 
562  /// Moves the operation before or after the other operation.
563  void moveAfter(PyOperationBase &other);
564  void moveBefore(PyOperationBase &other);
565 
566  /// Verify the operation. Throws `MLIRError` if verification fails, and
567  /// returns `true` otherwise.
568  bool verify();
569 
570  /// Each must provide access to the raw Operation.
571  virtual PyOperation &getOperation() = 0;
572 };
573 
574 /// Wrapper around PyOperation.
575 /// Operations exist in either an attached (dependent) or detached (top-level)
576 /// state. In the detached state (as on creation), an operation is owned by
577 /// the creator and its lifetime extends either until its reference count
578 /// drops to zero or it is attached to a parent, at which point its lifetime
579 /// is bounded by its top-level parent reference.
580 class PyOperation;
583 public:
584  ~PyOperation() override;
585  PyOperation &getOperation() override { return *this; }
586 
587  /// Returns a PyOperation for the given MlirOperation, optionally associating
588  /// it with a parentKeepAlive.
589  static PyOperationRef
590  forOperation(PyMlirContextRef contextRef, MlirOperation operation,
591  pybind11::object parentKeepAlive = pybind11::object());
592 
593  /// Creates a detached operation. The operation must not be associated with
594  /// any existing live operation.
595  static PyOperationRef
596  createDetached(PyMlirContextRef contextRef, MlirOperation operation,
597  pybind11::object parentKeepAlive = pybind11::object());
598 
599  /// Parses a source string (either text assembly or bytecode), creating a
600  /// detached operation.
601  static PyOperationRef parse(PyMlirContextRef contextRef,
602  const std::string &sourceStr,
603  const std::string &sourceName);
604 
605  /// Detaches the operation from its parent block and updates its state
606  /// accordingly.
609  setDetached();
610  parentKeepAlive = pybind11::object();
611  }
612 
613  /// Gets the backing operation.
614  operator MlirOperation() const { return get(); }
615  MlirOperation get() const {
616  checkValid();
617  return operation;
618  }
619 
621  return PyOperationRef(
622  this, pybind11::reinterpret_borrow<pybind11::object>(handle));
623  }
624 
625  bool isAttached() { return attached; }
626  void setAttached(const pybind11::object &parent = pybind11::object()) {
627  assert(!attached && "operation already attached");
628  attached = true;
629  }
630  void setDetached() {
631  assert(attached && "operation already detached");
632  attached = false;
633  }
634  void checkValid() const;
635 
636  /// Gets the owning block or raises an exception if the operation has no
637  /// owning block.
638  PyBlock getBlock();
639 
640  /// Gets the parent operation or raises an exception if the operation has
641  /// no parent.
642  std::optional<PyOperationRef> getParentOperation();
643 
644  /// Gets a capsule wrapping the void* within the MlirOperation.
645  pybind11::object getCapsule();
646 
647  /// Creates a PyOperation from the MlirOperation wrapped by a capsule.
648  /// Ownership of the underlying MlirOperation is taken by calling this
649  /// function.
650  static pybind11::object createFromCapsule(pybind11::object capsule);
651 
652  /// Creates an operation. See corresponding python docstring.
653  static pybind11::object
654  create(const std::string &name, std::optional<std::vector<PyType *>> results,
655  std::optional<std::vector<PyValue *>> operands,
656  std::optional<pybind11::dict> attributes,
657  std::optional<std::vector<PyBlock *>> successors, int regions,
658  DefaultingPyLocation location, const pybind11::object &ip,
659  bool inferType);
660 
661  /// Creates an OpView suitable for this operation.
662  pybind11::object createOpView();
663 
664  /// Erases the underlying MlirOperation, removes its pointer from the
665  /// parent context's live operations map, and sets the valid bit false.
666  void erase();
667 
668  /// Invalidate the operation.
669  void setInvalid() { valid = false; }
670 
671  /// Clones this operation.
672  pybind11::object clone(const pybind11::object &ip);
673 
674 private:
675  PyOperation(PyMlirContextRef contextRef, MlirOperation operation);
676  static PyOperationRef createInstance(PyMlirContextRef contextRef,
677  MlirOperation operation,
678  pybind11::object parentKeepAlive);
679 
680  MlirOperation operation;
681  pybind11::handle handle;
682  // Keeps the parent alive, regardless of whether it is an Operation or
683  // Module.
684  // TODO: As implemented, this facility is only sufficient for modeling the
685  // trivial module parent back-reference. Generalize this to also account for
686  // transitions from detached to attached and address TODOs in the
687  // ir_operation.py regarding testing corresponding lifetime guarantees.
688  pybind11::object parentKeepAlive;
689  bool attached = true;
690  bool valid = true;
691 
692  friend class PyOperationBase;
693  friend class PySymbolTable;
694 };
695 
696 /// A PyOpView is equivalent to the C++ "Op" wrappers: these are the basis for
697 /// providing more instance-specific accessors and serve as the base class for
698 /// custom ODS-style operation classes. Since this class is subclass on the
699 /// python side, it must present an __init__ method that operates in pure
700 /// python types.
701 class PyOpView : public PyOperationBase {
702 public:
703  PyOpView(const pybind11::object &operationObject);
704  PyOperation &getOperation() override { return operation; }
705 
706  pybind11::object getOperationObject() { return operationObject; }
707 
708  static pybind11::object buildGeneric(
709  const pybind11::object &cls, std::optional<pybind11::list> resultTypeList,
710  pybind11::list operandList, std::optional<pybind11::dict> attributes,
711  std::optional<std::vector<PyBlock *>> successors,
712  std::optional<int> regions, DefaultingPyLocation location,
713  const pybind11::object &maybeIp);
714 
715  /// Construct an instance of a class deriving from OpView, bypassing its
716  /// `__init__` method. The derived class will typically define a constructor
717  /// that provides a convenient builder, but we need to side-step this when
718  /// constructing an `OpView` for an already-built operation.
719  ///
720  /// The caller is responsible for verifying that `operation` is a valid
721  /// operation to construct `cls` with.
722  static pybind11::object constructDerived(const pybind11::object &cls,
723  const PyOperation &operation);
724 
725 private:
726  PyOperation &operation; // For efficient, cast-free access from C++
727  pybind11::object operationObject; // Holds the reference.
728 };
729 
730 /// Wrapper around an MlirRegion.
731 /// Regions are managed completely by their containing operation. Unlike the
732 /// C++ API, the python API does not support detached regions.
733 class PyRegion {
734 public:
735  PyRegion(PyOperationRef parentOperation, MlirRegion region)
736  : parentOperation(std::move(parentOperation)), region(region) {
737  assert(!mlirRegionIsNull(region) && "python region cannot be null");
738  }
739  operator MlirRegion() const { return region; }
740 
741  MlirRegion get() { return region; }
742  PyOperationRef &getParentOperation() { return parentOperation; }
743 
744  void checkValid() { return parentOperation->checkValid(); }
745 
746 private:
747  PyOperationRef parentOperation;
748  MlirRegion region;
749 };
750 
751 /// Wrapper around an MlirAsmState.
752 class PyAsmState {
753  public:
754  PyAsmState(MlirValue value, bool useLocalScope) {
755  flags = mlirOpPrintingFlagsCreate();
756  // The OpPrintingFlags are not exposed Python side, create locally and
757  // associate lifetime with the state.
758  if (useLocalScope)
760  state = mlirAsmStateCreateForValue(value, flags);
761  }
762 
763  PyAsmState(PyOperationBase &operation, bool useLocalScope) {
764  flags = mlirOpPrintingFlagsCreate();
765  // The OpPrintingFlags are not exposed Python side, create locally and
766  // associate lifetime with the state.
767  if (useLocalScope)
769  state =
770  mlirAsmStateCreateForOperation(operation.getOperation().get(), flags);
771  }
774  }
775  // Delete copy constructors.
776  PyAsmState(PyAsmState &other) = delete;
777  PyAsmState(const PyAsmState &other) = delete;
778 
779  MlirAsmState get() { return state; }
780 
781  private:
782  MlirAsmState state;
783  MlirOpPrintingFlags flags;
784 };
785 
786 /// Wrapper around an MlirBlock.
787 /// Blocks are managed completely by their containing operation. Unlike the
788 /// C++ API, the python API does not support detached blocks.
789 class PyBlock {
790 public:
791  PyBlock(PyOperationRef parentOperation, MlirBlock block)
792  : parentOperation(std::move(parentOperation)), block(block) {
793  assert(!mlirBlockIsNull(block) && "python block cannot be null");
794  }
795 
796  MlirBlock get() { return block; }
797  PyOperationRef &getParentOperation() { return parentOperation; }
798 
799  void checkValid() { return parentOperation->checkValid(); }
800 
801  /// Gets a capsule wrapping the void* within the MlirBlock.
802  pybind11::object getCapsule();
803 
804 private:
805  PyOperationRef parentOperation;
806  MlirBlock block;
807 };
808 
809 /// An insertion point maintains a pointer to a Block and a reference operation.
810 /// Calls to insert() will insert a new operation before the
811 /// reference operation. If the reference operation is null, then appends to
812 /// the end of the block.
814 public:
815  /// Creates an insertion point positioned after the last operation in the
816  /// block, but still inside the block.
817  PyInsertionPoint(PyBlock &block);
818  /// Creates an insertion point positioned before a reference operation.
819  PyInsertionPoint(PyOperationBase &beforeOperationBase);
820 
821  /// Shortcut to create an insertion point at the beginning of the block.
822  static PyInsertionPoint atBlockBegin(PyBlock &block);
823  /// Shortcut to create an insertion point before the block terminator.
825 
826  /// Inserts an operation.
827  void insert(PyOperationBase &operationBase);
828 
829  /// Enter and exit the context manager.
830  pybind11::object contextEnter();
831  void contextExit(const pybind11::object &excType,
832  const pybind11::object &excVal,
833  const pybind11::object &excTb);
834 
835  PyBlock &getBlock() { return block; }
836 
837 private:
838  // Trampoline constructor that avoids null initializing members while
839  // looking up parents.
840  PyInsertionPoint(PyBlock block, std::optional<PyOperationRef> refOperation)
841  : refOperation(std::move(refOperation)), block(std::move(block)) {}
842 
843  std::optional<PyOperationRef> refOperation;
844  PyBlock block;
845 };
846 /// Wrapper around the generic MlirType.
847 /// The lifetime of a type is bound by the PyContext that created it.
848 class PyType : public BaseContextObject {
849 public:
850  PyType(PyMlirContextRef contextRef, MlirType type)
851  : BaseContextObject(std::move(contextRef)), type(type) {}
852  bool operator==(const PyType &other) const;
853  operator MlirType() const { return type; }
854  MlirType get() const { return type; }
855 
856  /// Gets a capsule wrapping the void* within the MlirType.
857  pybind11::object getCapsule();
858 
859  /// Creates a PyType from the MlirType wrapped by a capsule.
860  /// Note that PyType instances are uniqued, so the returned object
861  /// may be a pre-existing object. Ownership of the underlying MlirType
862  /// is taken by calling this function.
863  static PyType createFromCapsule(pybind11::object capsule);
864 
865 private:
866  MlirType type;
867 };
868 
869 /// A TypeID provides an efficient and unique identifier for a specific C++
870 /// type. This allows for a C++ type to be compared, hashed, and stored in an
871 /// opaque context. This class wraps around the generic MlirTypeID.
872 class PyTypeID {
873 public:
874  PyTypeID(MlirTypeID typeID) : typeID(typeID) {}
875  // Note, this tests whether the underlying TypeIDs are the same,
876  // not whether the wrapper MlirTypeIDs are the same, nor whether
877  // the PyTypeID objects are the same (i.e., PyTypeID is a value type).
878  bool operator==(const PyTypeID &other) const;
879  operator MlirTypeID() const { return typeID; }
880  MlirTypeID get() { return typeID; }
881 
882  /// Gets a capsule wrapping the void* within the MlirTypeID.
883  pybind11::object getCapsule();
884 
885  /// Creates a PyTypeID from the MlirTypeID wrapped by a capsule.
886  static PyTypeID createFromCapsule(pybind11::object capsule);
887 
888 private:
889  MlirTypeID typeID;
890 };
891 
892 /// CRTP base classes for Python types that subclass Type and should be
893 /// castable from it (i.e. via something like IntegerType(t)).
894 /// By default, type class hierarchies are one level deep (i.e. a
895 /// concrete type class extends PyType); however, intermediate python-visible
896 /// base classes can be modeled by specifying a BaseTy.
897 template <typename DerivedTy, typename BaseTy = PyType>
898 class PyConcreteType : public BaseTy {
899 public:
900  // Derived classes must define statics for:
901  // IsAFunctionTy isaFunction
902  // const char *pyClassName
903  using ClassTy = pybind11::class_<DerivedTy, BaseTy>;
904  using IsAFunctionTy = bool (*)(MlirType);
905  using GetTypeIDFunctionTy = MlirTypeID (*)();
906  static constexpr GetTypeIDFunctionTy getTypeIdFunction = nullptr;
907 
908  PyConcreteType() = default;
909  PyConcreteType(PyMlirContextRef contextRef, MlirType t)
910  : BaseTy(std::move(contextRef), t) {}
912  : PyConcreteType(orig.getContext(), castFrom(orig)) {}
913 
914  static MlirType castFrom(PyType &orig) {
915  if (!DerivedTy::isaFunction(orig)) {
916  auto origRepr = pybind11::repr(pybind11::cast(orig)).cast<std::string>();
917  throw py::value_error((llvm::Twine("Cannot cast type to ") +
918  DerivedTy::pyClassName + " (from " + origRepr +
919  ")")
920  .str());
921  }
922  return orig;
923  }
924 
925  static void bind(pybind11::module &m) {
926  auto cls = ClassTy(m, DerivedTy::pyClassName, pybind11::module_local());
927  cls.def(pybind11::init<PyType &>(), pybind11::keep_alive<0, 1>(),
928  pybind11::arg("cast_from_type"));
929  cls.def_static(
930  "isinstance",
931  [](PyType &otherType) -> bool {
932  return DerivedTy::isaFunction(otherType);
933  },
934  pybind11::arg("other"));
935  cls.def_property_readonly_static(
936  "static_typeid", [](py::object & /*class*/) -> MlirTypeID {
937  if (DerivedTy::getTypeIdFunction)
938  return DerivedTy::getTypeIdFunction();
939  throw py::attribute_error(
940  (DerivedTy::pyClassName + llvm::Twine(" has no typeid.")).str());
941  });
942  cls.def_property_readonly("typeid", [](PyType &self) {
943  return py::cast(self).attr("typeid").cast<MlirTypeID>();
944  });
945  cls.def("__repr__", [](DerivedTy &self) {
946  PyPrintAccumulator printAccum;
947  printAccum.parts.append(DerivedTy::pyClassName);
948  printAccum.parts.append("(");
949  mlirTypePrint(self, printAccum.getCallback(), printAccum.getUserData());
950  printAccum.parts.append(")");
951  return printAccum.join();
952  });
953 
954  if (DerivedTy::getTypeIdFunction) {
956  DerivedTy::getTypeIdFunction(),
957  pybind11::cpp_function(
958  [](PyType pyType) -> DerivedTy { return pyType; }));
959  }
960 
961  DerivedTy::bindDerived(cls);
962  }
963 
964  /// Implemented by derived classes to add methods to the Python subclass.
965  static void bindDerived(ClassTy &m) {}
966 };
967 
968 /// Wrapper around the generic MlirAttribute.
969 /// The lifetime of a type is bound by the PyContext that created it.
971 public:
972  PyAttribute(PyMlirContextRef contextRef, MlirAttribute attr)
973  : BaseContextObject(std::move(contextRef)), attr(attr) {}
974  bool operator==(const PyAttribute &other) const;
975  operator MlirAttribute() const { return attr; }
976  MlirAttribute get() const { return attr; }
977 
978  /// Gets a capsule wrapping the void* within the MlirAttribute.
979  pybind11::object getCapsule();
980 
981  /// Creates a PyAttribute from the MlirAttribute wrapped by a capsule.
982  /// Note that PyAttribute instances are uniqued, so the returned object
983  /// may be a pre-existing object. Ownership of the underlying MlirAttribute
984  /// is taken by calling this function.
985  static PyAttribute createFromCapsule(pybind11::object capsule);
986 
987 private:
988  MlirAttribute attr;
989 };
990 
991 /// Represents a Python MlirNamedAttr, carrying an optional owned name.
992 /// TODO: Refactor this and the C-API to be based on an Identifier owned
993 /// by the context so as to avoid ownership issues here.
995 public:
996  /// Constructs a PyNamedAttr that retains an owned name. This should be
997  /// used in any code that originates an MlirNamedAttribute from a python
998  /// string.
999  /// The lifetime of the PyNamedAttr must extend to the lifetime of the
1000  /// passed attribute.
1001  PyNamedAttribute(MlirAttribute attr, std::string ownedName);
1002 
1004 
1005 private:
1006  // Since the MlirNamedAttr contains an internal pointer to the actual
1007  // memory of the owned string, it must be heap allocated to remain valid.
1008  // Otherwise, strings that fit within the small object optimization threshold
1009  // will have their memory address change as the containing object is moved,
1010  // resulting in an invalid aliased pointer.
1011  std::unique_ptr<std::string> ownedName;
1012 };
1013 
1014 /// CRTP base classes for Python attributes that subclass Attribute and should
1015 /// be castable from it (i.e. via something like StringAttr(attr)).
1016 /// By default, attribute class hierarchies are one level deep (i.e. a
1017 /// concrete attribute class extends PyAttribute); however, intermediate
1018 /// python-visible base classes can be modeled by specifying a BaseTy.
1019 template <typename DerivedTy, typename BaseTy = PyAttribute>
1020 class PyConcreteAttribute : public BaseTy {
1021 public:
1022  // Derived classes must define statics for:
1023  // IsAFunctionTy isaFunction
1024  // const char *pyClassName
1025  using ClassTy = pybind11::class_<DerivedTy, BaseTy>;
1026  using IsAFunctionTy = bool (*)(MlirAttribute);
1027  using GetTypeIDFunctionTy = MlirTypeID (*)();
1028  static constexpr GetTypeIDFunctionTy getTypeIdFunction = nullptr;
1029 
1030  PyConcreteAttribute() = default;
1031  PyConcreteAttribute(PyMlirContextRef contextRef, MlirAttribute attr)
1032  : BaseTy(std::move(contextRef), attr) {}
1034  : PyConcreteAttribute(orig.getContext(), castFrom(orig)) {}
1035 
1036  static MlirAttribute castFrom(PyAttribute &orig) {
1037  if (!DerivedTy::isaFunction(orig)) {
1038  auto origRepr = pybind11::repr(pybind11::cast(orig)).cast<std::string>();
1039  throw py::value_error((llvm::Twine("Cannot cast attribute to ") +
1040  DerivedTy::pyClassName + " (from " + origRepr +
1041  ")")
1042  .str());
1043  }
1044  return orig;
1045  }
1046 
1047  static void bind(pybind11::module &m) {
1048  auto cls = ClassTy(m, DerivedTy::pyClassName, pybind11::buffer_protocol(),
1049  pybind11::module_local());
1050  cls.def(pybind11::init<PyAttribute &>(), pybind11::keep_alive<0, 1>(),
1051  pybind11::arg("cast_from_attr"));
1052  cls.def_static(
1053  "isinstance",
1054  [](PyAttribute &otherAttr) -> bool {
1055  return DerivedTy::isaFunction(otherAttr);
1056  },
1057  pybind11::arg("other"));
1058  cls.def_property_readonly(
1059  "type", [](PyAttribute &attr) { return mlirAttributeGetType(attr); });
1060  cls.def_property_readonly_static(
1061  "static_typeid", [](py::object & /*class*/) -> MlirTypeID {
1062  if (DerivedTy::getTypeIdFunction)
1063  return DerivedTy::getTypeIdFunction();
1064  throw py::attribute_error(
1065  (DerivedTy::pyClassName + llvm::Twine(" has no typeid.")).str());
1066  });
1067  cls.def_property_readonly("typeid", [](PyAttribute &self) {
1068  return py::cast(self).attr("typeid").cast<MlirTypeID>();
1069  });
1070  cls.def("__repr__", [](DerivedTy &self) {
1071  PyPrintAccumulator printAccum;
1072  printAccum.parts.append(DerivedTy::pyClassName);
1073  printAccum.parts.append("(");
1074  mlirAttributePrint(self, printAccum.getCallback(),
1075  printAccum.getUserData());
1076  printAccum.parts.append(")");
1077  return printAccum.join();
1078  });
1079 
1080  if (DerivedTy::getTypeIdFunction) {
1082  DerivedTy::getTypeIdFunction(),
1083  pybind11::cpp_function([](PyAttribute pyAttribute) -> DerivedTy {
1084  return pyAttribute;
1085  }));
1086  }
1087 
1088  DerivedTy::bindDerived(cls);
1089  }
1090 
1091  /// Implemented by derived classes to add methods to the Python subclass.
1092  static void bindDerived(ClassTy &m) {}
1093 };
1094 
1095 /// Wrapper around the generic MlirValue.
1096 /// Values are managed completely by the operation that resulted in their
1097 /// definition. For op result value, this is the operation that defines the
1098 /// value. For block argument values, this is the operation that contains the
1099 /// block to which the value is an argument (blocks cannot be detached in Python
1100 /// bindings so such operation always exists).
1101 class PyValue {
1102 public:
1103  PyValue(PyOperationRef parentOperation, MlirValue value)
1104  : parentOperation(std::move(parentOperation)), value(value) {}
1105  operator MlirValue() const { return value; }
1106 
1107  MlirValue get() { return value; }
1108  PyOperationRef &getParentOperation() { return parentOperation; }
1109 
1110  void checkValid() { return parentOperation->checkValid(); }
1111 
1112  /// Gets a capsule wrapping the void* within the MlirValue.
1113  pybind11::object getCapsule();
1114 
1115  /// Creates a PyValue from the MlirValue wrapped by a capsule. Ownership of
1116  /// the underlying MlirValue is still tied to the owning operation.
1117  static PyValue createFromCapsule(pybind11::object capsule);
1118 
1119 private:
1120  PyOperationRef parentOperation;
1121  MlirValue value;
1122 };
1123 
1124 /// Wrapper around MlirAffineExpr. Affine expressions are owned by the context.
1126 public:
1127  PyAffineExpr(PyMlirContextRef contextRef, MlirAffineExpr affineExpr)
1128  : BaseContextObject(std::move(contextRef)), affineExpr(affineExpr) {}
1129  bool operator==(const PyAffineExpr &other) const;
1130  operator MlirAffineExpr() const { return affineExpr; }
1131  MlirAffineExpr get() const { return affineExpr; }
1132 
1133  /// Gets a capsule wrapping the void* within the MlirAffineExpr.
1134  pybind11::object getCapsule();
1135 
1136  /// Creates a PyAffineExpr from the MlirAffineExpr wrapped by a capsule.
1137  /// Note that PyAffineExpr instances are uniqued, so the returned object
1138  /// may be a pre-existing object. Ownership of the underlying MlirAffineExpr
1139  /// is taken by calling this function.
1140  static PyAffineExpr createFromCapsule(pybind11::object capsule);
1141 
1142  PyAffineExpr add(const PyAffineExpr &other) const;
1143  PyAffineExpr mul(const PyAffineExpr &other) const;
1144  PyAffineExpr floorDiv(const PyAffineExpr &other) const;
1145  PyAffineExpr ceilDiv(const PyAffineExpr &other) const;
1146  PyAffineExpr mod(const PyAffineExpr &other) const;
1147 
1148 private:
1149  MlirAffineExpr affineExpr;
1150 };
1151 
1153 public:
1154  PyAffineMap(PyMlirContextRef contextRef, MlirAffineMap affineMap)
1155  : BaseContextObject(std::move(contextRef)), affineMap(affineMap) {}
1156  bool operator==(const PyAffineMap &other) const;
1157  operator MlirAffineMap() const { return affineMap; }
1158  MlirAffineMap get() const { return affineMap; }
1159 
1160  /// Gets a capsule wrapping the void* within the MlirAffineMap.
1161  pybind11::object getCapsule();
1162 
1163  /// Creates a PyAffineMap from the MlirAffineMap wrapped by a capsule.
1164  /// Note that PyAffineMap instances are uniqued, so the returned object
1165  /// may be a pre-existing object. Ownership of the underlying MlirAffineMap
1166  /// is taken by calling this function.
1167  static PyAffineMap createFromCapsule(pybind11::object capsule);
1168 
1169 private:
1170  MlirAffineMap affineMap;
1171 };
1172 
1174 public:
1175  PyIntegerSet(PyMlirContextRef contextRef, MlirIntegerSet integerSet)
1176  : BaseContextObject(std::move(contextRef)), integerSet(integerSet) {}
1177  bool operator==(const PyIntegerSet &other) const;
1178  operator MlirIntegerSet() const { return integerSet; }
1179  MlirIntegerSet get() const { return integerSet; }
1180 
1181  /// Gets a capsule wrapping the void* within the MlirIntegerSet.
1182  pybind11::object getCapsule();
1183 
1184  /// Creates a PyIntegerSet from the MlirAffineMap wrapped by a capsule.
1185  /// Note that PyIntegerSet instances may be uniqued, so the returned object
1186  /// may be a pre-existing object. Integer sets are owned by the context.
1187  static PyIntegerSet createFromCapsule(pybind11::object capsule);
1188 
1189 private:
1190  MlirIntegerSet integerSet;
1191 };
1192 
1193 /// Bindings for MLIR symbol tables.
1195 public:
1196  /// Constructs a symbol table for the given operation.
1197  explicit PySymbolTable(PyOperationBase &operation);
1198 
1199  /// Destroys the symbol table.
1201 
1202  /// Returns the symbol (opview) with the given name, throws if there is no
1203  /// such symbol in the table.
1204  pybind11::object dunderGetItem(const std::string &name);
1205 
1206  /// Removes the given operation from the symbol table and erases it.
1207  void erase(PyOperationBase &symbol);
1208 
1209  /// Removes the operation with the given name from the symbol table and erases
1210  /// it, throws if there is no such symbol in the table.
1211  void dunderDel(const std::string &name);
1212 
1213  /// Inserts the given operation into the symbol table. The operation must have
1214  /// the symbol trait.
1215  MlirAttribute insert(PyOperationBase &symbol);
1216 
1217  /// Gets and sets the name of a symbol op.
1218  static MlirAttribute getSymbolName(PyOperationBase &symbol);
1219  static void setSymbolName(PyOperationBase &symbol, const std::string &name);
1220 
1221  /// Gets and sets the visibility of a symbol op.
1222  static MlirAttribute getVisibility(PyOperationBase &symbol);
1223  static void setVisibility(PyOperationBase &symbol,
1224  const std::string &visibility);
1225 
1226  /// Replaces all symbol uses within an operation. See the API
1227  /// mlirSymbolTableReplaceAllSymbolUses for all caveats.
1228  static void replaceAllSymbolUses(const std::string &oldSymbol,
1229  const std::string &newSymbol,
1230  PyOperationBase &from);
1231 
1232  /// Walks all symbol tables under and including 'from'.
1233  static void walkSymbolTables(PyOperationBase &from, bool allSymUsesVisible,
1234  pybind11::object callback);
1235 
1236  /// Casts the bindings class into the C API structure.
1237  operator MlirSymbolTable() { return symbolTable; }
1238 
1239 private:
1240  PyOperationRef operation;
1241  MlirSymbolTable symbolTable;
1242 };
1243 
1244 /// Custom exception that allows access to error diagnostic information. This is
1245 /// converted to the `ir.MLIRError` python exception when thrown.
1246 struct MLIRError {
1247  MLIRError(llvm::Twine message,
1248  std::vector<PyDiagnostic::DiagnosticInfo> &&errorDiagnostics = {})
1249  : message(message.str()), errorDiagnostics(std::move(errorDiagnostics)) {}
1250  std::string message;
1251  std::vector<PyDiagnostic::DiagnosticInfo> errorDiagnostics;
1252 };
1253 
1254 void populateIRAffine(pybind11::module &m);
1255 void populateIRAttributes(pybind11::module &m);
1256 void populateIRCore(pybind11::module &m);
1257 void populateIRInterfaces(pybind11::module &m);
1258 void populateIRTypes(pybind11::module &m);
1259 
1260 } // namespace python
1261 } // namespace mlir
1262 
1263 namespace pybind11 {
1264 namespace detail {
1265 
1266 template <>
1267 struct type_caster<mlir::python::DefaultingPyMlirContext>
1268  : MlirDefaultingCaster<mlir::python::DefaultingPyMlirContext> {};
1269 template <>
1270 struct type_caster<mlir::python::DefaultingPyLocation>
1271  : MlirDefaultingCaster<mlir::python::DefaultingPyLocation> {};
1272 
1273 } // namespace detail
1274 } // namespace pybind11
1275 
1276 #endif // MLIR_BINDINGS_PYTHON_IRMODULES_H
static std::string diag(const llvm::Value &value)
Base class for all objects that directly or indirectly depend on an MlirContext.
Definition: IRModule.h:279
PyMlirContextRef & getContext()
Accesses the context reference.
Definition: IRModule.h:287
BaseContextObject(PyMlirContextRef ref)
Definition: IRModule.h:281
Used in function arguments when None should resolve to the current context manager set instance.
Definition: IRModule.h:493
static PyLocation & resolve()
Definition: IRCore.cpp:992
static constexpr const char kTypeDescription[]
Definition: IRModule.h:496
Used in function arguments when None should resolve to the current context manager set instance.
Definition: IRModule.h:268
static constexpr const char kTypeDescription[]
Definition: IRModule.h:271
static PyMlirContext & resolve()
Definition: IRCore.cpp:715
CRTP template for special wrapper types that are allowed to be passed in as 'None' function arguments...
Definition: PybindUtils.h:38
Defaulting()=default
Type casters require the type to be default constructible, but using such an instance is illegal.
Wrapper around MlirAffineExpr. Affine expressions are owned by the context.
Definition: IRModule.h:1125
static PyAffineExpr createFromCapsule(pybind11::object capsule)
Creates a PyAffineExpr from the MlirAffineExpr wrapped by a capsule.
Definition: IRAffine.cpp:360
pybind11::object getCapsule()
Gets a capsule wrapping the void* within the MlirAffineExpr.
Definition: IRAffine.cpp:355
PyAffineExpr(PyMlirContextRef contextRef, MlirAffineExpr affineExpr)
Definition: IRModule.h:1127
PyAffineExpr ceilDiv(const PyAffineExpr &other) const
PyAffineExpr mul(const PyAffineExpr &other) const
PyAffineExpr mod(const PyAffineExpr &other) const
PyAffineExpr floorDiv(const PyAffineExpr &other) const
bool operator==(const PyAffineExpr &other) const
Definition: IRAffine.cpp:351
PyAffineExpr add(const PyAffineExpr &other) const
MlirAffineExpr get() const
Definition: IRModule.h:1131
pybind11::object getCapsule()
Gets a capsule wrapping the void* within the MlirAffineMap.
Definition: IRAffine.cpp:414
PyAffineMap(PyMlirContextRef contextRef, MlirAffineMap affineMap)
Definition: IRModule.h:1154
bool operator==(const PyAffineMap &other) const
Definition: IRAffine.cpp:410
MlirAffineMap get() const
Definition: IRModule.h:1158
static PyAffineMap createFromCapsule(pybind11::object capsule)
Creates a PyAffineMap from the MlirAffineMap wrapped by a capsule.
Definition: IRAffine.cpp:418
Wrapper around an MlirAsmState.
Definition: IRModule.h:752
PyAsmState(PyOperationBase &operation, bool useLocalScope)
Definition: IRModule.h:763
PyAsmState(MlirValue value, bool useLocalScope)
Definition: IRModule.h:754
PyAsmState(PyAsmState &other)=delete
PyAsmState(const PyAsmState &other)=delete
MlirAsmState get()
Definition: IRModule.h:779
Wrapper around the generic MlirAttribute.
Definition: IRModule.h:970
PyAttribute(PyMlirContextRef contextRef, MlirAttribute attr)
Definition: IRModule.h:972
static PyAttribute createFromCapsule(pybind11::object capsule)
Creates a PyAttribute from the MlirAttribute wrapped by a capsule.
Definition: IRCore.cpp:1815
pybind11::object getCapsule()
Gets a capsule wrapping the void* within the MlirAttribute.
Definition: IRCore.cpp:1811
MlirAttribute get() const
Definition: IRModule.h:976
bool operator==(const PyAttribute &other) const
Definition: IRCore.cpp:1807
Wrapper around an MlirBlock.
Definition: IRModule.h:789
MlirBlock get()
Definition: IRModule.h:796
pybind11::object getCapsule()
Gets a capsule wrapping the void* within the MlirBlock.
Definition: IRCore.cpp:269
PyOperationRef & getParentOperation()
Definition: IRModule.h:797
PyBlock(PyOperationRef parentOperation, MlirBlock block)
Definition: IRModule.h:791
CRTP base classes for Python attributes that subclass Attribute and should be castable from it (i....
Definition: IRModule.h:1020
pybind11::class_< DerivedTy, BaseTy > ClassTy
Definition: IRModule.h:1025
MlirTypeID(*)() GetTypeIDFunctionTy
Definition: IRModule.h:1027
static MlirAttribute castFrom(PyAttribute &orig)
Definition: IRModule.h:1036
static void bind(pybind11::module &m)
Definition: IRModule.h:1047
static constexpr GetTypeIDFunctionTy getTypeIdFunction
Definition: IRModule.h:1028
bool(*)(MlirAttribute) IsAFunctionTy
Definition: IRModule.h:1026
PyConcreteAttribute(PyAttribute &orig)
Definition: IRModule.h:1033
PyConcreteAttribute(PyMlirContextRef contextRef, MlirAttribute attr)
Definition: IRModule.h:1031
static void bindDerived(ClassTy &m)
Implemented by derived classes to add methods to the Python subclass.
Definition: IRModule.h:1092
CRTP base classes for Python types that subclass Type and should be castable from it (i....
Definition: IRModule.h:898
static void bind(pybind11::module &m)
Definition: IRModule.h:925
pybind11::class_< DerivedTy, BaseTy > ClassTy
Definition: IRModule.h:903
PyConcreteType(PyType &orig)
Definition: IRModule.h:911
MlirTypeID(*)() GetTypeIDFunctionTy
Definition: IRModule.h:905
bool(*)(MlirType) IsAFunctionTy
Definition: IRModule.h:904
static void bindDerived(ClassTy &m)
Implemented by derived classes to add methods to the Python subclass.
Definition: IRModule.h:965
static constexpr GetTypeIDFunctionTy getTypeIdFunction
Definition: IRModule.h:906
PyConcreteType(PyMlirContextRef contextRef, MlirType t)
Definition: IRModule.h:909
static MlirType castFrom(PyType &orig)
Definition: IRModule.h:914
Represents a diagnostic handler attached to the context.
Definition: IRModule.h:375
void contextExit(const pybind11::object &excType, const pybind11::object &excVal, const pybind11::object &excTb)
Definition: IRModule.h:387
void detach()
Detaches the handler. Does nothing if not attached.
Definition: IRCore.cpp:877
PyDiagnosticHandler(MlirContext context, pybind11::object callback)
Definition: IRCore.cpp:871
pybind11::object contextEnter()
Definition: IRModule.h:386
Python class mirroring the C MlirDiagnostic struct.
Definition: IRModule.h:325
pybind11::str getMessage()
Definition: IRCore.cpp:907
PyLocation getLocation()
Definition: IRCore.cpp:900
DiagnosticInfo getInfo()
Definition: IRCore.cpp:928
PyDiagnostic(MlirDiagnostic diagnostic)
Definition: IRModule.h:327
MlirDiagnosticSeverity getSeverity()
Definition: IRCore.cpp:895
pybind11::tuple getNotes()
Definition: IRCore.cpp:915
Wrapper around an MlirDialect.
Definition: IRModule.h:430
PyDialectDescriptor(PyMlirContextRef contextRef, MlirDialect dialect)
Definition: IRModule.h:432
Wrapper around an MlirDialectRegistry.
Definition: IRModule.h:467
PyDialectRegistry(PyDialectRegistry &)=delete
static PyDialectRegistry createFromCapsule(pybind11::object capsule)
Definition: IRCore.cpp:958
MlirDialectRegistry get() const
Definition: IRModule.h:481
pybind11::object getCapsule()
Definition: IRCore.cpp:953
PyDialectRegistry(MlirDialectRegistry registry)
Definition: IRModule.h:470
PyDialectRegistry(PyDialectRegistry &&other)
Definition: IRModule.h:476
User-level dialect object.
Definition: IRModule.h:454
PyDialect(pybind11::object descriptor)
Definition: IRModule.h:456
pybind11::object getDescriptor()
Definition: IRModule.h:458
User-level object for accessing dialects with dotted syntax such as: ctx.dialect.std.
Definition: IRModule.h:443
PyDialects(PyMlirContextRef contextRef)
Definition: IRModule.h:445
MlirDialect getDialectForKey(const std::string &key, bool attrError)
Definition: IRCore.cpp:939
void registerTypeCaster(MlirTypeID mlirTypeID, pybind11::function typeCaster, bool replace=false)
Adds a user-friendly type caster.
Definition: IRModule.cpp:78
static PyGlobals & get()
Most code should get the globals via this static accessor.
Definition: Globals.h:34
An insertion point maintains a pointer to a Block and a reference operation.
Definition: IRModule.h:813
static PyInsertionPoint atBlockTerminator(PyBlock &block)
Shortcut to create an insertion point before the block terminator.
Definition: IRCore.cpp:1784
PyInsertionPoint(PyBlock &block)
Creates an insertion point positioned after the last operation in the block, but still inside the blo...
Definition: IRCore.cpp:1739
static PyInsertionPoint atBlockBegin(PyBlock &block)
Shortcut to create an insertion point at the beginning of the block.
Definition: IRCore.cpp:1771
void insert(PyOperationBase &operationBase)
Inserts an operation.
Definition: IRCore.cpp:1745
void contextExit(const pybind11::object &excType, const pybind11::object &excVal, const pybind11::object &excTb)
Definition: IRCore.cpp:1797
pybind11::object contextEnter()
Enter and exit the context manager.
Definition: IRCore.cpp:1793
static PyIntegerSet createFromCapsule(pybind11::object capsule)
Creates a PyIntegerSet from the MlirAffineMap wrapped by a capsule.
Definition: IRAffine.cpp:496
MlirIntegerSet get() const
Definition: IRModule.h:1179
bool operator==(const PyIntegerSet &other) const
Definition: IRAffine.cpp:487
pybind11::object getCapsule()
Gets a capsule wrapping the void* within the MlirIntegerSet.
Definition: IRAffine.cpp:491
PyIntegerSet(PyMlirContextRef contextRef, MlirIntegerSet integerSet)
Definition: IRModule.h:1175
Wrapper around an MlirLocation.
Definition: IRModule.h:294
PyLocation(PyMlirContextRef contextRef, MlirLocation loc)
Definition: IRModule.h:296
pybind11::object getCapsule()
Gets a capsule wrapping the void* within the MlirLocation.
Definition: IRCore.cpp:970
static PyLocation createFromCapsule(pybind11::object capsule)
Creates a PyLocation from the MlirLocation wrapped by a capsule.
Definition: IRCore.cpp:974
void contextExit(const pybind11::object &excType, const pybind11::object &excVal, const pybind11::object &excTb)
Definition: IRCore.cpp:986
pybind11::object contextEnter()
Enter and exit the context manager.
Definition: IRCore.cpp:982
MlirLocation get() const
Definition: IRModule.h:300
pybind11::object attachDiagnosticHandler(pybind11::object callback)
Attaches a Python callback as a diagnostic handler, returning a registration object (internally a PyD...
Definition: IRCore.cpp:650
PyMlirContext(const PyMlirContext &)=delete
PyMlirContext(PyMlirContext &&)=delete
MlirContext get()
Accesses the underlying MlirContext.
Definition: IRModule.h:182
PyMlirContextRef getRef()
Gets a strong reference to this context, which will ensure it is kept alive for the life of the refer...
Definition: IRModule.h:186
static pybind11::object createFromCapsule(pybind11::object capsule)
Creates a PyMlirContext from the MlirContext wrapped by a capsule.
Definition: IRCore.cpp:592
static size_t getLiveCount()
Gets the count of live context objects. Used for testing.
Definition: IRCore.cpp:626
static PyMlirContext * createNewContextForInit()
For the case of a python init (py::init) method, pybind11 is quite strict about needing to return a p...
Definition: IRCore.cpp:599
size_t getLiveModuleCount()
Gets the count of live modules associated with this context.
Definition: IRCore.cpp:638
pybind11::object contextEnter()
Enter and exit the context manager.
Definition: IRCore.cpp:640
size_t clearLiveOperations()
Clears the live operations map, returning the number of entries which were invalidated.
Definition: IRCore.cpp:630
void contextExit(const pybind11::object &excType, const pybind11::object &excVal, const pybind11::object &excTb)
Definition: IRCore.cpp:644
static PyMlirContextRef forContext(MlirContext context)
Returns a context reference for the singleton PyMlirContext wrapper for the given context.
Definition: IRCore.cpp:604
size_t getLiveOperationCount()
Gets the count of live operations associated with this context.
Definition: IRCore.cpp:628
void setEmitErrorDiagnostics(bool value)
Controls whether error diagnostics should be propagated to diagnostic handlers, instead of being capt...
Definition: IRModule.h:228
pybind11::object getCapsule()
Gets a capsule wrapping the void* within the MlirContext.
Definition: IRCore.cpp:588
MlirModule get()
Gets the backing MlirModule.
Definition: IRModule.h:516
static PyModuleRef forModule(MlirModule module)
Returns a PyModule reference for the given MlirModule.
Definition: IRCore.cpp:1019
pybind11::object getCapsule()
Gets a capsule wrapping the void* within the MlirModule.
Definition: IRCore.cpp:1052
static pybind11::object createFromCapsule(pybind11::object capsule)
Creates a PyModule from the MlirModule wrapped by a capsule.
Definition: IRCore.cpp:1045
PyModuleRef getRef()
Gets a strong reference to this module.
Definition: IRModule.h:519
PyModule(PyModule &)=delete
PyModule(PyMlirContext &&)=delete
Represents a Python MlirNamedAttr, carrying an optional owned name.
Definition: IRModule.h:994
PyNamedAttribute(MlirAttribute attr, std::string ownedName)
Constructs a PyNamedAttr that retains an owned name.
Definition: IRCore.cpp:1827
MlirNamedAttribute namedAttr
Definition: IRModule.h:1003
Template for a reference to a concrete type which captures a python reference to its underlying pytho...
Definition: IRModule.h:47
PyObjectRef(T *referrent, pybind11::object object)
Definition: IRModule.h:49
pybind11::object getObject()
Definition: IRModule.h:85
pybind11::object releaseObject()
Releases the object held by this instance, returning it.
Definition: IRModule.h:73
PyObjectRef(PyObjectRef &&other)
Definition: IRModule.h:55
PyObjectRef(const PyObjectRef &other)
Definition: IRModule.h:60
A PyOpView is equivalent to the C++ "Op" wrappers: these are the basis for providing more instance-sp...
Definition: IRModule.h:701
PyOpView(const pybind11::object &operationObject)
Definition: IRCore.cpp:1729
pybind11::object getOperationObject()
Definition: IRModule.h:706
static pybind11::object buildGeneric(const pybind11::object &cls, std::optional< pybind11::list > resultTypeList, pybind11::list operandList, std::optional< pybind11::dict > attributes, std::optional< std::vector< PyBlock * >> successors, std::optional< int > regions, DefaultingPyLocation location, const pybind11::object &maybeIp)
Definition: IRCore.cpp:1540
static pybind11::object constructDerived(const pybind11::object &cls, const PyOperation &operation)
Construct an instance of a class deriving from OpView, bypassing its __init__ method.
Definition: IRCore.cpp:1718
PyOperation & getOperation() override
Each must provide access to the raw Operation.
Definition: IRModule.h:704
Base class for PyOperation and PyOpView which exposes the primary, user visible methods for manipulat...
Definition: IRModule.h:544
virtual PyOperation & getOperation()=0
Each must provide access to the raw Operation.
void writeBytecode(const pybind11::object &fileObject, std::optional< int64_t > bytecodeVersion)
Definition: IRCore.cpp:1173
pybind11::object getAsm(bool binary, std::optional< int64_t > largeElementsLimit, bool enableDebugInfo, bool prettyDebugInfo, bool printGenericOpForm, bool useLocalScope, bool assumeVerified)
Definition: IRCore.cpp:1194
virtual ~PyOperationBase()=default
void print(pybind11::object fileObject, bool binary, std::optional< int64_t > largeElementsLimit, bool enableDebugInfo, bool prettyDebugInfo, bool printGenericOpForm, bool useLocalScope, bool assumeVerified)
Implements the bound 'print' method and helps with others.
Definition: IRCore.cpp:1144
void moveAfter(PyOperationBase &other)
Moves the operation before or after the other operation.
Definition: IRCore.cpp:1216
void moveBefore(PyOperationBase &other)
Definition: IRCore.cpp:1225
bool verify()
Verify the operation.
Definition: IRCore.cpp:1234
pybind11::object clone(const pybind11::object &ip)
Clones this operation.
Definition: IRCore.cpp:1416
void detachFromParent()
Detaches the operation from its parent block and updates its state accordingly.
Definition: IRModule.h:607
void erase()
Erases the underlying MlirOperation, removes its pointer from the parent context's live operations ma...
Definition: IRCore.cpp:1436
pybind11::object getCapsule()
Gets a capsule wrapping the void* within the MlirOperation.
Definition: IRCore.cpp:1261
PyOperation & getOperation() override
Each must provide access to the raw Operation.
Definition: IRModule.h:585
PyOperationRef getRef()
Definition: IRModule.h:620
MlirOperation get() const
Definition: IRModule.h:615
void setAttached(const pybind11::object &parent=pybind11::object())
Definition: IRModule.h:626
static pybind11::object create(const std::string &name, std::optional< std::vector< PyType * >> results, std::optional< std::vector< PyValue * >> operands, std::optional< pybind11::dict > attributes, std::optional< std::vector< PyBlock * >> successors, int regions, DefaultingPyLocation location, const pybind11::object &ip, bool inferType)
Creates an operation. See corresponding python docstring.
Definition: IRCore.cpp:1290
pybind11::object createOpView()
Creates an OpView suitable for this operation.
Definition: IRCore.cpp:1425
static PyOperationRef forOperation(PyMlirContextRef contextRef, MlirOperation operation, pybind11::object parentKeepAlive=pybind11::object())
Returns a PyOperation for the given MlirOperation, optionally associating it with a parentKeepAlive.
Definition: IRCore.cpp:1096
std::optional< PyOperationRef > getParentOperation()
Gets the parent operation or raises an exception if the operation has no parent.
Definition: IRCore.cpp:1242
PyBlock getBlock()
Gets the owning block or raises an exception if the operation has no owning block.
Definition: IRCore.cpp:1252
static PyOperationRef createDetached(PyMlirContextRef contextRef, MlirOperation operation, pybind11::object parentKeepAlive=pybind11::object())
Creates a detached operation.
Definition: IRCore.cpp:1112
static PyOperationRef parse(PyMlirContextRef contextRef, const std::string &sourceStr, const std::string &sourceName)
Parses a source string (either text assembly or bytecode), creating a detached operation.
Definition: IRCore.cpp:1126
static pybind11::object createFromCapsule(pybind11::object capsule)
Creates a PyOperation from the MlirOperation wrapped by a capsule.
Definition: IRCore.cpp:1266
void checkValid() const
Definition: IRCore.cpp:1138
void setInvalid()
Invalidate the operation.
Definition: IRModule.h:669
Wrapper around an MlirRegion.
Definition: IRModule.h:733
PyRegion(PyOperationRef parentOperation, MlirRegion region)
Definition: IRModule.h:735
PyOperationRef & getParentOperation()
Definition: IRModule.h:742
MlirRegion get()
Definition: IRModule.h:741
Bindings for MLIR symbol tables.
Definition: IRModule.h:1194
void dunderDel(const std::string &name)
Removes the operation with the given name from the symbol table and erases it, throws if there is no ...
Definition: IRCore.cpp:1932
static void replaceAllSymbolUses(const std::string &oldSymbol, const std::string &newSymbol, PyOperationBase &from)
Replaces all symbol uses within an operation.
Definition: IRCore.cpp:2003
static void setVisibility(PyOperationBase &symbol, const std::string &visibility)
Definition: IRCore.cpp:1985
static void setSymbolName(PyOperationBase &symbol, const std::string &name)
Definition: IRCore.cpp:1959
~PySymbolTable()
Destroys the symbol table.
Definition: IRModule.h:1200
MlirAttribute insert(PyOperationBase &symbol)
Inserts the given operation into the symbol table.
Definition: IRCore.cpp:1937
void erase(PyOperationBase &symbol)
Removes the given operation from the symbol table and erases it.
Definition: IRCore.cpp:1922
PySymbolTable(PyOperationBase &operation)
Constructs a symbol table for the given operation.
Definition: IRCore.cpp:1902
static MlirAttribute getSymbolName(PyOperationBase &symbol)
Gets and sets the name of a symbol op.
Definition: IRCore.cpp:1947
pybind11::object dunderGetItem(const std::string &name)
Returns the symbol (opview) with the given name, throws if there is no such symbol in the table.
Definition: IRCore.cpp:1910
static MlirAttribute getVisibility(PyOperationBase &symbol)
Gets and sets the visibility of a symbol op.
Definition: IRCore.cpp:1974
static void walkSymbolTables(PyOperationBase &from, bool allSymUsesVisible, pybind11::object callback)
Walks all symbol tables under and including 'from'.
Definition: IRCore.cpp:2015
Tracks an entry in the thread context stack.
Definition: IRModule.h:104
static PyThreadContextEntry * getTopOfStack()
Stack management.
Definition: IRCore.cpp:735
static void popLocation(PyLocation &location)
Definition: IRCore.cpp:847
PyThreadContextEntry(FrameKind frameKind, pybind11::object context, pybind11::object insertionPoint, pybind11::object location)
Definition: IRModule.h:112
static pybind11::object pushContext(PyMlirContext &context)
Definition: IRCore.cpp:797
static PyLocation * getDefaultLocation()
Gets the top of stack location and returns nullptr if not defined.
Definition: IRCore.cpp:792
static void popInsertionPoint(PyInsertionPoint &insertionPoint)
Definition: IRCore.cpp:827
static void popContext(PyMlirContext &context)
Definition: IRCore.cpp:805
static PyInsertionPoint * getDefaultInsertionPoint()
Gets the top of stack insertion point and return nullptr if not defined.
Definition: IRCore.cpp:787
static pybind11::object pushInsertionPoint(PyInsertionPoint &insertionPoint)
Definition: IRCore.cpp:816
static pybind11::object pushLocation(PyLocation &location)
Definition: IRCore.cpp:838
PyMlirContext * getContext()
Definition: IRCore.cpp:764
static PyMlirContext * getDefaultContext()
Gets the top of stack context and return nullptr if not defined.
Definition: IRCore.cpp:782
static std::vector< PyThreadContextEntry > & getStack()
Gets the thread local stack.
Definition: IRCore.cpp:730
PyInsertionPoint * getInsertionPoint()
Definition: IRCore.cpp:770
A TypeID provides an efficient and unique identifier for a specific C++ type.
Definition: IRModule.h:872
MlirTypeID get()
Definition: IRModule.h:880
bool operator==(const PyTypeID &other) const
Definition: IRCore.cpp:1869
static PyTypeID createFromCapsule(pybind11::object capsule)
Creates a PyTypeID from the MlirTypeID wrapped by a capsule.
Definition: IRCore.cpp:1863
pybind11::object getCapsule()
Gets a capsule wrapping the void* within the MlirTypeID.
Definition: IRCore.cpp:1859
PyTypeID(MlirTypeID typeID)
Definition: IRModule.h:874
Wrapper around the generic MlirType.
Definition: IRModule.h:848
pybind11::object getCapsule()
Gets a capsule wrapping the void* within the MlirType.
Definition: IRCore.cpp:1843
static PyType createFromCapsule(pybind11::object capsule)
Creates a PyType from the MlirType wrapped by a capsule.
Definition: IRCore.cpp:1847
PyType(PyMlirContextRef contextRef, MlirType type)
Definition: IRModule.h:850
MlirType get() const
Definition: IRModule.h:854
bool operator==(const PyType &other) const
Definition: IRCore.cpp:1839
Wrapper around the generic MlirValue.
Definition: IRModule.h:1101
static PyValue createFromCapsule(pybind11::object capsule)
Creates a PyValue from the MlirValue wrapped by a capsule.
Definition: IRCore.cpp:1881
PyValue(PyOperationRef parentOperation, MlirValue value)
Definition: IRModule.h:1103
pybind11::object getCapsule()
Gets a capsule wrapping the void* within the MlirValue.
Definition: IRCore.cpp:1877
PyOperationRef & getParentOperation()
Definition: IRModule.h:1108
MlirDiagnosticSeverity
Severity of a diagnostic.
Definition: Diagnostics.h:32
MLIR_CAPI_EXPORTED MlirDiagnosticHandlerID mlirContextAttachDiagnosticHandler(MlirContext context, MlirDiagnosticHandler handler, void *userData, void(*deleteUserData)(void *))
Attaches the diagnostic handler to the context.
Definition: Diagnostics.cpp:56
MLIR_CAPI_EXPORTED void mlirContextDetachDiagnosticHandler(MlirContext context, MlirDiagnosticHandlerID id)
Detaches an attached diagnostic handler from the context given its identifier.
Definition: Diagnostics.cpp:72
uint64_t MlirDiagnosticHandlerID
Opaque identifier of a diagnostic handler, useful to detach a handler.
Definition: Diagnostics.h:41
MLIR_CAPI_EXPORTED void mlirOpPrintingFlagsUseLocalScope(MlirOpPrintingFlags flags)
Use local scope when printing the operation.
Definition: IR.cpp:212
MLIR_CAPI_EXPORTED void mlirDialectRegistryDestroy(MlirDialectRegistry registry)
Takes a dialect registry owned by the caller and destroys it.
Definition: IR.cpp:137
MLIR_CAPI_EXPORTED MlirType mlirAttributeGetType(MlirAttribute attribute)
Gets the type of this attribute.
Definition: IR.cpp:1021
MLIR_CAPI_EXPORTED void mlirTypePrint(MlirType type, MlirStringCallback callback, void *userData)
Prints a location by sending chunks of the string representation and forwarding userData tocallback`.
Definition: IR.cpp:1002
MLIR_CAPI_EXPORTED void mlirAttributePrint(MlirAttribute attr, MlirStringCallback callback, void *userData)
Prints an attribute by sending chunks of the string representation and forwarding userData tocallback...
Definition: IR.cpp:1040
MLIR_CAPI_EXPORTED MlirAsmState mlirAsmStateCreateForOperation(MlirOperation op, MlirOpPrintingFlags flags)
Creates new AsmState, as with AsmState the IR should not be mutated in-between using this state.
Definition: IR.cpp:145
static bool mlirBlockIsNull(MlirBlock block)
Checks whether a block is null.
Definition: IR.h:769
MLIR_CAPI_EXPORTED void mlirSymbolTableDestroy(MlirSymbolTable symbolTable)
Destroys the symbol table created with mlirSymbolTableCreate.
Definition: IR.cpp:1091
static bool mlirDialectRegistryIsNull(MlirDialectRegistry registry)
Checks if the dialect registry is null.
Definition: IR.h:236
static bool mlirRegionIsNull(MlirRegion region)
Checks whether a region is null.
Definition: IR.h:708
MLIR_CAPI_EXPORTED void mlirOpPrintingFlagsDestroy(MlirOpPrintingFlags flags)
Destroys printing flags created with mlirOpPrintingFlagsCreate.
Definition: IR.cpp:194
MLIR_CAPI_EXPORTED MlirDialectRegistry mlirDialectRegistryCreate(void)
Creates a dialect registry and transfers its ownership to the caller.
Definition: IR.cpp:133
MLIR_CAPI_EXPORTED void mlirOperationRemoveFromParent(MlirOperation op)
Removes the given operation from its parent block.
Definition: IR.cpp:498
MLIR_CAPI_EXPORTED MlirOpPrintingFlags mlirOpPrintingFlagsCreate(void)
Creates new printing flags with defaults, intended for customization.
Definition: IR.cpp:190
MLIR_CAPI_EXPORTED MlirAsmState mlirAsmStateCreateForValue(MlirValue value, MlirOpPrintingFlags flags)
Creates new AsmState from value.
Definition: IR.cpp:166
void populateIRAttributes(pybind11::module &m)
void populateIRTypes(pybind11::module &m)
PyObjectRef< PyMlirContext > PyMlirContextRef
Wrapper around MlirContext.
Definition: IRModule.h:159
void populateIRAffine(pybind11::module &m)
PyObjectRef< PyModule > PyModuleRef
Definition: IRModule.h:505
void populateIRCore(pybind11::module &m)
PyObjectRef< PyOperation > PyOperationRef
Definition: IRModule.h:581
void populateIRInterfaces(py::module &m)
This header declares functions that assist transformations in the MemRef dialect.
An opaque reference to a diagnostic, always owned by the diagnostics engine (context).
Definition: Diagnostics.h:26
A logical result value, essentially a boolean with named states.
Definition: Support.h:116
Named MLIR attribute.
Definition: IR.h:77
Accumulates into a python string from a method that accepts an MlirStringCallback.
Definition: PybindUtils.h:101
pybind11::list parts
Definition: PybindUtils.h:102
pybind11::str join()
Definition: PybindUtils.h:116
MlirStringCallback getCallback()
Definition: PybindUtils.h:106
Custom exception that allows access to error diagnostic information.
Definition: IRModule.h:1246
MLIRError(llvm::Twine message, std::vector< PyDiagnostic::DiagnosticInfo > &&errorDiagnostics={})
Definition: IRModule.h:1247
std::vector< PyDiagnostic::DiagnosticInfo > errorDiagnostics
Definition: IRModule.h:1251
Materialized diagnostic information.
Definition: IRModule.h:337
std::vector< DiagnosticInfo > notes
Definition: IRModule.h:341
RAII object that captures any error diagnostics emitted to the provided context.
Definition: IRModule.h:403
std::vector< PyDiagnostic::DiagnosticInfo > take()
Definition: IRModule.h:413
ErrorCapture(PyMlirContextRef ctx)
Definition: IRModule.h:404