rust/tests/run-make/embed-metadata/rmake.rs
Jakub Beránek 5a71da56d8 Add tests
2025-03-31 10:41:10 +02:00

86 lines
2.7 KiB
Rust

// Tests the -Zembed-metadata compiler flag.
// Tracking issue: https://github.com/rust-lang/rust/issues/139165
use run_make_support::rfs::{create_dir, remove_file, rename};
use run_make_support::{Rustc, dynamic_lib_name, path, run_in_tmpdir, rust_lib_name, rustc};
#[derive(Debug, Copy, Clone)]
enum LibraryKind {
Rlib,
Dylib,
}
impl LibraryKind {
fn crate_type(&self) -> &str {
match self {
LibraryKind::Rlib => "rlib",
LibraryKind::Dylib => "dylib",
}
}
fn add_extern(&self, rustc: &mut Rustc, dep_name: &str, dep_path: &str) {
let dep_path = match self {
LibraryKind::Dylib => format!("{dep_path}/{}", dynamic_lib_name(dep_name)),
LibraryKind::Rlib => format!("{dep_path}/{}", rust_lib_name(dep_name)),
};
rustc.extern_(dep_name, dep_path);
}
}
fn main() {
// The compiler takes different paths based on if --extern is passed or not, so we test all
// combinations (`rlib`/`dylib` x `--extern`/`no --extern`).
for kind in [LibraryKind::Rlib, LibraryKind::Dylib] {
eprintln!("Testing library kind {kind:?}");
lookup_rmeta_in_lib_dir(kind);
lookup_rmeta_through_extern(kind);
lookup_rmeta_missing(kind);
}
}
// Lookup .rmeta file in the same directory as a rlib/dylib with stub metadata.
fn lookup_rmeta_in_lib_dir(kind: LibraryKind) {
run_in_tmpdir(|| {
build_dep_rustc(kind).run();
rustc().input("foo.rs").run();
});
}
// Lookup .rmeta file when specifying the dependency using --extern.
fn lookup_rmeta_through_extern(kind: LibraryKind) {
run_in_tmpdir(|| {
// Generate libdep1.rlib and libdep1.rmeta in deps
create_dir("deps");
build_dep_rustc(kind).out_dir("deps").run();
let mut rustc = rustc();
kind.add_extern(&mut rustc, "dep1", "deps");
rustc.extern_("dep1", path("deps").join("libdep1.rmeta"));
rustc.input("foo.rs").run();
});
}
// Check the error message when the .rmeta file is missing.
fn lookup_rmeta_missing(kind: LibraryKind) {
run_in_tmpdir(|| {
create_dir("deps");
build_dep_rustc(kind).out_dir("deps").run();
let mut rustc = rustc();
kind.add_extern(&mut rustc, "dep1", "deps");
rustc.input("foo.rs").run_fail().assert_stderr_contains("only metadata stub found");
});
}
fn build_dep_rustc(kind: LibraryKind) -> Rustc {
let mut dep_rustc = rustc();
dep_rustc
.arg("-Zembed-metadata=no")
.crate_type(kind.crate_type())
.input("dep1.rs")
.emit("metadata,link");
if matches!(kind, LibraryKind::Dylib) {
dep_rustc.arg("-Cprefer-dynamic");
}
dep_rustc
}