From d8ad7d3bb9c184faeb300e5885574fe0cdf7f2f3 Mon Sep 17 00:00:00 2001 From: yuchuan Date: Mon, 5 Oct 2026 20:51:09 -0400 Subject: [PATCH 1/2] update the doc. Signed-off-by: yuchuan --- docs/guides/rust_lang_guide.md | 4 ++-- rust/README.md | 4 ++-- rust/tvm-ffi/build.rs | 10 ++++++---- 3 files changed, 10 insertions(+), 8 deletions(-) diff --git a/docs/guides/rust_lang_guide.md b/docs/guides/rust_lang_guide.md index 015dea10e..9c8691212 100644 --- a/docs/guides/rust_lang_guide.md +++ b/docs/guides/rust_lang_guide.md @@ -48,11 +48,11 @@ Add to your `Cargo.toml`: tvm-ffi = { path = "path/to/tvm-ffi/rust/tvm-ffi" } ``` -For published versions (when available): +For published versions: ```toml [dependencies] -tvm-ffi = "0.1.0-alpha.0" +tvm-ffi = "0.1.14" ``` ### Environment Setup diff --git a/rust/README.md b/rust/README.md index 31f3fb01b..84a584c71 100644 --- a/rust/README.md +++ b/rust/README.md @@ -53,9 +53,9 @@ The build will: - Query `tvm-ffi-config --libdir` to add the appropriate link search path. - Link against `tvm_ffi`. -- Update the appropriate dynamic loader path environment variable for `cargo run` and `cargo test`. +- Update the appropriate dynamic loader path environment variable for `cargo run` and `cargo test` within this workspace. -For running downstream applications, you need to set the `LD_LIBRARY_PATH` so `libtvm_ffi` is available in the path. +Downstream crates do not inherit this: set the `LD_LIBRARY_PATH` so `libtvm_ffi` is available in the path, also for `cargo run` and `cargo test`. ```bash export LD_LIBRARY_PATH=${LD_LIBRARY_PATH}:`tvm-ffi-config --libdir` diff --git a/rust/tvm-ffi/build.rs b/rust/tvm-ffi/build.rs index 7209745bd..458ca740b 100644 --- a/rust/tvm-ffi/build.rs +++ b/rust/tvm-ffi/build.rs @@ -63,10 +63,12 @@ fn update_ld_library_path(lib_dir: &str) { fn main() { // Run `mylib-config --libdir` to get the library path - let config_output = Command::new("tvm-ffi-config") - .arg("--libdir") - .output() - .expect("Failed to run tvm-ffi-config"); + let config_output = match Command::new("tvm-ffi-config").arg("--libdir").output() { + Ok(output) => output, + // docs.rs (and docs/conf.py) build the documentation without tvm-ffi installed. + Err(_) if env::var_os("DOCS_RS").is_some() => return, + Err(err) => panic!("Failed to run tvm-ffi-config: {err}"), + }; let lib_dir = String::from_utf8(config_output.stdout) .expect("Invalid UTF-8 output from tvm-ffi-config") .trim() From 5f6ae7a328ac715188724d940226b3d9e5bdba77 Mon Sep 17 00:00:00 2001 From: yuchuan Date: Mon, 5 Oct 2026 21:08:45 -0400 Subject: [PATCH 2/2] enhance the build. Signed-off-by: yuchuan --- rust/tvm-ffi/build.rs | 62 ++++++++++++++++++++++++++++++++++--------- 1 file changed, 49 insertions(+), 13 deletions(-) diff --git a/rust/tvm-ffi/build.rs b/rust/tvm-ffi/build.rs index 458ca740b..4c9e8b481 100644 --- a/rust/tvm-ffi/build.rs +++ b/rust/tvm-ffi/build.rs @@ -49,6 +49,7 @@ fn update_ld_library_path(lib_dir: &str) { return; } // Get the current value of the environment variable at build time (if any) + println!("cargo:rerun-if-env-changed={}", os_env_var); let current_val = env::var(os_env_var).unwrap_or_else(|_| String::new()); // Use platform-specific separator let separator = if os_env_var == "PATH" { ";" } else { ":" }; @@ -62,20 +63,55 @@ fn update_ld_library_path(lib_dir: &str) { } fn main() { - // Run `mylib-config --libdir` to get the library path - let config_output = match Command::new("tvm-ffi-config").arg("--libdir").output() { - Ok(output) => output, - // docs.rs (and docs/conf.py) build the documentation without tvm-ffi installed. - Err(_) if env::var_os("DOCS_RS").is_some() => return, - Err(err) => panic!("Failed to run tvm-ffi-config: {err}"), + // docs.rs builds the documentation without tvm-ffi installed, and so does + // docs/conf.py, which sets DOCS_RS as docs.rs does. Cargo sets RUSTDOC for + // every build script, so it cannot tell a documentation build apart. + let docs_only = env::var_os("DOCS_RS").is_some(); + println!("cargo:rerun-if-env-changed=DOCS_RS"); + // The library directory comes from the tvm-ffi-config found on PATH. + println!("cargo:rerun-if-env-changed=PATH"); + println!("cargo:rerun-if-changed=build.rs"); + + // Run `tvm-ffi-config --libdir` to get the library path + let found = match Command::new("tvm-ffi-config").arg("--libdir").output() { + Ok(output) if output.status.success() => { + let lib_dir = String::from_utf8(output.stdout) + .unwrap_or_default() + .trim() + .to_string(); + if lib_dir.is_empty() { + Err("`tvm-ffi-config --libdir` printed no library directory".to_string()) + } else { + Ok(lib_dir) + } + } + Ok(output) => Err(format!( + "`tvm-ffi-config --libdir` failed ({}): {}", + output.status, + String::from_utf8_lossy(&output.stderr).trim() + )), + Err(err) => Err(format!("could not run `tvm-ffi-config`: {err}")), + }; + let lib_dir = match found { + Ok(lib_dir) => lib_dir, + Err(reason) if docs_only => { + println!( + "cargo:warning={reason}; not setting the loader path for a documentation build" + ); + return; + } + Err(reason) => panic!( + "{reason}. tvm-ffi sets the dynamic loader path for `cargo run` and `cargo test` \ + from the directory that `tvm-ffi-config --libdir` prints: install tvm-ffi (e.g. \ + `pip install apache-tvm-ffi`) and put tvm-ffi-config on PATH. To build \ + documentation only, set DOCS_RS=1." + ), }; - let lib_dir = String::from_utf8(config_output.stdout) - .expect("Invalid UTF-8 output from tvm-ffi-config") - .trim() - .to_string(); - // update the LD_LIBRARY_PATH environment variable - // note that we will also need to update ld_library_path for - // the cases here besides the tvm-ffi-sys crate so cargo test works out of the box + + // Let `cargo run` and `cargo test` in this workspace find libtvm_ffi. Cargo only + // forwards a package's own build-script environment to the binaries it runs, so + // the tvm-ffi-sys build script cannot do this for us, and downstream crates set + // the loader path themselves (see ../README.md). update_ld_library_path(&lib_dir); // generate the example library generate_example_lib();