Skip to content

Commit 0d8252f

Browse files
committed
Revert "[MLIR][Python] use FetchContent_Declare for nanobind and remove pybind (#161230)"
This reverts commit 84a2148.
1 parent 5960f5c commit 0d8252f

File tree

18 files changed

+1082
-121
lines changed

18 files changed

+1082
-121
lines changed

.ci/all_requirements.txt

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -194,6 +194,10 @@ ml-dtypes==0.5.1 ; python_version < "3.13" \
194194
--hash=sha256:d13755f8e8445b3870114e5b6240facaa7cb0c3361e54beba3e07fa912a6e12b \
195195
--hash=sha256:fd918d4e6a4e0c110e2e05be7a7814d10dc1b95872accbf6512b80a109b71ae1
196196
# via -r mlir/python/requirements.txt
197+
nanobind==2.9.2 \
198+
--hash=sha256:c37957ffd5eac7eda349cff3622ecd32e5ee1244ecc912c99b5bc8188bafd16e \
199+
--hash=sha256:e7608472de99d375759814cab3e2c94aba3f9ec80e62cfef8ced495ca5c27d6e
200+
# via -r mlir/python/requirements.txt
197201
numpy==2.0.2 \
198202
--hash=sha256:0123ffdaa88fa4ab64835dcbde75dcdf89c453c922f18dced6e27c90d1d0ec5a \
199203
--hash=sha256:11a76c372d1d37437857280aa142086476136a8c0f373b2e648ab2c8f18fb195 \
@@ -295,6 +299,10 @@ pyasn1-modules==0.4.2 \
295299
--hash=sha256:29253a9207ce32b64c3ac6600edc75368f98473906e8fd1043bd6b5b1de2c14a \
296300
--hash=sha256:677091de870a80aae844b1ca6134f54652fa2c8c5a52aa396440ac3106e941e6
297301
# via google-auth
302+
pybind11==2.13.6 \
303+
--hash=sha256:237c41e29157b962835d356b370ededd57594a26d5894a795960f0047cb5caf5 \
304+
--hash=sha256:ba6af10348c12b24e92fa086b39cfba0eff619b61ac77c406167d813b096d39a
305+
# via -r mlir/python/requirements.txt
298306
pyyaml==6.0.1 \
299307
--hash=sha256:04ac92ad1925b2cff1db0cfebffb6ffc43457495c9b3c39d3fcae417d7125dc5 \
300308
--hash=sha256:062582fca9fabdd2c8b54a3ef1c978d786e0f6b3a1510e0ac93ef59e0ddae2bc \

mlir/cmake/modules/AddMLIRPython.cmake

Lines changed: 72 additions & 55 deletions
Original file line numberDiff line numberDiff line change
@@ -123,12 +123,12 @@ function(mlir_generate_type_stubs)
123123
"IMPORT_PATHS;DEPENDS_TARGETS;OUTPUTS;DEPENDS_TARGET_SRC_DEPS"
124124
${ARGN})
125125

126-
# for people installing a distro (e.g., pip install) of nanobind
126+
# for people doing find_package(nanobind)
127127
if(EXISTS ${nanobind_DIR}/../src/stubgen.py)
128128
set(NB_STUBGEN "${nanobind_DIR}/../src/stubgen.py")
129129
elseif(EXISTS ${nanobind_DIR}/../stubgen.py)
130130
set(NB_STUBGEN "${nanobind_DIR}/../stubgen.py")
131-
# for people using nanobind git source tree (e.g., FetchContent_Declare and FetchContent_MakeAvailable)
131+
# for people using FetchContent_Declare and FetchContent_MakeAvailable
132132
elseif(EXISTS ${nanobind_SOURCE_DIR}/src/stubgen.py)
133133
set(NB_STUBGEN "${nanobind_SOURCE_DIR}/src/stubgen.py")
134134
elseif(EXISTS ${nanobind_SOURCE_DIR}/stubgen.py)
@@ -226,10 +226,11 @@ endfunction()
226226
# EMBED_CAPI_LINK_LIBS: Dependent CAPI libraries that this extension depends
227227
# on. These will be collected for all extensions and put into an
228228
# aggregate dylib that is linked against.
229+
# PYTHON_BINDINGS_LIBRARY: Either pybind11 or nanobind.
229230
function(declare_mlir_python_extension name)
230231
cmake_parse_arguments(ARG
231232
""
232-
"ROOT_DIR;MODULE_NAME;ADD_TO_PARENT"
233+
"ROOT_DIR;MODULE_NAME;ADD_TO_PARENT;PYTHON_BINDINGS_LIBRARY"
233234
"SOURCES;PRIVATE_LINK_LIBS;EMBED_CAPI_LINK_LIBS"
234235
${ARGN})
235236

