From c02be1502c76cc504ccf7f73dce929585c94377c Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Wed, 31 Oct 2018 15:13:49 +0300 Subject: move resolve local name --- crates/ra_analysis/src/descriptors/function/mod.rs | 2 +- .../ra_analysis/src/descriptors/function/scope.rs | 4 +- crates/ra_analysis/src/imp.rs | 30 ++++++--- crates/ra_analysis/src/syntax_ptr.rs | 4 ++ crates/ra_editor/src/lib.rs | 10 +-- crates/ra_editor/src/scope/fn_scope.rs | 73 ---------------------- crates/ra_editor/src/scope/mod.rs | 2 +- 7 files changed, 31 insertions(+), 94 deletions(-) (limited to 'crates') diff --git a/crates/ra_analysis/src/descriptors/function/mod.rs b/crates/ra_analysis/src/descriptors/function/mod.rs index 687413ddc..bb68b0ce7 100644 --- a/crates/ra_analysis/src/descriptors/function/mod.rs +++ b/crates/ra_analysis/src/descriptors/function/mod.rs @@ -10,7 +10,7 @@ use crate::{ syntax_ptr::SyntaxPtr }; -pub(crate) use self::scope::FnScopes; +pub(crate) use self::scope::{FnScopes, resolve_local_name}; #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] diff --git a/crates/ra_analysis/src/descriptors/function/scope.rs b/crates/ra_analysis/src/descriptors/function/scope.rs index 5333a0a3b..d9929414c 100644 --- a/crates/ra_analysis/src/descriptors/function/scope.rs +++ b/crates/ra_analysis/src/descriptors/function/scope.rs @@ -1,4 +1,4 @@ -use rustc_hash::FxHashMap; +use rustc_hash::{FxHashMap, FxHashSet}; use ra_syntax::{ algo::generate, @@ -261,8 +261,6 @@ pub fn resolve_local_name<'a>( name_ref: ast::NameRef, scopes: &'a FnScopes, ) -> Option<&'a ScopeEntry> { - use rustc_hash::FxHashSet; - let mut shadowed = FxHashSet::default(); let ret = scopes .scope_chain(name_ref.syntax()) diff --git a/crates/ra_analysis/src/imp.rs b/crates/ra_analysis/src/imp.rs index 49b693ae8..6473a1dbc 100644 --- a/crates/ra_analysis/src/imp.rs +++ b/crates/ra_analysis/src/imp.rs @@ -3,7 +3,7 @@ use std::{ sync::Arc, }; -use ra_editor::{self, find_node_at_offset, resolve_local_name, FileSymbol, LineIndex, LocalEdit, CompletionItem}; +use ra_editor::{self, find_node_at_offset, FileSymbol, LineIndex, LocalEdit, CompletionItem}; use ra_syntax::{ ast::{self, ArgListOwner, Expr, NameOwner}, AstNode, File, SmolStr, @@ -21,10 +21,13 @@ use crate::{ self, SyntaxDatabase, FileSyntaxQuery, }, input::{SourceRootId, FilesDatabase, SourceRoot, WORKSPACE}, - descriptors::DescriptorDatabase, - descriptors::module::{ModuleTree, Problem}, - descriptors::function::{FnDescriptor}, + descriptors::{ + DescriptorDatabase, + module::{ModuleTree, Problem}, + function::{FnDescriptor, FnId}, + }, symbol_index::SymbolIndex, + syntax_ptr::SyntaxPtrDatabase, CrateGraph, CrateId, Diagnostic, FileId, FileResolver, FileSystemEdit, Position, Query, SourceChange, SourceFileEdit, Cancelable, }; @@ -272,7 +275,7 @@ impl AnalysisImpl { let syntax = file.syntax(); if let Some(name_ref) = find_node_at_offset::(syntax, offset) { // First try to resolve the symbol locally - return if let Some((name, range)) = resolve_local_name(name_ref) { + return if let Some((name, range)) = resolve_local_name(&self.db, file_id, name_ref) { let mut vec = vec![]; vec.push(( file_id, @@ -326,7 +329,7 @@ impl AnalysisImpl { if let Some(name_ref) = find_node_at_offset::(syntax, offset) { // We are only handing local references for now - if let Some(resolved) = resolve_local_name(name_ref) { + if let Some(resolved) = resolve_local_name(&self.db, file_id, name_ref) { ret.push((file_id, resolved.1)); @@ -334,7 +337,7 @@ impl AnalysisImpl { let refs : Vec<_> = fn_def.syntax().descendants() .filter_map(ast::NameRef::cast) - .filter(|&n: &ast::NameRef| resolve_local_name(n) == Some(resolved.clone())) + .filter(|&n: &ast::NameRef| resolve_local_name(&self.db, file_id, n) == Some(resolved.clone())) .collect(); for r in refs { @@ -598,3 +601,16 @@ impl<'a> FnCallNode<'a> { } } } + +fn resolve_local_name( + db: &db::RootDatabase, + file_id: FileId, + name_ref: ast::NameRef, +) -> Option<(SmolStr, TextRange)> { + let fn_def = name_ref.syntax().ancestors().find_map(ast::FnDef::cast)?; + let fn_id = FnId::new(file_id, fn_def); + let scopes = db.fn_scopes(fn_id); + let scope_entry = crate::descriptors::function::resolve_local_name(name_ref, &scopes)?; + let syntax = db.resolve_syntax_ptr(scope_entry.ptr().into_global(file_id)); + Some((scope_entry.name().clone(), syntax.range())) +} diff --git a/crates/ra_analysis/src/syntax_ptr.rs b/crates/ra_analysis/src/syntax_ptr.rs index aee214318..563a010d7 100644 --- a/crates/ra_analysis/src/syntax_ptr.rs +++ b/crates/ra_analysis/src/syntax_ptr.rs @@ -84,6 +84,10 @@ impl LocalSyntaxPtr { .unwrap_or_else(|| panic!("can't resovle local ptr to SyntaxNode: {:?}", self)) } } + + pub(crate) fn into_global(self, file_id: FileId) -> SyntaxPtr { + SyntaxPtr { file_id, local: self} + } } diff --git a/crates/ra_editor/src/lib.rs b/crates/ra_editor/src/lib.rs index b73eb4ac7..ddcb6c6a2 100644 --- a/crates/ra_editor/src/lib.rs +++ b/crates/ra_editor/src/lib.rs @@ -151,15 +151,7 @@ pub fn find_node_at_offset<'a, N: AstNode<'a>>( leaf.ancestors().filter_map(N::cast).next() } -pub fn resolve_local_name( - name_ref: ast::NameRef, -) -> Option<(SmolStr, TextRange)> { - let fn_def = name_ref.syntax().ancestors().find_map(ast::FnDef::cast)?; - let scopes = scope::FnScopes::new(fn_def); - let scope_entry = scope::resolve_local_name(name_ref, &scopes)?; - let name = scope_entry.ast().name()?; - Some((scope_entry.name(), name.syntax().range())) -} + #[cfg(test)] mod tests { diff --git a/crates/ra_editor/src/scope/fn_scope.rs b/crates/ra_editor/src/scope/fn_scope.rs index f5c113fd9..4cb1f077c 100644 --- a/crates/ra_editor/src/scope/fn_scope.rs +++ b/crates/ra_editor/src/scope/fn_scope.rs @@ -258,22 +258,6 @@ struct ScopeData { entries: Vec, } -pub fn resolve_local_name<'a>( - name_ref: ast::NameRef, - scopes: &'a FnScopes, -) -> Option<&'a ScopeEntry> { - use rustc_hash::FxHashSet; - - let mut shadowed = FxHashSet::default(); - let ret = scopes - .scope_chain(name_ref.syntax()) - .flat_map(|scope| scopes.entries(scope).iter()) - .filter(|entry| shadowed.insert(entry.name())) - .filter(|entry| entry.name() == name_ref.text()) - .nth(0); - ret -} - #[cfg(test)] mod tests { use super::*; @@ -376,61 +360,4 @@ mod tests { &["x"], ); } - - fn do_check_local_name(code: &str, expected_offset: u32) { - let (off, code) = extract_offset(code); - let file = File::parse(&code); - let fn_def: ast::FnDef = find_node_at_offset(file.syntax(), off).unwrap(); - let name_ref: ast::NameRef = find_node_at_offset(file.syntax(), off).unwrap(); - - let scopes = FnScopes::new(fn_def); - - let local_name = resolve_local_name(name_ref, &scopes) - .unwrap() - .ast() - .name() - .unwrap(); - let expected_name = - find_node_at_offset::(file.syntax(), expected_offset.into()).unwrap(); - assert_eq!(local_name.syntax().range(), expected_name.syntax().range()); - } - - #[test] - fn test_resolve_local_name() { - do_check_local_name( - r#" - fn foo(x: i32, y: u32) { - { - let z = x * 2; - } - { - let t = x<|> * 3; - } - }"#, - 21, - ); - } - - #[test] - fn test_resolve_local_name_declaration() { - do_check_local_name( - r#" - fn foo(x: String) { - let x : &str = &x<|>; - }"#, - 21, - ); - } - - #[test] - fn test_resolve_local_name_shadow() { - do_check_local_name( - r" - fn foo(x: String) { - let x : &str = &x; - x<|> - }", - 46, - ); - } } diff --git a/crates/ra_editor/src/scope/mod.rs b/crates/ra_editor/src/scope/mod.rs index cc2d49392..483f5e63c 100644 --- a/crates/ra_editor/src/scope/mod.rs +++ b/crates/ra_editor/src/scope/mod.rs @@ -2,6 +2,6 @@ mod fn_scope; mod mod_scope; pub use self::{ - fn_scope::{resolve_local_name, FnScopes}, + fn_scope::{FnScopes}, mod_scope::ModuleScope, }; -- cgit v1.2.3