From d19ff1834770e7eed7fa83b6aa073fd9c8d883f1 Mon Sep 17 00:00:00 2001 From: Bryan Donlan Date: Wed, 24 Jun 2020 21:45:55 +0000 Subject: [PATCH] Expose built cdylib artifacts in the Compilation structure This change makes it much easier to find these artifacts in a platform-independent way when writing automation around the cargo API. --- src/cargo/core/compiler/compilation.rs | 4 ++ src/cargo/core/compiler/context/mod.rs | 6 +++ tests/testsuite/build.rs | 54 +++++++++++++++++++++++++- 3 files changed, 63 insertions(+), 1 deletion(-) diff --git a/src/cargo/core/compiler/compilation.rs b/src/cargo/core/compiler/compilation.rs index daa78fbda58..e2b71ed02ef 100644 --- a/src/cargo/core/compiler/compilation.rs +++ b/src/cargo/core/compiler/compilation.rs @@ -34,6 +34,9 @@ pub struct Compilation<'cfg> { /// An array of all binaries created. pub binaries: Vec<(Unit, PathBuf)>, + /// An array of all cdylibs created. + pub cdylibs: Vec<(Unit, PathBuf)>, + /// All directories for the output of native build commands. /// /// This is currently used to drive some entries which are added to the @@ -123,6 +126,7 @@ impl<'cfg> Compilation<'cfg> { .collect(), tests: Vec::new(), binaries: Vec::new(), + cdylibs: Vec::new(), extra_env: HashMap::new(), to_doc_test: Vec::new(), cfgs: HashMap::new(), diff --git a/src/cargo/core/compiler/context/mod.rs b/src/cargo/core/compiler/context/mod.rs index c2139c43a4d..52b954dd12d 100644 --- a/src/cargo/core/compiler/context/mod.rs +++ b/src/cargo/core/compiler/context/mod.rs @@ -179,6 +179,12 @@ impl<'a, 'cfg> Context<'a, 'cfg> { self.compilation .binaries .push((unit.clone(), bindst.clone())); + } else if unit.target.is_cdylib() { + if !self.compilation.cdylibs.iter().any(|(u, _)| u == unit) { + self.compilation + .cdylibs + .push((unit.clone(), bindst.clone())); + } } } diff --git a/tests/testsuite/build.rs b/tests/testsuite/build.rs index 6953f5932c0..9d43e46cb00 100644 --- a/tests/testsuite/build.rs +++ b/tests/testsuite/build.rs @@ -1,6 +1,9 @@ //! Tests for the `cargo build` command. -use cargo::util::paths::dylib_path_envvar; +use cargo::{ + core::compiler::CompileMode, core::Workspace, ops::CompileOptions, + util::paths::dylib_path_envvar, Config, +}; use cargo_test_support::paths::{root, CargoPathExt}; use cargo_test_support::registry::Package; use cargo_test_support::{ @@ -399,6 +402,55 @@ Caused by: .run(); } +#[cargo_test] +fn cargo_compile_api_exposes_artifact_paths() { + let p = project() + .file( + "Cargo.toml", + r#" + [package] + name = "foo" + authors = [] + version = "0.0.0" + + [[bin]] + name = "the_foo_bin" + path = "src/bin.rs" + + [lib] + name = "the_foo_lib" + path = "src/foo.rs" + crate-type = ["cdylib", "rlib"] + "#, + ) + .file("src/foo.rs", "pub fn bar() {}") + .file("src/bin.rs", "pub fn main() {}") + .build(); + + let config = Config::default().unwrap(); + let ws = Workspace::new(&p.root().join("Cargo.toml"), &config).unwrap(); + let compile_options = CompileOptions::new(ws.config(), CompileMode::Build).unwrap(); + + let result = cargo::ops::compile(&ws, &compile_options).unwrap(); + + assert_eq!(1, result.binaries.len()); + assert!(result.binaries[0].1.exists()); + assert!(result.binaries[0] + .1 + .to_str() + .unwrap() + .contains("the_foo_bin")); + + assert_eq!(1, result.cdylibs.len()); + // The exact library path varies by platform, but should certainly exist at least + assert!(result.cdylibs[0].1.exists()); + assert!(result.cdylibs[0] + .1 + .to_str() + .unwrap() + .contains("the_foo_lib")); +} + #[cargo_test] fn cargo_compile_with_bin_and_proc() { let p = project()