@@ -238,15 +239,20 @@ function(declare_mlir_python_extension name)
238239
endif()
239240
set(_install_destination "src/python/${name}")
240241

242+
if(NOT ARG_PYTHON_BINDINGS_LIBRARY)
243+
set(ARG_PYTHON_BINDINGS_LIBRARY "pybind11")
244+
endif()
245+
241246
add_library(${name} INTERFACE)
242247
set_target_properties(${name} PROPERTIES
243248
# Yes: Leading-lowercase property names are load bearing and the recommended
244249
# way to do this: https://gitlab.kitware.com/cmake/cmake/-/issues/19261
245-
EXPORT_PROPERTIES "mlir_python_SOURCES_TYPE;mlir_python_EXTENSION_MODULE_NAME;mlir_python_EMBED_CAPI_LINK_LIBS;mlir_python_DEPENDS"
250+
EXPORT_PROPERTIES "mlir_python_SOURCES_TYPE;mlir_python_EXTENSION_MODULE_NAME;mlir_python_EMBED_CAPI_LINK_LIBS;mlir_python_DEPENDS;mlir_python_BINDINGS_LIBRARY"
246251
mlir_python_SOURCES_TYPE extension
247252
mlir_python_EXTENSION_MODULE_NAME "${ARG_MODULE_NAME}"
248253
mlir_python_EMBED_CAPI_LINK_LIBS "${ARG_EMBED_CAPI_LINK_LIBS}"
249254
mlir_python_DEPENDS ""
255+
mlir_python_BINDINGS_LIBRARY "${ARG_PYTHON_BINDINGS_LIBRARY}"
250256
)
251257

