tqchen commented on code in PR #254: URL: https://github.com/apache/tvm-ffi/pull/254#discussion_r2981541520
########## addons/tvm-ffi-orcjit/tools/install_llvm.ps1: ########## @@ -0,0 +1,98 @@ +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, +# software distributed under the License is distributed on an +# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +# KIND, either express or implied. See the License for the +# specific language governing permissions and limitations +# under the License. + +# Install LLVM from conda-forge using micromamba (Windows). +# Usage: powershell -ExecutionPolicy Bypass -File tools/install_llvm.ps1 [version] +# version defaults to LLVM_VERSION env var, then 22.1.0 + +param( + [string]$Version = "" +) + +$ErrorActionPreference = "Stop" +Set-StrictMode -Version Latest + +if (-not $Version) { + $Version = if ($env:LLVM_VERSION) { $env:LLVM_VERSION } else { "22.1.0" } +} +$Prefix = if ($env:LLVM_PREFIX) { $env:LLVM_PREFIX } else { "C:\opt\llvm" } + +Write-Host "Installing LLVM $Version to $Prefix" + +# Install micromamba from GitHub releases (micro.mamba.pm cert expired as of 2026-03) +$MicromambaExe = "$env:TEMP\micromamba.exe" + +if (-not (Test-Path $MicromambaExe)) { + Write-Host "Downloading micromamba from GitHub releases..." + $maxRetries = 3 + for ($attempt = 1; $attempt -le $maxRetries; $attempt++) { + try { + & curl.exe -sSL -o $MicromambaExe "https://github.com/mamba-org/micromamba-releases/releases/latest/download/micromamba-win-64.exe" + if ($LASTEXITCODE -ne 0) { throw "curl failed with exit code $LASTEXITCODE" } + break + } catch { + Write-Host "Attempt $attempt/$maxRetries failed: $_" + if ($attempt -eq $maxRetries) { throw } + Start-Sleep -Seconds 5 + } + } +} +Write-Host "Using micromamba: $MicromambaExe" + +# Install LLVM and zlib. No clangdev or compiler-rt on Windows — test objects +# use C-only strategy compiled with the system compiler (MSVC), and liborc_rt +# is not used (Windows ORC JIT skips COFFPlatform). +& $MicromambaExe create -p $Prefix -c conda-forge ` + "llvmdev=$Version" ` + zlib ` + -y +if ($LASTEXITCODE -ne 0) { throw "micromamba create failed" } + +# Build static zstd from source. Review Comment: consider bringing to addons/tvm-ffi-orcjit/scripts/install_llvm.ps1, BTW, if we are using it for gh workflow, likely it can be simplified via setup miniconda action https://github.com/apache/tvm/blob/main/.github/actions/setup/action.yml#L21 ########## addons/tvm-ffi-orcjit/src/ffi/orcjit_utils.h: ########## @@ -0,0 +1,70 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +/*! + * \file orcjit_utils.h + * \brief LLVM ORC JIT utils + */ +#ifndef TVM_FFI_ORCJIT_ORCJIT_UTILS_H_ +#define TVM_FFI_ORCJIT_ORCJIT_UTILS_H_ + +#include <llvm/ExecutionEngine/Orc/LLJIT.h> +#include <llvm/Support/Error.h> +#include <tvm/ffi/string.h> + +#include <string> + +namespace tvm { +namespace ffi { +namespace orcjit { + +inline void call_llvm(llvm::Error err, const std::string& context_msg = "") { Review Comment: minor, CamelCase CallLLVM, also need documentation. To make it lazy, likely we want to keep TVM_FFI_ORCJIT_LLVM_CALL a macro like TVM_FFI_CUDA_CALL ########## addons/tvm-ffi-orcjit/tests/run_all_tests.py: ########## @@ -0,0 +1,81 @@ +#!/usr/bin/env python3 +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, +# software distributed under the License is distributed on an +# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +# KIND, either express or implied. See the License for the +# specific language governing permissions and limitations +# under the License. +"""Build test objects, run pytest, and run quick-start examples. + +Single entry point for CI. Replaces the separate cmake build step and +platform-specific test commands. + +Usage: + python run_all_tests.py [--llvm-prefix /opt/llvm] +""" + +from __future__ import annotations + +import argparse Review Comment: would be good to cross check if we can run this as normal pytest, via tvm_ffi.cpp.build_inline in temp dir and then load test ########## addons/tvm-ffi-orcjit/tests/build_test_objects.py: ########## @@ -0,0 +1,319 @@ +#!/usr/bin/env python3 +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, +# software distributed under the License is distributed on an +# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +# KIND, either express or implied. See the License for the +# specific language governing permissions and limitations +# under the License. +"""Build test objects and quick-start example via direct compiler invocation. + +Detects platform and available compilers, then builds all applicable variants: + Linux: LLVM Clang (default) + GCC + macOS: LLVM Clang (default) + Apple Clang + Windows: LLVM Clang (default) + MSVC + clang-cl + +Objects are cached: files are only recompiled when the source is newer than the +output. Re-running this script is near-instant when nothing changed. + +Usage: + python build_test_objects.py [--llvm-prefix /opt/llvm] +""" + +from __future__ import annotations + +import argparse +import os +import platform +import shutil +import subprocess +import sys +from pathlib import Path + +TESTS_DIR = Path(__file__).resolve().parent +ADDON_DIR = TESTS_DIR.parent +QUICKSTART_DIR = ADDON_DIR / "examples" / "quick-start" +SOURCES_C = TESTS_DIR / "sources" / "c" +SOURCES_CC = TESTS_DIR / "sources" / "cc" + + +# --------------------------------------------------------------------------- +# Helpers +# --------------------------------------------------------------------------- + + +def _get_tvm_ffi_includedir() -> str: + """Return the tvm-ffi C/C++ include directory.""" + result = subprocess.run( + [sys.executable, "-m", "tvm_ffi.config", "--includedir"], + capture_output=True, + text=True, + check=True, + ) + return result.stdout.strip() + + +def _needs_build(source: Path, output: Path) -> bool: + """Check whether *output* is missing or older than *source*.""" + if not output.exists(): + return True + return source.stat().st_mtime > output.stat().st_mtime + + +def _compile( + compiler: str, source: Path, output: Path, flags: list[str], include_dirs: list[str] +) -> None: + """Compile *source* → *output*. Skips if cached.""" + if not _needs_build(source, output): + return + output.parent.mkdir(parents=True, exist_ok=True) + cmd: list[str] = [compiler, *flags] + for d in include_dirs: + if compiler in ("cl", "cl.exe", "clang-cl", "clang-cl.exe"): + cmd.append(f"/I{d}") + else: + cmd += ["-I", d] + if compiler in ("cl", "cl.exe", "clang-cl", "clang-cl.exe"): + cmd += ["/c", f"/Fo{output}", str(source)] + else: + cmd += ["-c", "-o", str(output), str(source)] + print(f" {' '.join(cmd)}", flush=True) + subprocess.check_call(cmd) + + +# --------------------------------------------------------------------------- +# Variant builder +# --------------------------------------------------------------------------- + + +def _build_variant( + name: str, + *, + c_compiler: str, + cxx_compiler: str | None, + c_flags: list[str], + cxx_flags: list[str], + include_dirs: list[str], + c_outdir: Path, + cc_outdir: Path | None, +) -> None: + """Build all test objects for one compiler variant.""" + print(f"\n--- {name} ---", flush=True) + for src in sorted(SOURCES_C.glob("*.c")): + _compile(c_compiler, src, c_outdir / f"{src.stem}.o", c_flags, include_dirs) + if cxx_compiler and cc_outdir: + for src in sorted(SOURCES_CC.glob("*.cc")): + _compile(cxx_compiler, src, cc_outdir / f"{src.stem}.o", cxx_flags, include_dirs) + + +# --------------------------------------------------------------------------- +# Platform dispatch +# --------------------------------------------------------------------------- + + +def _default_llvm_prefix() -> str: + if platform.system() == "Windows": + return "C:/opt/llvm" + return "/opt/llvm" + + +def _find_llvm_bin(prefix: str) -> Path: + """Return the LLVM bin directory under *prefix*.""" + p = Path(prefix) + # conda-forge on Windows: Library/bin; elsewhere: bin + win_lib = p / "Library" / "bin" + if win_lib.exists(): + return win_lib + return p / "bin" + + +def _base_flags(system: str, machine: str) -> tuple[list[str], list[str]]: + """Return (c_flags, cxx_flags) base lists for *system*.""" + c: list[str] = ["-O2"] + cxx: list[str] = ["-std=c++17", "-O2"] + if system != "Windows": + c.append("-fPIC") + cxx.append("-fPIC") + if machine in ("aarch64", "arm64"): + c.append("-mno-outline-atomics") + cxx.append("-mno-outline-atomics") + return c, cxx + + +def _build_all(llvm_prefix: str) -> None: Review Comment: would be good to cross check if we can leverage (enhance) tvm_ffi.cpp.build_inline here(cc @yaoyaoding ) ########## addons/tvm-ffi-orcjit/tools/install_llvm.sh: ########## @@ -0,0 +1,73 @@ +#!/bin/bash +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, +# software distributed under the License is distributed on an +# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +# KIND, either express or implied. See the License for the +# specific language governing permissions and limitations +# under the License. + +# Install LLVM from conda-forge using micromamba. +# Usage: bash tools/install_llvm.sh [version] +# version defaults to LLVM_VERSION env var, then 22.1.0 +set -ex Review Comment: simplify via setup-miniconda action -- This is an automated message from the Apache Git Service. To respond to the message, please log on to GitHub and use the URL above to go to the specific comment. To unsubscribe, e-mail: [email protected] For queries about this service, please contact Infrastructure at: [email protected] --------------------------------------------------------------------- To unsubscribe, e-mail: [email protected] For additional commands, e-mail: [email protected]
