diff options
author | Aleksey Kladov <[email protected]> | 2019-01-03 16:55:34 +0000 |
---|---|---|
committer | Aleksey Kladov <[email protected]> | 2019-01-03 16:55:34 +0000 |
commit | 9bb2a742564fc893f5b8e1e605c760798e102765 (patch) | |
tree | 04f1672848134a53f143bff86b9658d7751ca29a /crates/ra_analysis/src | |
parent | 23d45177e25d6d30945d859a29d516d4058f518f (diff) |
embed file_id into FileSymbol
Diffstat (limited to 'crates/ra_analysis/src')
-rw-r--r-- | crates/ra_analysis/src/imp.rs | 22 | ||||
-rw-r--r-- | crates/ra_analysis/src/lib.rs | 11 | ||||
-rw-r--r-- | crates/ra_analysis/src/symbol_index.rs | 36 |
3 files changed, 34 insertions, 35 deletions
diff --git a/crates/ra_analysis/src/imp.rs b/crates/ra_analysis/src/imp.rs index 771dad475..eae73c2c4 100644 --- a/crates/ra_analysis/src/imp.rs +++ b/crates/ra_analysis/src/imp.rs | |||
@@ -165,9 +165,11 @@ impl db::RootDatabase { | |||
165 | }; | 165 | }; |
166 | } | 166 | } |
167 | // If that fails try the index based approach. | 167 | // If that fails try the index based approach. |
168 | for (file_id, symbol) in self.index_resolve(name_ref)? { | 168 | rr.resolves_to.extend( |
169 | rr.add_resolution(file_id, symbol); | 169 | self.index_resolve(name_ref)? |
170 | } | 170 | .into_iter() |
171 | .map(NavigationTarget::from_symbol), | ||
172 | ); | ||
171 | return Ok(Some(rr)); | 173 | return Ok(Some(rr)); |
172 | } | 174 | } |
173 | if let Some(name) = find_node_at_offset::<ast::Name>(syntax, position.offset) { | 175 | if let Some(name) = find_node_at_offset::<ast::Name>(syntax, position.offset) { |
@@ -352,13 +354,15 @@ impl db::RootDatabase { | |||
352 | 354 | ||
353 | // Resolve the function's NameRef (NOTE: this isn't entirely accurate). | 355 | // Resolve the function's NameRef (NOTE: this isn't entirely accurate). |
354 | let file_symbols = self.index_resolve(name_ref)?; | 356 | let file_symbols = self.index_resolve(name_ref)?; |
355 | for (fn_file_id, fs) in file_symbols { | 357 | for symbol in file_symbols { |
356 | if fs.ptr.kind() == FN_DEF { | 358 | if symbol.ptr.kind() == FN_DEF { |
357 | let fn_file = self.source_file(fn_file_id); | 359 | let fn_file = self.source_file(symbol.file_id); |
358 | let fn_def = fs.ptr.resolve(&fn_file); | 360 | let fn_def = symbol.ptr.resolve(&fn_file); |
359 | let fn_def = ast::FnDef::cast(fn_def.borrowed()).unwrap(); | 361 | let fn_def = ast::FnDef::cast(fn_def.borrowed()).unwrap(); |
360 | let descr = ctry!(source_binder::function_from_source( | 362 | let descr = ctry!(source_binder::function_from_source( |
361 | self, fn_file_id, fn_def | 363 | self, |
364 | symbol.file_id, | ||
365 | fn_def | ||
362 | )?); | 366 | )?); |
363 | if let Some(descriptor) = descr.signature_info(self) { | 367 | if let Some(descriptor) = descr.signature_info(self) { |
364 | // If we have a calling expression let's find which argument we are on | 368 | // If we have a calling expression let's find which argument we are on |
@@ -438,7 +442,7 @@ impl db::RootDatabase { | |||
438 | .collect::<Vec<_>>(); | 442 | .collect::<Vec<_>>(); |
439 | Ok(res) | 443 | Ok(res) |
440 | } | 444 | } |
441 | fn index_resolve(&self, name_ref: ast::NameRef) -> Cancelable<Vec<(FileId, FileSymbol)>> { | 445 | fn index_resolve(&self, name_ref: ast::NameRef) -> Cancelable<Vec<FileSymbol>> { |
442 | let name = name_ref.text(); | 446 | let name = name_ref.text(); |
443 | let mut query = Query::new(name.to_string()); | 447 | let mut query = Query::new(name.to_string()); |
444 | query.exact(); | 448 | query.exact(); |
diff --git a/crates/ra_analysis/src/lib.rs b/crates/ra_analysis/src/lib.rs index 61af676b2..ab935954c 100644 --- a/crates/ra_analysis/src/lib.rs +++ b/crates/ra_analysis/src/lib.rs | |||
@@ -237,11 +237,11 @@ pub struct NavigationTarget { | |||
237 | } | 237 | } |
238 | 238 | ||
239 | impl NavigationTarget { | 239 | impl NavigationTarget { |
240 | fn from_symbol(file_id: FileId, symbol: FileSymbol) -> NavigationTarget { | 240 | fn from_symbol(symbol: FileSymbol) -> NavigationTarget { |
241 | NavigationTarget { | 241 | NavigationTarget { |
242 | file_id: symbol.file_id, | ||
242 | name: symbol.name.clone(), | 243 | name: symbol.name.clone(), |
243 | kind: symbol.ptr.kind(), | 244 | kind: symbol.ptr.kind(), |
244 | file_id, | ||
245 | range: symbol.ptr.range(), | 245 | range: symbol.ptr.range(), |
246 | ptr: Some(symbol.ptr.clone()), | 246 | ptr: Some(symbol.ptr.clone()), |
247 | } | 247 | } |
@@ -278,11 +278,6 @@ impl ReferenceResolution { | |||
278 | resolves_to: Vec::new(), | 278 | resolves_to: Vec::new(), |
279 | } | 279 | } |
280 | } | 280 | } |
281 | |||
282 | fn add_resolution(&mut self, file_id: FileId, symbol: FileSymbol) { | ||
283 | self.resolves_to | ||
284 | .push(NavigationTarget::from_symbol(file_id, symbol)) | ||
285 | } | ||
286 | } | 281 | } |
287 | 282 | ||
288 | /// `AnalysisHost` stores the current state of the world. | 283 | /// `AnalysisHost` stores the current state of the world. |
@@ -380,7 +375,7 @@ impl Analysis { | |||
380 | pub fn symbol_search(&self, query: Query) -> Cancelable<Vec<NavigationTarget>> { | 375 | pub fn symbol_search(&self, query: Query) -> Cancelable<Vec<NavigationTarget>> { |
381 | let res = symbol_index::world_symbols(&*self.db, query)? | 376 | let res = symbol_index::world_symbols(&*self.db, query)? |
382 | .into_iter() | 377 | .into_iter() |
383 | .map(|(file_id, symbol)| NavigationTarget::from_symbol(file_id, symbol)) | 378 | .map(NavigationTarget::from_symbol) |
384 | .collect(); | 379 | .collect(); |
385 | Ok(res) | 380 | Ok(res) |
386 | } | 381 | } |
diff --git a/crates/ra_analysis/src/symbol_index.rs b/crates/ra_analysis/src/symbol_index.rs index 10d8e8059..b355b14ed 100644 --- a/crates/ra_analysis/src/symbol_index.rs +++ b/crates/ra_analysis/src/symbol_index.rs | |||
@@ -58,10 +58,7 @@ fn file_symbols(db: &impl SyntaxDatabase, file_id: FileId) -> Cancelable<Arc<Sym | |||
58 | Ok(Arc::new(SymbolIndex::for_file(file_id, syntax))) | 58 | Ok(Arc::new(SymbolIndex::for_file(file_id, syntax))) |
59 | } | 59 | } |
60 | 60 | ||
61 | pub(crate) fn world_symbols( | 61 | pub(crate) fn world_symbols(db: &RootDatabase, query: Query) -> Cancelable<Vec<FileSymbol>> { |
62 | db: &RootDatabase, | ||
63 | query: Query, | ||
64 | ) -> Cancelable<Vec<(FileId, FileSymbol)>> { | ||
65 | /// Need to wrap Snapshot to provide `Clone` impl for `map_with` | 62 | /// Need to wrap Snapshot to provide `Clone` impl for `map_with` |
66 | struct Snap(salsa::Snapshot<RootDatabase>); | 63 | struct Snap(salsa::Snapshot<RootDatabase>); |
67 | impl Clone for Snap { | 64 | impl Clone for Snap { |
@@ -95,7 +92,7 @@ pub(crate) fn world_symbols( | |||
95 | 92 | ||
96 | #[derive(Default, Debug)] | 93 | #[derive(Default, Debug)] |
97 | pub(crate) struct SymbolIndex { | 94 | pub(crate) struct SymbolIndex { |
98 | symbols: Vec<(FileId, FileSymbol)>, | 95 | symbols: Vec<FileSymbol>, |
99 | map: fst::Map, | 96 | map: fst::Map, |
100 | } | 97 | } |
101 | 98 | ||
@@ -126,14 +123,18 @@ impl SymbolIndex { | |||
126 | file.syntax() | 123 | file.syntax() |
127 | .descendants() | 124 | .descendants() |
128 | .filter_map(to_symbol) | 125 | .filter_map(to_symbol) |
129 | .map(move |symbol| (symbol.name.as_str().to_lowercase(), (file_id, symbol))) | 126 | .map(move |(name, ptr)| { |
127 | ( | ||
128 | name.as_str().to_lowercase(), | ||
129 | FileSymbol { name, ptr, file_id }, | ||
130 | ) | ||
131 | }) | ||
130 | .collect::<Vec<_>>() | 132 | .collect::<Vec<_>>() |
131 | }) | 133 | }) |
132 | .collect::<Vec<_>>(); | 134 | .collect::<Vec<_>>(); |
133 | symbols.par_sort_by(|s1, s2| s1.0.cmp(&s2.0)); | 135 | symbols.par_sort_by(|s1, s2| s1.0.cmp(&s2.0)); |
134 | symbols.dedup_by(|s1, s2| s1.0 == s2.0); | 136 | symbols.dedup_by(|s1, s2| s1.0 == s2.0); |
135 | let (names, symbols): (Vec<String>, Vec<(FileId, FileSymbol)>) = | 137 | let (names, symbols): (Vec<String>, Vec<FileSymbol>) = symbols.into_iter().unzip(); |
136 | symbols.into_iter().unzip(); | ||
137 | let map = fst::Map::from_iter(names.into_iter().zip(0u64..)).unwrap(); | 138 | let map = fst::Map::from_iter(names.into_iter().zip(0u64..)).unwrap(); |
138 | SymbolIndex { symbols, map } | 139 | SymbolIndex { symbols, map } |
139 | } | 140 | } |
@@ -144,7 +145,7 @@ impl SymbolIndex { | |||
144 | } | 145 | } |
145 | 146 | ||
146 | impl Query { | 147 | impl Query { |
147 | pub(crate) fn search(self, indices: &[Arc<SymbolIndex>]) -> Vec<(FileId, FileSymbol)> { | 148 | pub(crate) fn search(self, indices: &[Arc<SymbolIndex>]) -> Vec<FileSymbol> { |
148 | let mut op = fst::map::OpBuilder::new(); | 149 | let mut op = fst::map::OpBuilder::new(); |
149 | for file_symbols in indices.iter() { | 150 | for file_symbols in indices.iter() { |
150 | let automaton = fst::automaton::Subsequence::new(&self.lowercased); | 151 | let automaton = fst::automaton::Subsequence::new(&self.lowercased); |
@@ -160,14 +161,14 @@ impl Query { | |||
160 | let file_symbols = &indices[indexed_value.index]; | 161 | let file_symbols = &indices[indexed_value.index]; |
161 | let idx = indexed_value.value as usize; | 162 | let idx = indexed_value.value as usize; |
162 | 163 | ||
163 | let (file_id, symbol) = &file_symbols.symbols[idx]; | 164 | let symbol = &file_symbols.symbols[idx]; |
164 | if self.only_types && !is_type(symbol.ptr.kind()) { | 165 | if self.only_types && !is_type(symbol.ptr.kind()) { |
165 | continue; | 166 | continue; |
166 | } | 167 | } |
167 | if self.exact && symbol.name != self.query { | 168 | if self.exact && symbol.name != self.query { |
168 | continue; | 169 | continue; |
169 | } | 170 | } |
170 | res.push((*file_id, symbol.clone())); | 171 | res.push(symbol.clone()); |
171 | } | 172 | } |
172 | } | 173 | } |
173 | res | 174 | res |
@@ -185,17 +186,16 @@ fn is_type(kind: SyntaxKind) -> bool { | |||
185 | /// possible. | 186 | /// possible. |
186 | #[derive(Debug, Clone, PartialEq, Eq, Hash)] | 187 | #[derive(Debug, Clone, PartialEq, Eq, Hash)] |
187 | pub(crate) struct FileSymbol { | 188 | pub(crate) struct FileSymbol { |
189 | pub(crate) file_id: FileId, | ||
188 | pub(crate) name: SmolStr, | 190 | pub(crate) name: SmolStr, |
189 | pub(crate) ptr: LocalSyntaxPtr, | 191 | pub(crate) ptr: LocalSyntaxPtr, |
190 | } | 192 | } |
191 | 193 | ||
192 | fn to_symbol(node: SyntaxNodeRef) -> Option<FileSymbol> { | 194 | fn to_symbol(node: SyntaxNodeRef) -> Option<(SmolStr, LocalSyntaxPtr)> { |
193 | fn decl<'a, N: NameOwner<'a>>(node: N) -> Option<FileSymbol> { | 195 | fn decl<'a, N: NameOwner<'a>>(node: N) -> Option<(SmolStr, LocalSyntaxPtr)> { |
194 | let name = node.name()?; | 196 | let name = node.name()?.text(); |
195 | Some(FileSymbol { | 197 | let ptr = LocalSyntaxPtr::new(node.syntax()); |
196 | name: name.text(), | 198 | Some((name, ptr)) |
197 | ptr: LocalSyntaxPtr::new(node.syntax()), | ||
198 | }) | ||
199 | } | 199 | } |
200 | visitor() | 200 | visitor() |
201 | .visit(decl::<ast::FnDef>) | 201 | .visit(decl::<ast::FnDef>) |