Isekai923 opened PR #14144 from Isekai923:c-api-header-install-without-cmake to bytecodealliance:main:
Currently
wasmtime-c-api-impl's build script shells out tocmake -P cmake/install-headers.cmaketo produce the C API headers inOUT_DIR. cmake is only used as a scripting engine there — it substitutes the#cmakedefinelines inconf.h.inand copies the.h/.hhfiles — but this makes cmake a build requirement for every crate that transitively depends onwasmtime-c-api-impl, most notably anything using tree-sitter'swasmfeature, even though nothing is actually compiled with cmake.This regularly surprises downstream users because the failure only appears when the build-script fingerprint is invalidated ("it built yesterday"), and the error (
failed to spawn 'cmake') doesn't look related to their code. See e.g. zed-industries/zed#18084; we hit the same thing in our project when a dev machine lost its cmake install.What this PR does
Reimplements the header install directly in
build.rsusing std only (~60 lines):
wasmtime/conf.his generated fromconf.h.inby turning each#cmakedefine WASMTIME_FEATURE_Xline into#define ...//* #undef ... */based on the correspondingCARGO_FEATURE_*env var, with CRLF newlines matching cmake'sNEWLINE_STYLE CRLF. The feature list is read from the template itself, sobuild.rsno longer needs its own copy of theWASMTIME_FEATURE_LIST.- Headers are copied recursively, preserving directory structure — the equivalent of
file(INSTALL ... FILES_MATCHING REGEX "\.hh?$").The cmake scripts themselves are untouched and still used by the standalone CMake build of the C API;
build.rssimply no longer invokes cmake.Verification
- The
OUT_DIR/includetree is byte-for-byte identical (diff -r) to the cmake-generated one, tested in both directions: all features off, and withgc-drc/cranelift/wasi/watenabled (covering#defineand/* #undef */paths, CRLF endings, and the recursive copy).cargo check -p wasmtime-c-api-implsucceeds with cmake removed fromPATH.
Isekai923 requested pchickey for a review on PR #14144.
Isekai923 requested wasmtime-core-reviewers for a review on PR #14144.
github-actions[bot] added the label wasmtime:c-api on PR #14144.
pchickey requested alexcrichton for a review on PR #14144.
pchickey unassigned pchickey from PR #14144 c-api: install headers from build.rs without requiring cmake.
pchickey commented on PR #14144:
I'm fine with this change in principle but I don't know why cmake was originally used here, so I'm passing this to Alex.
alexcrichton commented on PR #14144:
Thanks for the PR, and while I've no doubt an LLM can reproduce CMake's
configure_filelogic the original purpose here was to avoid duplicating creation of header files across build systems. I understand the motivation to reduce dependencies, but from a maintenance perspective I'd prefer to not have two ways of doing the same thing with no comments indicating that they need to be kept in sync.One strategy we've taken in the past for situations like this is to add extra CI checks to ensure that two systems intended to do the same thing actually do the same thing. For example there'd be some sort of CI check that the CMake-created set of header files is the same as the Rust-build-script-created set of header files. That would reduce the likelihood of divergence between the two, and while it wouldn't solve the duplication problem the duplication here is in theory not going to get all that much more complicated than it currently is.
Last updated: Aug 30 2026 at 09:07 UTC