22
33use std:: iter;
44use std:: path:: PathBuf ;
5+ use std:: str:: from_utf8;
56use std:: { ops, process:: Command } ;
67
78use anyhow:: { Context , Result } ;
@@ -98,6 +99,8 @@ pub struct CargoConfig {
9899 pub wrap_rustc_in_build_scripts : bool ,
99100
100101 pub run_build_script_command : Option < Vec < String > > ,
102+
103+ pub extra_env : FxHashMap < String , String > ,
101104}
102105
103106impl CargoConfig {
@@ -263,8 +266,8 @@ impl CargoWorkspace {
263266 let target = config
264267 . target
265268 . clone ( )
266- . or_else ( || cargo_config_build_target ( cargo_toml) )
267- . or_else ( || rustc_discover_host_triple ( cargo_toml) ) ;
269+ . or_else ( || cargo_config_build_target ( cargo_toml, config ) )
270+ . or_else ( || rustc_discover_host_triple ( cargo_toml, config ) ) ;
268271
269272 let mut meta = MetadataCommand :: new ( ) ;
270273 meta. cargo_path ( toolchain:: cargo ( ) ) ;
@@ -292,8 +295,27 @@ impl CargoWorkspace {
292295 // unclear whether cargo itself supports it.
293296 progress ( "metadata" . to_string ( ) ) ;
294297
295- let meta =
296- meta. exec ( ) . with_context ( || format ! ( "Failed to run `{:?}`" , meta. cargo_command( ) ) ) ?;
298+ fn exec_with_env (
299+ command : & cargo_metadata:: MetadataCommand ,
300+ extra_env : & FxHashMap < String , String > ,
301+ ) -> Result < cargo_metadata:: Metadata , cargo_metadata:: Error > {
302+ let mut command = command. cargo_command ( ) ;
303+ command. envs ( extra_env) ;
304+ let output = command. output ( ) ?;
305+ if !output. status . success ( ) {
306+ return Err ( cargo_metadata:: Error :: CargoMetadata {
307+ stderr : String :: from_utf8 ( output. stderr ) ?,
308+ } ) ;
309+ }
310+ let stdout = from_utf8 ( & output. stdout ) ?
311+ . lines ( )
312+ . find ( |line| line. starts_with ( '{' ) )
313+ . ok_or ( cargo_metadata:: Error :: NoJson ) ?;
314+ cargo_metadata:: MetadataCommand :: parse ( stdout)
315+ }
316+
317+ let meta = exec_with_env ( & meta, & config. extra_env )
318+ . with_context ( || format ! ( "Failed to run `{:?}`" , meta. cargo_command( ) ) ) ?;
297319
298320 Ok ( meta)
299321 }
@@ -463,8 +485,9 @@ impl CargoWorkspace {
463485 }
464486}
465487
466- fn rustc_discover_host_triple ( cargo_toml : & ManifestPath ) -> Option < String > {
488+ fn rustc_discover_host_triple ( cargo_toml : & ManifestPath , config : & CargoConfig ) -> Option < String > {
467489 let mut rustc = Command :: new ( toolchain:: rustc ( ) ) ;
490+ rustc. envs ( & config. extra_env ) ;
468491 rustc. current_dir ( cargo_toml. parent ( ) ) . arg ( "-vV" ) ;
469492 tracing:: debug!( "Discovering host platform by {:?}" , rustc) ;
470493 match utf8_stdout ( rustc) {
@@ -486,8 +509,9 @@ fn rustc_discover_host_triple(cargo_toml: &ManifestPath) -> Option<String> {
486509 }
487510}
488511
489- fn cargo_config_build_target ( cargo_toml : & ManifestPath ) -> Option < String > {
512+ fn cargo_config_build_target ( cargo_toml : & ManifestPath , config : & CargoConfig ) -> Option < String > {
490513 let mut cargo_config = Command :: new ( toolchain:: cargo ( ) ) ;
514+ cargo_config. envs ( & config. extra_env ) ;
491515 cargo_config
492516 . current_dir ( cargo_toml. parent ( ) )
493517 . args ( & [ "-Z" , "unstable-options" , "config" , "get" , "build.target" ] )
0 commit comments