252258
# Set the interface source and link_libs properties of the target
@@ -335,12 +341,14 @@ function(add_mlir_python_modules name)
335341
elseif(_source_type STREQUAL "extension")
336342
# Native CPP extension.
337343
get_target_property(_module_name ${sources_target} mlir_python_EXTENSION_MODULE_NAME)
344+
get_target_property(_bindings_library ${sources_target} mlir_python_BINDINGS_LIBRARY)
338345
# Transform relative source to based on root dir.
339346
set(_extension_target "${modules_target}.extension.${_module_name}.dso")
340347
add_mlir_python_extension(${_extension_target} "${_module_name}"
341348
INSTALL_COMPONENT ${modules_target}
342349
INSTALL_DIR "${ARG_INSTALL_PREFIX}/_mlir_libs"
343350
OUTPUT_DIRECTORY "${ARG_ROOT_PREFIX}/_mlir_libs"
351+
PYTHON_BINDINGS_LIBRARY ${_bindings_library}
344352
LINK_LIBS PRIVATE
345353
${sources_target}
346354
${ARG_COMMON_CAPI_LINK_LIBS}
@@ -745,69 +753,78 @@ endfunction()
745753
function(add_mlir_python_extension libname extname)
746754
cmake_parse_arguments(ARG
747755
""
748-
"INSTALL_COMPONENT;INSTALL_DIR;OUTPUT_DIRECTORY"
756+
"INSTALL_COMPONENT;INSTALL_DIR;OUTPUT_DIRECTORY;PYTHON_BINDINGS_LIBRARY"
749757
"SOURCES;LINK_LIBS"
750758
${ARGN})
751759
if(ARG_UNPARSED_ARGUMENTS)
752760
message(FATAL_ERROR "Unhandled arguments to add_mlir_python_extension(${libname}, ... : ${ARG_UNPARSED_ARGUMENTS}")
753761
endif()
754762

755763
# The extension itself must be compiled with RTTI and exceptions enabled.
756-
# Also, some warning classes triggered by nanobind are disabled.
764+
# Also, some warning classes triggered by pybind11 are disabled.
757765
set(eh_rtti_enable)
758766
if (MSVC)
759767
set(eh_rtti_enable /EHsc /GR)
760768
elseif(LLVM_COMPILER_IS_GCC_COMPATIBLE OR CLANG_CL)
761769
set(eh_rtti_enable -frtti -fexceptions)
762770
endif ()
763771

764-
nanobind_add_module(${libname}
765-
NB_DOMAIN ${MLIR_BINDINGS_PYTHON_NB_DOMAIN}
766-
FREE_THREADED
767-
${ARG_SOURCES}
768-
)
772+
# The actual extension library produces a shared-object or DLL and has
773+
# sources that must be compiled in accordance with pybind11 needs (RTTI and
774+
# exceptions).
775+
if(NOT DEFINED ARG_PYTHON_BINDINGS_LIBRARY OR ARG_PYTHON_BINDINGS_LIBRARY STREQUAL "pybind11")
776+
pybind11_add_module(${libname}
777+
${ARG_SOURCES}
778+
)
779+
elseif(ARG_PYTHON_BINDINGS_LIBRARY STREQUAL "nanobind")
780+
nanobind_add_module(${libname}
781+
NB_DOMAIN ${MLIR_BINDINGS_PYTHON_NB_DOMAIN}
782+
FREE_THREADED
783+
${ARG_SOURCES}
784+
)
769785

770-
if (NOT MLIR_DISABLE_CONFIGURE_PYTHON_DEV_PACKAGES
771-
AND (LLVM_COMPILER_IS_GCC_COMPATIBLE OR CLANG_CL))
772-
# Avoid some warnings from upstream nanobind.
773-
# If a superproject set MLIR_DISABLE_CONFIGURE_PYTHON_DEV_PACKAGES, let
774-
# the super project handle compile options as it wishes.
775-
get_property(NB_LIBRARY_TARGET_NAME TARGET ${libname} PROPERTY LINK_LIBRARIES)
776-
target_compile_options(${NB_LIBRARY_TARGET_NAME}
777-
PRIVATE
778-
-Wall -Wextra -Wpedantic
779-
-Wno-c++98-compat-extra-semi
780-
-Wno-cast-qual
781-
-Wno-covered-switch-default
782-
-Wno-deprecated-literal-operator
783-
-Wno-nested-anon-types
784-
-Wno-unused-parameter
785-
-Wno-zero-length-array
786-
${eh_rtti_enable})
787-
788-
target_compile_options(${libname}
789-
PRIVATE
790-
-Wall -Wextra -Wpedantic
791-
-Wno-c++98-compat-extra-semi
792-
-Wno-cast-qual
793-
-Wno-covered-switch-default
794-
-Wno-deprecated-literal-operator
795-
-Wno-nested-anon-types
796-
-Wno-unused-parameter
797-
-Wno-zero-length-array
798-
${eh_rtti_enable})
799-
endif()
786+
if (NOT MLIR_DISABLE_CONFIGURE_PYTHON_DEV_PACKAGES
787+
AND (LLVM_COMPILER_IS_GCC_COMPATIBLE OR CLANG_CL))
788+
# Avoid some warnings from upstream nanobind.
789+
# If a superproject set MLIR_DISABLE_CONFIGURE_PYTHON_DEV_PACKAGES, let
790+
# the super project handle compile options as it wishes.
791+
get_property(NB_LIBRARY_TARGET_NAME TARGET ${libname} PROPERTY LINK_LIBRARIES)
792+
target_compile_options(${NB_LIBRARY_TARGET_NAME}
793+
PRIVATE
794+
-Wall -Wextra -Wpedantic
795+
-Wno-c++98-compat-extra-semi
796+
-Wno-cast-qual
797+
-Wno-covered-switch-default
798+
-Wno-deprecated-literal-operator
799+
-Wno-nested-anon-types
800+
-Wno-unused-parameter
801+
-Wno-zero-length-array
802+
${eh_rtti_enable})
803+
804+
target_compile_options(${libname}
805+
PRIVATE
806+
-Wall -Wextra -Wpedantic
807+
-Wno-c++98-compat-extra-semi
808+
-Wno-cast-qual
809+
-Wno-covered-switch-default
810+
-Wno-deprecated-literal-operator
811+
-Wno-nested-anon-types
812+
-Wno-unused-parameter
813+
-Wno-zero-length-array
814+
${eh_rtti_enable})
815+
endif()
800816

801-
if(APPLE)
802-
# NanobindAdaptors.h uses PyClassMethod_New to build `pure_subclass`es but nanobind
803-
# doesn't declare this API as undefined in its linker flags. So we need to declare it as such
804-
# for downstream users that do not do something like `-undefined dynamic_lookup`.
805-
# Same for the rest.
806-
target_link_options(${libname} PUBLIC
807-
"LINKER:-U,_PyClassMethod_New"
808-
"LINKER:-U,_PyCode_Addr2Location"
809-
"LINKER:-U,_PyFrame_GetLasti"
810-
)
817+
if(APPLE)
818+
# NanobindAdaptors.h uses PyClassMethod_New to build `pure_subclass`es but nanobind
819+
# doesn't declare this API as undefined in its linker flags. So we need to declare it as such
820+
# for downstream users that do not do something like `-undefined dynamic_lookup`.
821+
# Same for the rest.
822+
target_link_options(${libname} PUBLIC
823+
"LINKER:-U,_PyClassMethod_New"
824+
"LINKER:-U,_PyCode_Addr2Location"
825+
"LINKER:-U,_PyFrame_GetLasti"
826+
)
827+
endif()
811828
endif()
812829

813830
target_compile_options(${libname} PRIVATE ${eh_rtti_enable})
@@ -845,11 +862,11 @@ function(add_mlir_python_extension libname extname)
845862
if(WIN32)
846863
# On Windows, pyconfig.h (and by extension python.h) hardcode the version of the
847864
# python library which will be used for linkage depending on the flavor of the build.
848-
# nanobind has a workaround which depends on the definition of Py_DEBUG (if Py_DEBUG
849-
# is not passed in as a compile definition, nanobind undefs _DEBUG when including
865+
# pybind11 has a workaround which depends on the definition of Py_DEBUG (if Py_DEBUG
866+
# is not passed in as a compile definition, pybind11 undefs _DEBUG when including
850867
# python.h, so that the release python library would be used).
851-
# Since mlir uses nanobind, we can leverage their workaround by never directly
852-
# pyconfig.h or python.h and instead relying on the nanobind headers to include the
868+
# Since mlir uses pybind11, we can leverage their workaround by never directly
869+
# pyconfig.h or python.h and instead relying on the pybind11 headers to include the
853870
# necessary python headers. This results in mlir always linking against the
854871
# release python library via the (undocumented) cmake property Python3_LIBRARY_RELEASE.
855872
target_link_libraries(${libname} PRIVATE ${Python3_LIBRARY_RELEASE})

mlir/cmake/modules/MLIRDetectPythonEnv.cmake

Lines changed: 76 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -46,20 +46,81 @@ macro(mlir_configure_python_dev_packages)
4646
message(STATUS "Found python include dirs: ${Python3_INCLUDE_DIRS}")
4747
message(STATUS "Found python libraries: ${Python3_LIBRARIES}")
4848
message(STATUS "Found numpy v${Python3_NumPy_VERSION}: ${Python3_NumPy_INCLUDE_DIRS}")
49-
message(STATUS "Python extension suffix for modules: '${Python3_SOABI}'")
50-
if(nanobind_DIR)
51-
message(STATUS "Using explicit nanobind cmake directory: ${nanobind_DIR} (-Dnanobind_DIR to change)")
52-
find_package(nanobind 2.9 CONFIG REQUIRED)
53-
else()
54-
include(FetchContent)
55-
FetchContent_Declare(
56-
nanobind
57-
GIT_REPOSITORY https://github.com/wjakob/nanobind.git
58-
GIT_TAG v2.9.0
59-
GIT_SHALLOW TRUE
60-
)
61-
FetchContent_MakeAvailable(nanobind)
62-
endif()
63-
message(STATUS "Found nanobind: ${NB_DIR}")
49+
mlir_detect_pybind11_install()
50+
find_package(pybind11 2.10 CONFIG REQUIRED)
51+
message(STATUS "Found pybind11 v${pybind11_VERSION}: ${pybind11_INCLUDE_DIR}")
52+
message(STATUS "Python prefix = '${PYTHON_MODULE_PREFIX}', "
53+
"suffix = '${PYTHON_MODULE_SUFFIX}', "
54+
"extension = '${PYTHON_MODULE_EXTENSION}")
55+
56+
mlir_detect_nanobind_install()
57+
find_package(nanobind 2.9 CONFIG REQUIRED)
58+
message(STATUS "Found nanobind v${nanobind_VERSION}: ${nanobind_INCLUDE_DIR}")
59+
message(STATUS "Python prefix = '${PYTHON_MODULE_PREFIX}', "
60+
"suffix = '${PYTHON_MODULE_SUFFIX}', "
61+
"extension = '${PYTHON_MODULE_EXTENSION}")
6462
endif()
6563
endmacro()
64+
65+
# Detects a pybind11 package installed in the current python environment
66+
# and sets variables to allow it to be found. This allows pybind11 to be
67+
# installed via pip, which typically yields a much more recent version than
68+
# the OS install, which will be available otherwise.
69+
function(mlir_detect_pybind11_install)
70+
if(pybind11_DIR)
71+
message(STATUS "Using explicit pybind11 cmake directory: ${pybind11_DIR} (-Dpybind11_DIR to change)")
72+
else()
73+
message(STATUS "Checking for pybind11 in python path...")
74+
execute_process(
75+
COMMAND "${Python3_EXECUTABLE}"
76+
-c "import pybind11;print(pybind11.get_cmake_dir(), end='')"
77+
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
78+
RESULT_VARIABLE STATUS
79+
OUTPUT_VARIABLE PACKAGE_DIR
80+
ERROR_QUIET)
81+
if(NOT STATUS EQUAL "0")
82+
message(STATUS "not found (install via 'pip install pybind11' or set pybind11_DIR)")
83+
return()
84+
endif()
85+
message(STATUS "found (${PACKAGE_DIR})")
86+
set(pybind11_DIR "${PACKAGE_DIR}" PARENT_SCOPE)
87+
endif()
88+
endfunction()
89+
90+
91+
# Detects a nanobind package installed in the current python environment
92+
# and sets variables to allow it to be found. This allows nanobind to be
93+
# installed via pip, which typically yields a much more recent version than
94+
# the OS install, which will be available otherwise.
95+
function(mlir_detect_nanobind_install)
96+
if(nanobind_DIR)
97+
message(STATUS "Using explicit nanobind cmake directory: ${nanobind_DIR} (-Dnanobind_DIR to change)")
98+
else()
99+
message(STATUS "Checking for nanobind in python path...")
100+
execute_process(
101+
COMMAND "${Python3_EXECUTABLE}"
102+
-c "import nanobind;print(nanobind.cmake_dir(), end='')"
103+
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
104+
RESULT_VARIABLE STATUS
105+
OUTPUT_VARIABLE PACKAGE_DIR
106+
ERROR_QUIET)
107+
if(NOT STATUS EQUAL "0")
108+
message(STATUS "not found (install via 'pip install nanobind' or set nanobind_DIR)")
109+
return()
110+
endif()
111+
message(STATUS "found (${PACKAGE_DIR})")
112+
set(nanobind_DIR "${PACKAGE_DIR}" PARENT_SCOPE)
113+
execute_process(
114+
COMMAND "${Python3_EXECUTABLE}"
115+
-c "import nanobind;print(nanobind.include_dir(), end='')"
116+
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
117+
RESULT_VARIABLE STATUS
118+
OUTPUT_VARIABLE PACKAGE_DIR
119+
ERROR_QUIET)
120+
if(NOT STATUS EQUAL "0")
121+
message(STATUS "not found (install via 'pip install nanobind' or set nanobind_DIR)")
122+
return()
123+
endif()
124+
set(nanobind_INCLUDE_DIR "${PACKAGE_DIR}" PARENT_SCOPE)
125+
endif()
126+
endfunction()

mlir/docs/Dialects/Linalg/OpDSL.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,15 +16,15 @@ corresponding `linalg.generic` IR for the composition.
1616
## Basic usage
1717

1818
The tool is bundled with the MLIR Python bindings. To use from the CMake build
19-
tree, MLIR must be built with Python bindings enabled
19+
tree, MLIR must be build with Python bindings enabled
2020
(`-DMLIR_ENABLE_BINDINGS_PYTHON=ON`). Then add the `python` directory in the
2121
build tree to your `PYTHONPATH` environment variable (i.e. `export
2222
PYTHONPATH=$PWD/build/tools/mlir/python_packages/mlir_core`). Optionally, use an
2323
installed MLIR package, if available, to avoid building.
2424

2525
```shell
2626
# Dump the `core_named_ops.py` module as YAML.
27-
python -m mlir.dialects.linalg.opdsl.dump_oplib.ops.core_named_ops
27+
python -m mlir.dialects.linalg.opdsl.dump_oplib .ops.core_named_ops
2828
```
2929

3030
Alternatively, run the `$PWD/build/bin/update_core_linalg_named_ops.sh` script,

mlir/examples/standalone/pyproject.toml

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,9 @@ Discussions = "https://discourse.llvm.org/"
2323
[build-system]
2424
requires = [
2525
"scikit-build-core>=0.10.7",
26-
"typing_extensions>=4.12.2"
26+
"typing_extensions>=4.12.2",
27+
"nanobind>=2.9, <3.0",
28+
"pybind11>=2.10.0, <=2.13.6",
2729
]
2830
build-backend = "scikit_build_core.build"
2931

mlir/examples/standalone/python/CMakeLists.txt

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,10 +16,27 @@ declare_mlir_dialect_python_bindings(
1616
ROOT_DIR "${CMAKE_CURRENT_SOURCE_DIR}/mlir_standalone"
1717
TD_FILE dialects/StandaloneOps.td
1818
SOURCES
19+
dialects/standalone_pybind11.py
1920
dialects/standalone_nanobind.py
2021
_mlir_libs/_standaloneDialectsNanobind/py.typed
2122
DIALECT_NAME standalone)
2223

24+
25+
declare_mlir_python_extension(StandalonePythonSources.Pybind11Extension
26+
MODULE_NAME _standaloneDialectsPybind11
27+
ADD_TO_PARENT StandalonePythonSources
28+
SOURCES
29+
StandaloneExtensionPybind11.cpp
30+
PRIVATE_LINK_LIBS
31+
LLVMSupport
32+
EMBED_CAPI_LINK_LIBS
33+
MLIRCAPIIR
34+
MLIRCAPIArith
35+
MLIRCAPITransforms
36+
StandaloneCAPI
37+
PYTHON_BINDINGS_LIBRARY pybind11
38+
)
39+
2340
declare_mlir_python_extension(StandalonePythonSources.NanobindExtension
2441
MODULE_NAME _standaloneDialectsNanobind
2542
ADD_TO_PARENT StandalonePythonSources
@@ -32,6 +49,7 @@ declare_mlir_python_extension(StandalonePythonSources.NanobindExtension
3249
MLIRCAPIArith
3350
MLIRCAPITransforms
3451
StandaloneCAPI
52+
PYTHON_BINDINGS_LIBRARY nanobind
3553
)
3654

3755

0 commit comments

Comments
 (0)