Skip to main content

revmc_build/
lib.rs

1#![doc = include_str!("../README.md")]
2#![cfg_attr(not(test), warn(unused_extern_crates))]
3#![cfg_attr(docsrs, feature(doc_cfg))]
4
5// Must be kept in sync with `remvc-builtins`.
6const MANGLE_PREFIX: &str = "__revmc_builtin_";
7
8/// Emits the linker flag to export all the necessary symbols.
9pub fn emit() {
10    let target_vendor = std::env::var("CARGO_CFG_TARGET_VENDOR").unwrap();
11    println!("cargo:rustc-link-arg={}", link_arg(&target_vendor));
12}
13
14fn link_arg(target_vendor: &str) -> String {
15    if target_vendor == "apple" {
16        // Mach-O C symbols have a leading `_`, so `__revmc_builtin_*` becomes `___revmc_builtin_*`.
17        format!("-Wl,-exported_symbol,_{MANGLE_PREFIX}*")
18    } else {
19        format!("-Wl,--export-dynamic-symbol,{MANGLE_PREFIX}*")
20    }
21}
22
23#[cfg(test)]
24mod tests {
25    use super::{emit, link_arg};
26
27    #[test]
28    fn emits() {
29        // SAFETY: These tests do not spawn threads or read this environment variable concurrently.
30        unsafe { std::env::set_var("CARGO_CFG_TARGET_VENDOR", "unknown") };
31        emit();
32    }
33
34    #[test]
35    fn emits_macho_export_for_apple_targets() {
36        assert_eq!(link_arg("apple"), "-Wl,-exported_symbol,___revmc_builtin_*");
37    }
38
39    #[test]
40    fn emits_elf_export_for_other_targets() {
41        assert_eq!(link_arg("unknown"), "-Wl,--export-dynamic-symbol,__revmc_builtin_*");
42    }
43}