|
| 1 | +import os |
| 2 | +import re |
| 3 | +import subprocess |
| 4 | +import sys |
| 5 | + |
| 6 | +from pybind11 import get_cmake_dir |
| 7 | +from pybind11.setup_helpers import Pybind11Extension, build_ext |
| 8 | +from setuptools import Extension, find_packages, setup |
| 9 | + |
| 10 | +__version__ = "0.0.1" |
| 11 | + |
| 12 | +# Convert distutils Windows platform specifiers to CMake -A arguments |
| 13 | +PLAT_TO_CMAKE = { |
| 14 | + "win32": "Win32", |
| 15 | + "win-amd64": "x64", |
| 16 | + "win-arm32": "ARM", |
| 17 | + "win-arm64": "ARM64", |
| 18 | +} |
| 19 | + |
| 20 | +# A CMakeExtension needs a sourcedir instead of a file list. |
| 21 | +# The name must be the _single_ output extension from the CMake build. |
| 22 | +# If you need multiple extensions, see scikit-build. |
| 23 | +class CMakeExtension(Extension): |
| 24 | + def __init__(self, name, sourcedir=""): |
| 25 | + Extension.__init__(self, name, sources=[]) |
| 26 | + self.sourcedir = os.path.abspath(sourcedir) |
| 27 | + |
| 28 | + |
| 29 | +class CMakeBuild(build_ext): |
| 30 | + def build_extension(self, ext): |
| 31 | + extdir = os.path.abspath(os.path.dirname(self.get_ext_fullpath(ext.name))) |
| 32 | + |
| 33 | + # required for auto-detection & inclusion of auxiliary "native" libs |
| 34 | + if not extdir.endswith(os.path.sep): |
| 35 | + extdir += os.path.sep |
| 36 | + |
| 37 | + # CMake lets you override the generator - we need to check this. |
| 38 | + # Can be set with Conda-Build, for example. |
| 39 | + cmake_generator = os.environ.get("CMAKE_GENERATOR", "") |
| 40 | + |
| 41 | + # Set Python_EXECUTABLE instead if you use PYBIND11_FINDPYTHON |
| 42 | + # EXAMPLE_VERSION_INFO shows you how to pass a value into the C++ code |
| 43 | + # from Python. |
| 44 | + cmake_args = [ |
| 45 | + f"-DCMAKE_LIBRARY_OUTPUT_DIRECTORY={extdir}", |
| 46 | + f"-DPYTHON_EXECUTABLE={sys.executable}", |
| 47 | + f"-DCMAKE_BUILD_TYPE=Debug", # not used on MSVC, but no harm |
| 48 | + ] |
| 49 | + build_args = [] |
| 50 | + # Adding CMake arguments set as environment variable |
| 51 | + # (needed e.g. to build for ARM OSx on conda-forge) |
| 52 | + if "CMAKE_ARGS" in os.environ: |
| 53 | + cmake_args += [item for item in os.environ["CMAKE_ARGS"].split(" ") if item] |
| 54 | + |
| 55 | + # if self.compiler.compiler_type != "msvc": |
| 56 | + # # Using Ninja-build since it a) is available as a wheel and b) |
| 57 | + # # multithreads automatically. MSVC would require all variables be |
| 58 | + # # exported for Ninja to pick it up, which is a little tricky to do. |
| 59 | + # # Users can override the generator with CMAKE_GENERATOR in CMake |
| 60 | + # # 3.15+. |
| 61 | + # if not cmake_generator: |
| 62 | + # try: |
| 63 | + # import ninja # noqa: F401 |
| 64 | + |
| 65 | + # cmake_args += ["-GNinja"] |
| 66 | + # except ImportError: |
| 67 | + # pass |
| 68 | + |
| 69 | + # else: |
| 70 | + |
| 71 | + # # Single config generators are handled "normally" |
| 72 | + # single_config = any(x in cmake_generator for x in {"NMake", "Ninja"}) |
| 73 | + |
| 74 | + # # CMake allows an arch-in-generator style for backward compatibility |
| 75 | + # contains_arch = any(x in cmake_generator for x in {"ARM", "Win64"}) |
| 76 | + |
| 77 | + # # Specify the arch if using MSVC generator, but only if it doesn't |
| 78 | + # # contain a backward-compatibility arch spec already in the |
| 79 | + # # generator name. |
| 80 | + # if not single_config and not contains_arch: |
| 81 | + # cmake_args += ["-A", PLAT_TO_CMAKE[self.plat_name]] |
| 82 | + |
| 83 | + # # Multi-config generators have a different way to specify configs |
| 84 | + # if not single_config: |
| 85 | + # cmake_args += [ |
| 86 | + # f"-DCMAKE_LIBRARY_OUTPUT_DIRECTORY_{cfg.upper()}={extdir}" |
| 87 | + # ] |
| 88 | + # build_args += ["--config", cfg] |
| 89 | + |
| 90 | + if sys.platform.startswith("darwin"): |
| 91 | + # Cross-compile support for macOS - respect ARCHFLAGS if set |
| 92 | + archs = re.findall(r"-arch (\S+)", os.environ.get("ARCHFLAGS", "")) |
| 93 | + if archs: |
| 94 | + cmake_args += ["-DCMAKE_OSX_ARCHITECTURES={}".format(";".join(archs))] |
| 95 | + |
| 96 | + # Set CMAKE_BUILD_PARALLEL_LEVEL to control the parallel build level |
| 97 | + # across all generators. |
| 98 | + if "CMAKE_BUILD_PARALLEL_LEVEL" not in os.environ: |
| 99 | + # self.parallel is a Python 3 only way to set parallel jobs by hand |
| 100 | + # using -j in the build_ext call, not supported by pip or PyPA-build. |
| 101 | + if hasattr(self, "parallel") and self.parallel: |
| 102 | + # CMake 3.12+ only. |
| 103 | + build_args += [f"-j{self.parallel}"] |
| 104 | + |
| 105 | + build_temp = os.path.join(self.build_temp, ext.name) |
| 106 | + if not os.path.exists(build_temp): |
| 107 | + os.makedirs(build_temp) |
| 108 | + |
| 109 | + subprocess.check_call(["cmake", ext.sourcedir] + cmake_args, cwd=build_temp) |
| 110 | + subprocess.check_call(["cmake", "--build", "."] + build_args, cwd=build_temp) |
| 111 | + |
| 112 | +ext_modules = [ |
| 113 | + CMakeExtension("monilog._monilog", sourcedir="src") |
| 114 | +] |
| 115 | + |
| 116 | +# ext_modules = [ |
| 117 | +# Pybind11Extension("monilog._monilog", |
| 118 | +# ["src/MoniLog.cc"], |
| 119 | +# define_macros = [('VERSION_INFO', __version__)], |
| 120 | +# cxx_std=17 |
| 121 | +# ), |
| 122 | +# ] |
| 123 | + |
| 124 | +setup( |
| 125 | + name="monilog", |
| 126 | + version=__version__, |
| 127 | + author="Dorian Leroy", |
| 128 | + |
| 129 | + url="https://github.com/cea-hpc/monilog", |
| 130 | + description="A Python logging and monitoring toolbox for C++ applications.", |
| 131 | + long_description="", |
| 132 | + packages=["monilog"], |
| 133 | + package_dir={"": "src"}, |
| 134 | + package_data={ |
| 135 | + "monilog": ["include/MoniLog.h"], |
| 136 | + }, |
| 137 | + ext_modules=ext_modules, |
| 138 | + cmdclass={"build_ext": CMakeBuild}, |
| 139 | + extras_require={"test": "pytest"}, |
| 140 | + test_suite='tests', |
| 141 | + zip_safe=False, |
| 142 | + python_requires=">=3.6", |
| 143 | +) |
0 commit comments