@@ -197,12 +197,15 @@ impl SysrootDownload {
197197 } )
198198 } ;
199199
200+ let host_libdir = self . cache_directory . join ( "lib" ) ;
201+ let target_libdir = target_libdir_from_host_libdir ( & host_libdir, & self . triple ) ;
200202 let components = ToolchainComponents :: from_binaries_and_libdir (
201203 sysroot_bin ( "rustc" ) ?,
202204 Some ( sysroot_bin ( "rustdoc" ) ?) ,
203205 sysroot_bin ( "clippy-driver" ) . ok ( ) ,
204206 sysroot_bin ( "cargo" ) ?,
205- & self . cache_directory . join ( "lib" ) ,
207+ & host_libdir,
208+ & target_libdir,
206209 ) ?;
207210
208211 Ok ( Sysroot {
@@ -302,6 +305,10 @@ impl SysrootDownload {
302305 }
303306}
304307
308+ fn target_libdir_from_host_libdir ( dir : & Path , target : & str ) -> PathBuf {
309+ dir. join ( "rustlib" ) . join ( target) . join ( "lib" )
310+ }
311+
305312/// Representation of a toolchain that can be used to compile Rust programs.
306313#[ derive( Debug , Clone ) ]
307314pub struct Toolchain {
@@ -329,7 +336,6 @@ pub struct ToolchainComponents {
329336 pub cargo_configs : Vec < String > ,
330337 pub lib_rustc : Option < PathBuf > ,
331338 pub lib_std : Option < PathBuf > ,
332- pub lib_test : Option < PathBuf > ,
333339 pub lib_llvm : Option < PathBuf > ,
334340}
335341
@@ -339,7 +345,8 @@ impl ToolchainComponents {
339345 rustdoc : Option < PathBuf > ,
340346 clippy : Option < PathBuf > ,
341347 cargo : PathBuf ,
342- libdir : & Path ,
348+ host_libdir : & Path ,
349+ target_libdir : & Path ,
343350 ) -> anyhow:: Result < Self > {
344351 let mut component = ToolchainComponents {
345352 rustc,
@@ -348,36 +355,41 @@ impl ToolchainComponents {
348355 cargo,
349356 ..Default :: default ( )
350357 } ;
351- component. fill_libraries ( libdir ) ?;
358+ component. fill_libraries ( host_libdir , target_libdir ) ?;
352359 Ok ( component)
353360 }
354361
355362 /// Finds known library components in the given `dir` and stores them in `self`.
356- fn fill_libraries ( & mut self , dir : & Path ) -> anyhow:: Result < ( ) > {
357- let files: Vec < ( PathBuf , String ) > = fs:: read_dir ( dir)
358- . with_context ( || format ! ( "Cannot read lib dir `{}` to find components" , dir. display( ) ) ) ?
359- . map ( |entry| Ok ( entry?) )
360- . collect :: < anyhow:: Result < Vec < _ > > > ( ) ?
361- . into_iter ( )
362- . filter ( |entry| entry. path ( ) . is_file ( ) )
363- . filter_map ( |entry| {
364- entry
365- . path ( )
366- . file_name ( )
367- . and_then ( |s| s. to_str ( ) )
368- . map ( |s| ( entry. path ( ) , s. to_string ( ) ) )
369- } )
370- . collect ( ) ;
371-
372- for ( path, filename) in & files {
373- if path. extension ( ) == Some ( OsStr :: new ( "so" ) ) {
374- if filename. starts_with ( "librustc_driver" ) {
375- self . lib_rustc = Some ( path. clone ( ) ) ;
376- } else if filename. starts_with ( "libstd" ) {
377- self . lib_std = Some ( path. clone ( ) ) ;
378- } else if filename. starts_with ( "libtest" ) {
379- self . lib_test = Some ( path. clone ( ) ) ;
380- }
363+ fn fill_libraries ( & mut self , host_libdir : & Path , target_libdir : & Path ) -> anyhow:: Result < ( ) > {
364+ let load_files = |path : & Path | -> anyhow:: Result < Vec < ( PathBuf , String ) > > {
365+ let files = fs:: read_dir ( path)
366+ . with_context ( || {
367+ format ! (
368+ "Cannot read lib dir `{}` to find components" ,
369+ path. display( )
370+ )
371+ } ) ?
372+ . map ( |entry| Ok ( entry?) )
373+ . collect :: < anyhow:: Result < Vec < _ > > > ( ) ?
374+ . into_iter ( )
375+ . filter ( |entry| entry. path ( ) . is_file ( ) )
376+ . filter_map ( |entry| {
377+ entry
378+ . path ( )
379+ . file_name ( )
380+ . and_then ( |s| s. to_str ( ) )
381+ . map ( |s| ( entry. path ( ) , s. to_string ( ) ) )
382+ } )
383+ . collect ( ) ;
384+ Ok ( files)
385+ } ;
386+
387+ // Look for librustc_driver.so and libLLVM.so in the *host* libdir
388+ let host_files = load_files ( host_libdir) ?;
389+ for ( path, filename) in & host_files {
390+ if path. extension ( ) == Some ( OsStr :: new ( "so" ) ) && filename. starts_with ( "librustc_driver" )
391+ {
392+ self . lib_rustc = Some ( path. clone ( ) ) ;
381393 }
382394 }
383395
@@ -386,14 +398,22 @@ impl ToolchainComponents {
386398 // libLLVM.so.<version>.
387399 // So we need to check if we have the new name, and use it.
388400 // If not, we want to look up the original name.
389- let new_llvm = files
401+ let new_llvm = host_files
390402 . iter ( )
391403 . find ( |( _, filename) | filename. starts_with ( "libLLVM.so" ) ) ;
392- let old_llvm = files . iter ( ) . find ( |( path, filename) | {
404+ let old_llvm = host_files . iter ( ) . find ( |( path, filename) | {
393405 path. extension ( ) == Some ( OsStr :: new ( "so" ) ) && filename. starts_with ( "libLLVM" )
394406 } ) ;
395407 self . lib_llvm = new_llvm. or ( old_llvm) . map ( |( path, _) | path. clone ( ) ) ;
396408
409+ // Now find libstd in the *target* libdir
410+ let target_files = load_files ( target_libdir) ?;
411+ for ( path, filename) in target_files {
412+ if path. extension ( ) == Some ( OsStr :: new ( "so" ) ) && filename. starts_with ( "libstd" ) {
413+ self . lib_std = Some ( path. clone ( ) ) ;
414+ }
415+ }
416+
397417 Ok ( ( ) )
398418 }
399419}
@@ -598,10 +618,17 @@ pub fn get_local_toolchain(
598618 debug ! ( "found cargo: {:?}" , & cargo) ;
599619 cargo
600620 } ;
601- let lib_dir = get_lib_dir_from_rustc ( & rustc) . context ( "Cannot find libdir for rustc" ) ?;
621+ let host_lib_dir = get_lib_dir_from_rustc ( & rustc) . context ( "Cannot find libdir for rustc" ) ?;
622+ let target_lib_dir = target_libdir_from_host_libdir ( & host_lib_dir, & target_triple) ;
602623
603- let mut components =
604- ToolchainComponents :: from_binaries_and_libdir ( rustc, rustdoc, clippy, cargo, & lib_dir) ?;
624+ let mut components = ToolchainComponents :: from_binaries_and_libdir (
625+ rustc,
626+ rustdoc,
627+ clippy,
628+ cargo,
629+ & host_lib_dir,
630+ & target_lib_dir,
631+ ) ?;
605632 components. cargo_configs = toolchain_config. cargo_configs . to_vec ( ) ;
606633 Ok ( Toolchain {
607634 components,
@@ -649,14 +676,16 @@ pub fn create_toolchain_from_published_version(
649676 debug ! ( "Found clippy: {}" , clippy. display( ) ) ;
650677 debug ! ( "Found cargo: {}" , cargo. display( ) ) ;
651678
652- let lib_dir = get_lib_dir_from_rustc ( & rustc) ?;
679+ let host_lib_dir = get_lib_dir_from_rustc ( & rustc) ?;
680+ let target_lib_dir = target_libdir_from_host_libdir ( & host_lib_dir, target_triple) ;
653681
654682 let components = ToolchainComponents :: from_binaries_and_libdir (
655683 rustc,
656684 Some ( rustdoc) ,
657685 Some ( clippy) ,
658686 cargo,
659- & lib_dir,
687+ & host_lib_dir,
688+ & target_lib_dir,
660689 ) ?;
661690
662691 Ok ( Toolchain {
@@ -695,19 +724,24 @@ mod tests {
695724 fn fill_libraries ( ) {
696725 let mut components = ToolchainComponents :: default ( ) ;
697726
698- // create mock dir and libraries
699727 let temp_dir: tempfile:: TempDir = tempfile:: tempdir ( ) . unwrap ( ) ;
700- let lib_rustc_path = create_temp_lib_path ( "librustc_driver.so" , & temp_dir) ;
701- let lib_std_path = create_temp_lib_path ( "libstd.so" , & temp_dir) ;
702- let lib_test_path = create_temp_lib_path ( "libtest.so" , & temp_dir) ;
703- let lib_new_llvm_path =
704- create_temp_lib_path ( "libLLVM.so.18.1-rust-1.78.0-nightly" , & temp_dir) ;
728+ let host_libdir = temp_dir. path ( ) ;
729+ let target_libdir = target_libdir_from_host_libdir ( host_libdir, "foo" ) ;
730+ std:: fs:: create_dir_all ( & target_libdir) . unwrap ( ) ;
731+
732+ let lib_rustc_path = create_lib ( host_libdir, "librustc_driver.so" ) ;
733+ let lib_std_path = create_lib (
734+ & host_libdir. join ( "rustlib" ) . join ( "foo" ) . join ( "lib" ) ,
735+ "libstd.so" ,
736+ ) ;
737+ let lib_new_llvm_path = create_lib ( host_libdir, "libLLVM.so.18.1-rust-1.78.0-nightly" ) ;
705738
706- components. fill_libraries ( temp_dir. path ( ) ) . unwrap ( ) ;
739+ components
740+ . fill_libraries ( host_libdir, & target_libdir)
741+ . unwrap ( ) ;
707742
708743 assert_eq ! ( components. lib_rustc, Some ( lib_rustc_path) ) ;
709744 assert_eq ! ( components. lib_std, Some ( lib_std_path) ) ;
710- assert_eq ! ( components. lib_test, Some ( lib_test_path) ) ;
711745 assert_eq ! ( components. lib_llvm, Some ( lib_new_llvm_path) ) ;
712746 }
713747
@@ -718,18 +752,25 @@ mod tests {
718752
719753 // create mock dir and libraries
720754 let temp_dir: tempfile:: TempDir = tempfile:: tempdir ( ) . unwrap ( ) ;
721- let lib_old_llvm_path = create_temp_lib_path ( lib_old_llvm, & temp_dir) ;
755+ let host_libdir = temp_dir. path ( ) ;
756+ let target_libdir = target_libdir_from_host_libdir ( host_libdir, "foo" ) ;
757+ std:: fs:: create_dir_all ( & target_libdir) . unwrap ( ) ;
758+
759+ let lib_old_llvm_path = create_lib ( host_libdir, lib_old_llvm) ;
722760
723- components. fill_libraries ( temp_dir. path ( ) ) . unwrap ( ) ;
761+ components
762+ . fill_libraries (
763+ host_libdir,
764+ & target_libdir_from_host_libdir ( temp_dir. path ( ) , "foo" ) ,
765+ )
766+ . unwrap ( ) ;
724767
725768 assert_eq ! ( components. lib_llvm, Some ( lib_old_llvm_path) ) ;
726769 }
727770
728- fn create_temp_lib_path ( lib_name : & str , temp_dir : & tempfile:: TempDir ) -> PathBuf {
729- let lib_path = temp_dir. path ( ) . join ( lib_name) ;
730- // create mock file
771+ fn create_lib ( path : & Path , lib_name : & str ) -> PathBuf {
772+ let lib_path = path. join ( lib_name) ;
731773 File :: create ( & lib_path) . unwrap ( ) ;
732-
733774 lib_path
734775 }
735776}
0 commit comments