Unnamed repository; edit this file 'description' to name the repository.
Diffstat (limited to 'crates/project-model/src/sysroot.rs')
-rw-r--r--crates/project-model/src/sysroot.rs64
1 files changed, 46 insertions, 18 deletions
diff --git a/crates/project-model/src/sysroot.rs b/crates/project-model/src/sysroot.rs
index 74e41eda76..e3a2de927c 100644
--- a/crates/project-model/src/sysroot.rs
+++ b/crates/project-model/src/sysroot.rs
@@ -12,13 +12,15 @@ use la_arena::{Arena, Idx};
use paths::{AbsPath, AbsPathBuf};
use rustc_hash::FxHashMap;
-use crate::{utf8_stdout, ManifestPath};
+use crate::{utf8_stdout, CargoConfig, CargoWorkspace, ManifestPath};
#[derive(Debug, Clone, Eq, PartialEq)]
pub struct Sysroot {
root: AbsPathBuf,
src_root: AbsPathBuf,
crates: Arena<SysrootCrateData>,
+ /// Stores the result of `cargo metadata` of the `RA_UNSTABLE_SYSROOT_HACK` workspace.
+ pub hack_cargo_workspace: Option<CargoWorkspace>,
}
pub(crate) type SysrootCrate = Idx<SysrootCrateData>;
@@ -74,6 +76,23 @@ impl Sysroot {
pub fn is_empty(&self) -> bool {
self.crates.is_empty()
}
+
+ pub fn loading_warning(&self) -> Option<String> {
+ if self.by_name("core").is_none() {
+ let var_note = if env::var_os("RUST_SRC_PATH").is_some() {
+ " (`RUST_SRC_PATH` might be incorrect, try unsetting it)"
+ } else {
+ " try running `rustup component add rust-src` to possible fix this"
+ };
+ Some(format!(
+ "could not find libcore in loaded sysroot at `{}`{}",
+ self.src_root.as_path().display(),
+ var_note,
+ ))
+ } else {
+ None
+ }
+ }
}
// FIXME: Expose a builder api as loading the sysroot got way too modular and complicated.
@@ -103,14 +122,36 @@ impl Sysroot {
pub fn with_sysroot_dir(sysroot_dir: AbsPathBuf) -> Result<Sysroot> {
let sysroot_src_dir = discover_sysroot_src_dir(&sysroot_dir).ok_or_else(|| {
- format_err!("can't load standard library from sysroot {}", sysroot_dir.display())
+ format_err!("can't load standard library from sysroot path {}", sysroot_dir.display())
})?;
Ok(Sysroot::load(sysroot_dir, sysroot_src_dir))
}
- pub fn load(sysroot_dir: AbsPathBuf, sysroot_src_dir: AbsPathBuf) -> Sysroot {
- let mut sysroot =
- Sysroot { root: sysroot_dir, src_root: sysroot_src_dir, crates: Arena::default() };
+ pub fn load(sysroot_dir: AbsPathBuf, mut sysroot_src_dir: AbsPathBuf) -> Sysroot {
+ // FIXME: Remove this `hack_cargo_workspace` field completely once we support sysroot dependencies
+ let hack_cargo_workspace = if let Ok(path) = std::env::var("RA_UNSTABLE_SYSROOT_HACK") {
+ let cargo_toml = ManifestPath::try_from(
+ AbsPathBuf::try_from(&*format!("{path}/Cargo.toml")).unwrap(),
+ )
+ .unwrap();
+ sysroot_src_dir = AbsPathBuf::try_from(&*path).unwrap().join("library");
+ CargoWorkspace::fetch_metadata(
+ &cargo_toml,
+ &AbsPathBuf::try_from("/").unwrap(),
+ &CargoConfig::default(),
+ &|_| (),
+ )
+ .map(CargoWorkspace::new)
+ .ok()
+ } else {
+ None
+ };
+ let mut sysroot = Sysroot {
+ root: sysroot_dir,
+ src_root: sysroot_src_dir,
+ crates: Arena::default(),
+ hack_cargo_workspace,
+ };
for path in SYSROOT_CRATES.trim().lines() {
let name = path.split('/').last().unwrap();
@@ -153,19 +194,6 @@ impl Sysroot {
}
}
- if sysroot.by_name("core").is_none() {
- let var_note = if env::var_os("RUST_SRC_PATH").is_some() {
- " (`RUST_SRC_PATH` might be incorrect, try unsetting it)"
- } else {
- ""
- };
- tracing::error!(
- "could not find libcore in sysroot path `{}`{}",
- sysroot.src_root.as_path().display(),
- var_note,
- );
- }
-
sysroot
}