diff --git a/mlir/include/mlir-c/Bindings/Python/Interop.h b/mlir/include/mlir-c/Bindings/Python/Interop.h --- a/mlir/include/mlir-c/Bindings/Python/Interop.h +++ b/mlir/include/mlir-c/Bindings/Python/Interop.h @@ -86,6 +86,16 @@ return PyCapsule_New(ptr, MLIR_PYTHON_CAPSULE_MODULE, NULL); } +/** Extracts an MlirModule from a capsule as produced from + * mlirPythonModuleToCapsule. If the capsule is not of the right type, then + * a null module is returned (as checked via mlirModuleIsNull). In such a + * case, the Python APIs will have already set an error. */ +inline MlirModule mlirPythonCapsuleToModule(PyObject *capsule) { + void *ptr = PyCapsule_GetPointer(capsule, MLIR_PYTHON_CAPSULE_MODULE); + MlirModule module = {ptr}; + return module; +} + #ifdef __cplusplus } #endif diff --git a/mlir/lib/Bindings/Python/IRModules.cpp b/mlir/lib/Bindings/Python/IRModules.cpp --- a/mlir/lib/Bindings/Python/IRModules.cpp +++ b/mlir/lib/Bindings/Python/IRModules.cpp @@ -1492,6 +1492,13 @@ return PyModule::create(self.getRef(), module).releaseObject(); }, kContextParseDocstring) + .def( + "create_module", + [](PyMlirContext &self, PyLocation &loc) { + MlirModule module = mlirModuleCreateEmpty(loc.loc); + return PyModule::create(self.getRef(), module).releaseObject(); + }, + py::arg("loc"), "Creates an empty module") .def( "parse_attr", [](PyMlirContext &self, std::string attrSpec) { diff --git a/mlir/test/Bindings/Python/ir_module.py b/mlir/test/Bindings/Python/ir_module.py --- a/mlir/test/Bindings/Python/ir_module.py +++ b/mlir/test/Bindings/Python/ir_module.py @@ -40,6 +40,21 @@ run(testParseError) +# Verify successful parse. +# CHECK-LABEL: TEST: testCreateEmpty +# CHECK: module { +def testCreateEmpty(): + ctx = mlir.ir.Context() + loc = ctx.get_unknown_location() + module = ctx.create_module(loc) + print("CLEAR CONTEXT") + ctx = None # Ensure that module captures the context. + gc.collect() + print(str(module)) + +run(testCreateEmpty) + + # Verify round-trip of ASM that contains unicode. # Note that this does not test that the print path converts unicode properly # because MLIR asm always normalizes it to the hex encoding.