@@ -13,8 +13,8 @@ use serde_json::from_value;
13
13
use span:: Edition ;
14
14
use toolchain:: Tool ;
15
15
16
- use crate :: { utf8_stdout, ManifestPath , Sysroot , SysrootQueryMetadata } ;
17
16
use crate :: { CfgOverrides , InvocationStrategy } ;
17
+ use crate :: { ManifestPath , Sysroot , SysrootQueryMetadata } ;
18
18
19
19
/// [`CargoWorkspace`] represents the logical structure of, well, a Cargo
20
20
/// workspace. It pretty closely mirrors `cargo metadata` output.
@@ -251,6 +251,18 @@ impl TargetKind {
251
251
}
252
252
}
253
253
254
+ #[ derive( Default , Clone , Debug , PartialEq , Eq ) ]
255
+ pub struct CargoMetadataConfig {
256
+ /// List of features to activate.
257
+ pub features : CargoFeatures ,
258
+ /// rustc targets
259
+ pub targets : Vec < String > ,
260
+ /// Extra args to pass to the cargo command.
261
+ pub extra_args : Vec < String > ,
262
+ /// Extra env vars to set when invoking the cargo command
263
+ pub extra_env : FxHashMap < String , String > ,
264
+ }
265
+
254
266
// Deserialize helper for the cargo metadata
255
267
#[ derive( Deserialize , Default ) ]
256
268
struct PackageMetadata {
@@ -265,7 +277,7 @@ impl CargoWorkspace {
265
277
pub fn fetch_metadata (
266
278
cargo_toml : & ManifestPath ,
267
279
current_dir : & AbsPath ,
268
- config : & CargoConfig ,
280
+ config : & CargoMetadataConfig ,
269
281
sysroot : & Sysroot ,
270
282
locked : bool ,
271
283
progress : & dyn Fn ( String ) ,
@@ -276,14 +288,12 @@ impl CargoWorkspace {
276
288
fn fetch_metadata_ (
277
289
cargo_toml : & ManifestPath ,
278
290
current_dir : & AbsPath ,
279
- config : & CargoConfig ,
291
+ config : & CargoMetadataConfig ,
280
292
sysroot : & Sysroot ,
281
293
locked : bool ,
282
294
no_deps : bool ,
283
295
progress : & dyn Fn ( String ) ,
284
296
) -> anyhow:: Result < ( cargo_metadata:: Metadata , Option < anyhow:: Error > ) > {
285
- let targets = find_list_of_build_targets ( config, cargo_toml, sysroot) ;
286
-
287
297
let cargo = sysroot. tool ( Tool :: Cargo ) ;
288
298
let mut meta = MetadataCommand :: new ( ) ;
289
299
meta. cargo_path ( cargo. get_program ( ) ) ;
@@ -319,12 +329,9 @@ impl CargoWorkspace {
319
329
}
320
330
}
321
331
322
- if !targets. is_empty ( ) {
323
- other_options. append (
324
- & mut targets
325
- . into_iter ( )
326
- . flat_map ( |target| [ "--filter-platform" . to_owned ( ) , target] )
327
- . collect ( ) ,
332
+ if !config. targets . is_empty ( ) {
333
+ other_options. extend (
334
+ config. targets . iter ( ) . flat_map ( |it| [ "--filter-platform" . to_owned ( ) , it. clone ( ) ] ) ,
328
335
) ;
329
336
}
330
337
// The manifest is a rust file, so this means its a script manifest
@@ -596,79 +603,3 @@ impl CargoWorkspace {
596
603
self . is_virtual_workspace
597
604
}
598
605
}
599
-
600
- fn find_list_of_build_targets (
601
- config : & CargoConfig ,
602
- cargo_toml : & ManifestPath ,
603
- sysroot : & Sysroot ,
604
- ) -> Vec < String > {
605
- if let Some ( target) = & config. target {
606
- return [ target. into ( ) ] . to_vec ( ) ;
607
- }
608
-
609
- let build_targets = cargo_config_build_target ( cargo_toml, & config. extra_env , sysroot) ;
610
- if !build_targets. is_empty ( ) {
611
- return build_targets;
612
- }
613
-
614
- rustc_discover_host_triple ( cargo_toml, & config. extra_env , sysroot) . into_iter ( ) . collect ( )
615
- }
616
-
617
- fn rustc_discover_host_triple (
618
- cargo_toml : & ManifestPath ,
619
- extra_env : & FxHashMap < String , String > ,
620
- sysroot : & Sysroot ,
621
- ) -> Option < String > {
622
- let mut rustc = sysroot. tool ( Tool :: Rustc ) ;
623
- rustc. envs ( extra_env) ;
624
- rustc. current_dir ( cargo_toml. parent ( ) ) . arg ( "-vV" ) ;
625
- tracing:: debug!( "Discovering host platform by {:?}" , rustc) ;
626
- match utf8_stdout ( rustc) {
627
- Ok ( stdout) => {
628
- let field = "host: " ;
629
- let target = stdout. lines ( ) . find_map ( |l| l. strip_prefix ( field) ) ;
630
- if let Some ( target) = target {
631
- Some ( target. to_owned ( ) )
632
- } else {
633
- // If we fail to resolve the host platform, it's not the end of the world.
634
- tracing:: info!( "rustc -vV did not report host platform, got:\n {}" , stdout) ;
635
- None
636
- }
637
- }
638
- Err ( e) => {
639
- tracing:: warn!( "Failed to discover host platform: {}" , e) ;
640
- None
641
- }
642
- }
643
- }
644
-
645
- fn cargo_config_build_target (
646
- cargo_toml : & ManifestPath ,
647
- extra_env : & FxHashMap < String , String > ,
648
- sysroot : & Sysroot ,
649
- ) -> Vec < String > {
650
- let mut cargo_config = sysroot. tool ( Tool :: Cargo ) ;
651
- cargo_config. envs ( extra_env) ;
652
- cargo_config
653
- . current_dir ( cargo_toml. parent ( ) )
654
- . args ( [ "-Z" , "unstable-options" , "config" , "get" , "build.target" ] )
655
- . env ( "RUSTC_BOOTSTRAP" , "1" ) ;
656
- // if successful we receive `build.target = "target-triple"`
657
- // or `build.target = ["<target 1>", ..]`
658
- tracing:: debug!( "Discovering cargo config target by {:?}" , cargo_config) ;
659
- utf8_stdout ( cargo_config) . map ( parse_output_cargo_config_build_target) . unwrap_or_default ( )
660
- }
661
-
662
- fn parse_output_cargo_config_build_target ( stdout : String ) -> Vec < String > {
663
- let trimmed = stdout. trim_start_matches ( "build.target = " ) . trim_matches ( '"' ) ;
664
-
665
- if !trimmed. starts_with ( '[' ) {
666
- return [ trimmed. to_owned ( ) ] . to_vec ( ) ;
667
- }
668
-
669
- let res = serde_json:: from_str ( trimmed) ;
670
- if let Err ( e) = & res {
671
- tracing:: warn!( "Failed to parse `build.target` as an array of target: {}`" , e) ;
672
- }
673
- res. unwrap_or_default ( )
674
- }
0 commit comments