Take the original extra-filename passed to a crate into account when
resolving it as a dependency. Fixes #46816
This commit is contained in:
parent
9942012f41
commit
bd8154784e
|
@ -589,6 +589,7 @@ define_dep_nodes!( <'tcx>
|
|||
[input] CrateDisambiguator(CrateNum),
|
||||
[input] CrateHash(CrateNum),
|
||||
[input] OriginalCrateName(CrateNum),
|
||||
[input] ExtraFileName(CrateNum),
|
||||
|
||||
[] ImplementationsOfTrait { krate: CrateNum, trait_id: DefId },
|
||||
[] AllTraitImplementations(CrateNum),
|
||||
|
|
|
@ -466,6 +466,12 @@ impl<'tcx> QueryDescription<'tcx> for queries::original_crate_name<'tcx> {
|
|||
}
|
||||
}
|
||||
|
||||
impl<'tcx> QueryDescription<'tcx> for queries::extra_filename<'tcx> {
|
||||
fn describe(_tcx: TyCtxt, _: CrateNum) -> String {
|
||||
format!("looking up the extra filename for a crate")
|
||||
}
|
||||
}
|
||||
|
||||
impl<'tcx> QueryDescription<'tcx> for queries::implementations_of_trait<'tcx> {
|
||||
fn describe(_tcx: TyCtxt, _: (CrateNum, DefId)) -> String {
|
||||
format!("looking up implementations of a trait in a crate")
|
||||
|
|
|
@ -328,6 +328,7 @@ define_maps! { <'tcx>
|
|||
[] fn crate_disambiguator: CrateDisambiguator(CrateNum) -> CrateDisambiguator,
|
||||
[] fn crate_hash: CrateHash(CrateNum) -> Svh,
|
||||
[] fn original_crate_name: OriginalCrateName(CrateNum) -> Symbol,
|
||||
[] fn extra_filename: ExtraFileName(CrateNum) -> String,
|
||||
|
||||
[] fn implementations_of_trait: implementations_of_trait_node((CrateNum, DefId))
|
||||
-> Lrc<Vec<DefId>>,
|
||||
|
|
|
@ -881,6 +881,7 @@ pub fn force_from_dep_node<'a, 'gcx, 'lcx>(tcx: TyCtxt<'a, 'gcx, 'lcx>,
|
|||
DepKind::CrateDisambiguator => { force!(crate_disambiguator, krate!()); }
|
||||
DepKind::CrateHash => { force!(crate_hash, krate!()); }
|
||||
DepKind::OriginalCrateName => { force!(original_crate_name, krate!()); }
|
||||
DepKind::ExtraFileName => { force!(extra_filename, krate!()); }
|
||||
|
||||
DepKind::AllTraitImplementations => {
|
||||
force!(all_trait_implementations, krate!());
|
||||
|
|
|
@ -262,6 +262,7 @@ impl<'a> CrateLoader<'a> {
|
|||
ident: Symbol,
|
||||
name: Symbol,
|
||||
hash: Option<&Svh>,
|
||||
extra_filename: Option<&str>,
|
||||
span: Span,
|
||||
path_kind: PathKind,
|
||||
mut dep_kind: DepKind)
|
||||
|
@ -277,6 +278,7 @@ impl<'a> CrateLoader<'a> {
|
|||
ident,
|
||||
crate_name: name,
|
||||
hash: hash.map(|a| &*a),
|
||||
extra_filename: extra_filename,
|
||||
filesearch: self.sess.target_filesearch(path_kind),
|
||||
target: &self.sess.target.target,
|
||||
triple: &self.sess.opts.target_triple,
|
||||
|
@ -409,7 +411,8 @@ impl<'a> CrateLoader<'a> {
|
|||
::std::iter::once(krate).chain(crate_root.crate_deps
|
||||
.decode(metadata)
|
||||
.map(|dep| {
|
||||
debug!("resolving dep crate {} hash: `{}`", dep.name, dep.hash);
|
||||
info!("resolving dep crate {} hash: `{}` extra filename: `{}`", dep.name, dep.hash,
|
||||
dep.extra_filename);
|
||||
if dep.kind == DepKind::UnexportedMacrosOnly {
|
||||
return krate;
|
||||
}
|
||||
|
@ -418,7 +421,8 @@ impl<'a> CrateLoader<'a> {
|
|||
_ => dep.kind,
|
||||
};
|
||||
let (local_cnum, ..) = self.resolve_crate(
|
||||
root, dep.name, dep.name, Some(&dep.hash), span, PathKind::Dependency, dep_kind,
|
||||
root, dep.name, dep.name, Some(&dep.hash), Some(&dep.extra_filename), span,
|
||||
PathKind::Dependency, dep_kind,
|
||||
);
|
||||
local_cnum
|
||||
})).collect()
|
||||
|
@ -437,6 +441,7 @@ impl<'a> CrateLoader<'a> {
|
|||
ident: orig_name,
|
||||
crate_name: rename,
|
||||
hash: None,
|
||||
extra_filename: None,
|
||||
filesearch: self.sess.host_filesearch(PathKind::Crate),
|
||||
target: &self.sess.host,
|
||||
triple: &host_triple,
|
||||
|
@ -664,7 +669,7 @@ impl<'a> CrateLoader<'a> {
|
|||
|
||||
let dep_kind = DepKind::Implicit;
|
||||
let (cnum, data) =
|
||||
self.resolve_crate(&None, name, name, None, DUMMY_SP, PathKind::Crate, dep_kind);
|
||||
self.resolve_crate(&None, name, name, None, None, DUMMY_SP, PathKind::Crate, dep_kind);
|
||||
|
||||
// Sanity check the loaded crate to ensure it is indeed a panic runtime
|
||||
// and the panic strategy is indeed what we thought it was.
|
||||
|
@ -771,7 +776,7 @@ impl<'a> CrateLoader<'a> {
|
|||
let symbol = Symbol::intern(name);
|
||||
let dep_kind = DepKind::Explicit;
|
||||
let (_, data) =
|
||||
self.resolve_crate(&None, symbol, symbol, None, DUMMY_SP,
|
||||
self.resolve_crate(&None, symbol, symbol, None, None, DUMMY_SP,
|
||||
PathKind::Crate, dep_kind);
|
||||
|
||||
// Sanity check the loaded crate to ensure it is indeed a sanitizer runtime
|
||||
|
@ -794,7 +799,7 @@ impl<'a> CrateLoader<'a> {
|
|||
let symbol = Symbol::intern("profiler_builtins");
|
||||
let dep_kind = DepKind::Implicit;
|
||||
let (_, data) =
|
||||
self.resolve_crate(&None, symbol, symbol, None, DUMMY_SP,
|
||||
self.resolve_crate(&None, symbol, symbol, None, None, DUMMY_SP,
|
||||
PathKind::Crate, dep_kind);
|
||||
|
||||
// Sanity check the loaded crate to ensure it is indeed a profiler runtime
|
||||
|
@ -909,6 +914,7 @@ impl<'a> CrateLoader<'a> {
|
|||
name,
|
||||
name,
|
||||
None,
|
||||
None,
|
||||
DUMMY_SP,
|
||||
PathKind::Crate,
|
||||
DepKind::Implicit);
|
||||
|
@ -1059,7 +1065,8 @@ impl<'a> middle::cstore::CrateLoader for CrateLoader<'a> {
|
|||
};
|
||||
|
||||
let (cnum, ..) = self.resolve_crate(
|
||||
&None, item.ident.name, orig_name, None, item.span, PathKind::Crate, dep_kind,
|
||||
&None, item.ident.name, orig_name, None, None,
|
||||
item.span, PathKind::Crate, dep_kind,
|
||||
);
|
||||
|
||||
let def_id = definitions.opt_local_def_id(item.id).unwrap();
|
||||
|
@ -1074,6 +1081,7 @@ impl<'a> middle::cstore::CrateLoader for CrateLoader<'a> {
|
|||
}
|
||||
|
||||
fn resolve_crate_from_path(&mut self, name: Symbol, span: Span) -> CrateNum {
|
||||
self.resolve_crate(&None, name, name, None, span, PathKind::Crate, DepKind::Explicit).0
|
||||
self.resolve_crate(&None, name, name, None, None, span, PathKind::Crate,
|
||||
DepKind::Explicit).0
|
||||
}
|
||||
}
|
||||
|
|
|
@ -213,6 +213,9 @@ provide! { <'tcx> tcx, def_id, other, cdata,
|
|||
crate_hash => { cdata.hash() }
|
||||
original_crate_name => { cdata.name() }
|
||||
|
||||
extra_filename => { cdata.root.extra_filename.clone() }
|
||||
|
||||
|
||||
implementations_of_trait => {
|
||||
let mut result = vec![];
|
||||
let filter = Some(other);
|
||||
|
|
|
@ -462,6 +462,7 @@ impl<'a, 'tcx> EncodeContext<'a, 'tcx> {
|
|||
let has_global_allocator = tcx.sess.has_global_allocator.get();
|
||||
let root = self.lazy(&CrateRoot {
|
||||
name: tcx.crate_name(LOCAL_CRATE),
|
||||
extra_filename: tcx.sess.opts.cg.extra_filename.clone(),
|
||||
triple: tcx.sess.opts.target_triple.clone(),
|
||||
hash: link_meta.crate_hash,
|
||||
disambiguator: tcx.sess.local_crate_disambiguator(),
|
||||
|
@ -1357,6 +1358,7 @@ impl<'a, 'b: 'a, 'tcx: 'b> IsolatedEncoder<'a, 'b, 'tcx> {
|
|||
name: self.tcx.original_crate_name(cnum),
|
||||
hash: self.tcx.crate_hash(cnum),
|
||||
kind: self.tcx.dep_kind(cnum),
|
||||
extra_filename: self.tcx.extra_filename(cnum),
|
||||
};
|
||||
(cnum, dep)
|
||||
})
|
||||
|
|
|
@ -83,7 +83,10 @@
|
|||
//! 1. Does the filename match an rlib/dylib pattern? That is to say, does the
|
||||
//! filename have the right prefix/suffix?
|
||||
//! 2. Does the filename have the right prefix for the crate name being queried?
|
||||
//! This is filtering for files like `libfoo*.rlib` and such.
|
||||
//! This is filtering for files like `libfoo*.rlib` and such. If the crate
|
||||
//! we're looking for was originally compiled with -C extra-filename, the
|
||||
//! extra filename will be included in this prefix to reduce reading
|
||||
//! metadata from crates that would otherwise share our prefix.
|
||||
//! 3. Is the file an actual rust library? This is done by loading the metadata
|
||||
//! from the library and making sure it's actually there.
|
||||
//! 4. Does the name in the metadata agree with the name of the library?
|
||||
|
@ -236,6 +239,7 @@ use syntax_pos::Span;
|
|||
use rustc_back::target::{Target, TargetTriple};
|
||||
|
||||
use std::cmp;
|
||||
use std::collections::HashSet;
|
||||
use std::fmt;
|
||||
use std::fs;
|
||||
use std::io::{self, Read};
|
||||
|
@ -256,6 +260,7 @@ pub struct Context<'a> {
|
|||
pub ident: Symbol,
|
||||
pub crate_name: Symbol,
|
||||
pub hash: Option<&'a Svh>,
|
||||
pub extra_filename: Option<&'a str>,
|
||||
// points to either self.sess.target.target or self.sess.host, must match triple
|
||||
pub target: &'a Target,
|
||||
pub triple: &'a TargetTriple,
|
||||
|
@ -303,7 +308,12 @@ impl CratePaths {
|
|||
|
||||
impl<'a> Context<'a> {
|
||||
pub fn maybe_load_library_crate(&mut self) -> Option<Library> {
|
||||
self.find_library_crate()
|
||||
let mut seen_paths = HashSet::new();
|
||||
match self.extra_filename {
|
||||
Some(s) => self.find_library_crate(s, &mut seen_paths)
|
||||
.or_else(|| self.find_library_crate("", &mut seen_paths)),
|
||||
None => self.find_library_crate("", &mut seen_paths)
|
||||
}
|
||||
}
|
||||
|
||||
pub fn report_errs(&mut self) -> ! {
|
||||
|
@ -419,7 +429,10 @@ impl<'a> Context<'a> {
|
|||
unreachable!();
|
||||
}
|
||||
|
||||
fn find_library_crate(&mut self) -> Option<Library> {
|
||||
fn find_library_crate(&mut self,
|
||||
extra_prefix: &str,
|
||||
seen_paths: &mut HashSet<PathBuf>)
|
||||
-> Option<Library> {
|
||||
// If an SVH is specified, then this is a transitive dependency that
|
||||
// must be loaded via -L plus some filtering.
|
||||
if self.hash.is_none() {
|
||||
|
@ -434,9 +447,9 @@ impl<'a> Context<'a> {
|
|||
let staticpair = self.staticlibname();
|
||||
|
||||
// want: crate_name.dir_part() + prefix + crate_name.file_part + "-"
|
||||
let dylib_prefix = format!("{}{}", dypair.0, self.crate_name);
|
||||
let rlib_prefix = format!("lib{}", self.crate_name);
|
||||
let staticlib_prefix = format!("{}{}", staticpair.0, self.crate_name);
|
||||
let dylib_prefix = format!("{}{}{}", dypair.0, self.crate_name, extra_prefix);
|
||||
let rlib_prefix = format!("lib{}{}", self.crate_name, extra_prefix);
|
||||
let staticlib_prefix = format!("{}{}{}", staticpair.0, self.crate_name, extra_prefix);
|
||||
|
||||
let mut candidates = FxHashMap();
|
||||
let mut staticlibs = vec![];
|
||||
|
@ -476,6 +489,7 @@ impl<'a> Context<'a> {
|
|||
}
|
||||
return FileDoesntMatch;
|
||||
};
|
||||
|
||||
info!("lib candidate: {}", path.display());
|
||||
|
||||
let hash_str = hash.to_string();
|
||||
|
@ -484,6 +498,10 @@ impl<'a> Context<'a> {
|
|||
let (ref mut rlibs, ref mut rmetas, ref mut dylibs) = *slot;
|
||||
fs::canonicalize(path)
|
||||
.map(|p| {
|
||||
if seen_paths.contains(&p) {
|
||||
return FileDoesntMatch
|
||||
};
|
||||
seen_paths.insert(p.clone());
|
||||
match found_kind {
|
||||
CrateFlavor::Rlib => { rlibs.insert(p, kind); }
|
||||
CrateFlavor::Rmeta => { rmetas.insert(p, kind); }
|
||||
|
|
|
@ -188,6 +188,7 @@ pub enum LazyState {
|
|||
pub struct CrateRoot {
|
||||
pub name: Symbol,
|
||||
pub triple: TargetTriple,
|
||||
pub extra_filename: String,
|
||||
pub hash: hir::svh::Svh,
|
||||
pub disambiguator: CrateDisambiguator,
|
||||
pub panic_strategy: PanicStrategy,
|
||||
|
@ -216,12 +217,14 @@ pub struct CrateDep {
|
|||
pub name: ast::Name,
|
||||
pub hash: hir::svh::Svh,
|
||||
pub kind: DepKind,
|
||||
pub extra_filename: String,
|
||||
}
|
||||
|
||||
impl_stable_hash_for!(struct CrateDep {
|
||||
name,
|
||||
hash,
|
||||
kind
|
||||
kind,
|
||||
extra_filename
|
||||
});
|
||||
|
||||
#[derive(RustcEncodable, RustcDecodable)]
|
||||
|
|
Loading…
Reference in New Issue