aboutsummaryrefslogtreecommitdiff
path: root/crates/ra_lsp_server/src/server_world.rs
diff options
context:
space:
mode:
Diffstat (limited to 'crates/ra_lsp_server/src/server_world.rs')
-rw-r--r--crates/ra_lsp_server/src/server_world.rs51
1 files changed, 49 insertions, 2 deletions
diff --git a/crates/ra_lsp_server/src/server_world.rs b/crates/ra_lsp_server/src/server_world.rs
index 2debbe557..4f3c231d3 100644
--- a/crates/ra_lsp_server/src/server_world.rs
+++ b/crates/ra_lsp_server/src/server_world.rs
@@ -44,7 +44,12 @@ impl ServerWorldState {
44 for pkg in ws.cargo.packages() { 44 for pkg in ws.cargo.packages() {
45 roots.push(pkg.root(&ws.cargo).to_path_buf()); 45 roots.push(pkg.root(&ws.cargo).to_path_buf());
46 } 46 }
47 for krate in ws.sysroot.crates() {
48 roots.push(krate.root_dir(&ws.sysroot).to_path_buf())
49 }
47 } 50 }
51 roots.sort();
52 roots.dedup();
48 let roots_to_scan = roots.len(); 53 let roots_to_scan = roots.len();
49 let (mut vfs, roots) = Vfs::new(roots); 54 let (mut vfs, roots) = Vfs::new(roots);
50 for r in roots { 55 for r in roots {
@@ -53,16 +58,43 @@ impl ServerWorldState {
53 } 58 }
54 59
55 let mut crate_graph = CrateGraph::default(); 60 let mut crate_graph = CrateGraph::default();
56 let mut pkg_to_lib_crate = FxHashMap::default();
57 let mut pkg_crates = FxHashMap::default();
58 for ws in workspaces.iter() { 61 for ws in workspaces.iter() {
62 // First, load std
63 let mut sysroot_crates = FxHashMap::default();
64 for krate in ws.sysroot.crates() {
65 if let Some(file_id) = vfs.load(krate.root(&ws.sysroot)) {
66 let file_id = FileId(file_id.0.into());
67 sysroot_crates.insert(krate, crate_graph.add_crate_root(file_id));
68 }
69 }
70 for from in ws.sysroot.crates() {
71 for to in from.deps(&ws.sysroot) {
72 let name = to.name(&ws.sysroot);
73 if let (Some(&from), Some(&to)) =
74 (sysroot_crates.get(&from), sysroot_crates.get(&to))
75 {
76 crate_graph.add_dep(from, name.clone(), to);
77 }
78 }
79 }
80
81 let libstd = ws
82 .sysroot
83 .std()
84 .and_then(|it| sysroot_crates.get(&it).map(|&it| it));
85
86 let mut pkg_to_lib_crate = FxHashMap::default();
87 let mut pkg_crates = FxHashMap::default();
88 // Next, create crates for each package, target pair
59 for pkg in ws.cargo.packages() { 89 for pkg in ws.cargo.packages() {
90 let mut lib_tgt = None;
60 for tgt in pkg.targets(&ws.cargo) { 91 for tgt in pkg.targets(&ws.cargo) {
61 let root = tgt.root(&ws.cargo); 92 let root = tgt.root(&ws.cargo);
62 if let Some(file_id) = vfs.load(root) { 93 if let Some(file_id) = vfs.load(root) {
63 let file_id = FileId(file_id.0.into()); 94 let file_id = FileId(file_id.0.into());
64 let crate_id = crate_graph.add_crate_root(file_id); 95 let crate_id = crate_graph.add_crate_root(file_id);
65 if tgt.kind(&ws.cargo) == TargetKind::Lib { 96 if tgt.kind(&ws.cargo) == TargetKind::Lib {
97 lib_tgt = Some(crate_id);
66 pkg_to_lib_crate.insert(pkg, crate_id); 98 pkg_to_lib_crate.insert(pkg, crate_id);
67 } 99 }
68 pkg_crates 100 pkg_crates
@@ -71,7 +103,22 @@ impl ServerWorldState {
71 .push(crate_id); 103 .push(crate_id);
72 } 104 }
73 } 105 }
106
107 // Set deps to the std and to the lib target of the current package
108 for &from in pkg_crates.get(&pkg).into_iter().flatten() {
109 if let Some(to) = lib_tgt {
110 if to != from {
111 crate_graph.add_dep(from, pkg.name(&ws.cargo).into(), to);
112 }
113 }
114 if let Some(std) = libstd {
115 crate_graph.add_dep(from, "std".into(), std);
116 }
117 }
74 } 118 }
119
120 // Now add a dep ednge from all targets of upstream to the lib
121 // target of downstream.
75 for pkg in ws.cargo.packages() { 122 for pkg in ws.cargo.packages() {
76 for dep in pkg.dependencies(&ws.cargo) { 123 for dep in pkg.dependencies(&ws.cargo) {
77 if let Some(&to) = pkg_to_lib_crate.get(&dep.pkg) { 124 if let Some(&to) = pkg_to_lib_crate.get(&dep.pkg) {