From a9e4142f434b1a2aa0729387534121fdf9c812a6 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Tue, 4 Dec 2018 21:21:39 +0300 Subject: include file itself in SourceFileItems --- crates/ra_hir/src/query_definitions.rs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/crates/ra_hir/src/query_definitions.rs b/crates/ra_hir/src/query_definitions.rs index 6f602878c..59318f307 100644 --- a/crates/ra_hir/src/query_definitions.rs +++ b/crates/ra_hir/src/query_definitions.rs @@ -36,9 +36,10 @@ pub(super) fn fn_scopes(db: &impl HirDatabase, fn_id: FnId) -> Arc { } pub(super) fn file_items(db: &impl HirDatabase, file_id: FileId) -> Arc { + let mut res = SourceFileItems::default(); let source_file = db.source_file(file_id); + res.alloc(source_file.syntax().owned()); let source_file = source_file.borrowed(); - let mut res = SourceFileItems::default(); source_file .syntax() .descendants() -- cgit v1.2.3 From 45fce9034909f2f0c5f6ac70eca7cf87ec3db856 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Tue, 4 Dec 2018 22:46:23 +0300 Subject: ModuleSource is ItemSource --- crates/ra_analysis/src/imp.rs | 5 +-- crates/ra_hir/src/lib.rs | 4 +++ crates/ra_hir/src/module/imp.rs | 13 +++----- crates/ra_hir/src/module/mod.rs | 69 ++++++++++++++++++----------------------- 4 files changed, 40 insertions(+), 51 deletions(-) diff --git a/crates/ra_analysis/src/imp.rs b/crates/ra_analysis/src/imp.rs index f5cb3550e..942b5b945 100644 --- a/crates/ra_analysis/src/imp.rs +++ b/crates/ra_analysis/src/imp.rs @@ -190,10 +190,7 @@ impl AnalysisImpl { Some(it) => it, }; let root = descr.crate_root(); - let file_id = root - .source() - .as_file() - .expect("root module always has a file as a source"); + let file_id = root.source().file_id(); let crate_graph = self.db.crate_graph(); let crate_id = crate_graph.crate_id_for_crate_root(file_id); diff --git a/crates/ra_hir/src/lib.rs b/crates/ra_hir/src/lib.rs index e7b6a81f4..0f84b2d61 100644 --- a/crates/ra_hir/src/lib.rs +++ b/crates/ra_hir/src/lib.rs @@ -131,6 +131,10 @@ impl SourceFileItems { .unwrap(); id } + pub fn id_of_source_file(&self) -> SourceFileItemId { + let (id, _syntax) = self.arena.iter().next().unwrap(); + id + } } impl Index for SourceFileItems { diff --git a/crates/ra_hir/src/module/imp.rs b/crates/ra_hir/src/module/imp.rs index 76ea129a7..0eec38797 100644 --- a/crates/ra_hir/src/module/imp.rs +++ b/crates/ra_hir/src/module/imp.rs @@ -66,7 +66,7 @@ fn create_module_tree<'a>( let source_root = db.source_root(source_root); for &file_id in source_root.files.iter() { - let source = ModuleSource::SourceFile(file_id); + let source = ModuleSource::new_file(db, file_id); if visited.contains(&source) { continue; // TODO: use explicit crate_roots here } @@ -126,7 +126,7 @@ fn build_subtree( visited, roots, Some(link), - ModuleSource::SourceFile(file_id), + ModuleSource::new_file(db, file_id), ), }) .collect::>>()?; @@ -157,13 +157,8 @@ fn resolve_submodule( name: &SmolStr, file_resolver: &FileResolverImp, ) -> (Vec, Option) { - let file_id = match source { - ModuleSource::SourceFile(it) => it, - ModuleSource::Module(..) => { - // TODO - return (Vec::new(), None); - } - }; + // TODO: handle submodules of inline modules properly + let file_id = source.file_id(); let mod_name = file_resolver.file_stem(file_id); let is_dir_owner = mod_name == "mod" || mod_name == "lib" || mod_name == "main"; diff --git a/crates/ra_hir/src/module/mod.rs b/crates/ra_hir/src/module/mod.rs index 3ae83d8cb..fa9ee94eb 100644 --- a/crates/ra_hir/src/module/mod.rs +++ b/crates/ra_hir/src/module/mod.rs @@ -14,7 +14,7 @@ use ra_db::{SourceRootId, FileId, FilePosition, Cancelable}; use relative_path::RelativePathBuf; use crate::{ - DefLoc, DefId, Path, PathKind, HirDatabase, SourceItemId, + DefLoc, DefId, Path, PathKind, HirDatabase, SourceItemId, SourceFileItemId, arena::{Arena, Id}, }; @@ -37,7 +37,8 @@ impl Module { db: &impl HirDatabase, file_id: FileId, ) -> Cancelable> { - Module::guess_from_source(db, file_id, ModuleSource::SourceFile(file_id)) + let module_source = ModuleSource::new_file(db, file_id); + Module::guess_from_source(db, module_source) } /// Lookup `Module` by position in the source code. Note that this @@ -51,17 +52,16 @@ impl Module { let module_source = match find_node_at_offset::(file.syntax(), position.offset) { Some(m) if !m.has_semi() => ModuleSource::new_inline(db, position.file_id, m), - _ => ModuleSource::SourceFile(position.file_id), + _ => ModuleSource::new_file(db, position.file_id), }; - Module::guess_from_source(db, position.file_id, module_source) + Module::guess_from_source(db, module_source) } fn guess_from_source( db: &impl HirDatabase, - file_id: FileId, module_source: ModuleSource, ) -> Cancelable> { - let source_root_id = db.file_source_root(file_id); + let source_root_id = db.file_source_root(module_source.file_id()); let module_tree = db.module_tree(source_root_id)?; let res = match module_tree.any_module_for_source(module_source) { @@ -209,10 +209,7 @@ impl ModuleTree { /// `ModuleSource` is the syntax tree element that produced this module: /// either a file, or an inlinde module. #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)] -pub enum ModuleSource { - SourceFile(FileId), - Module(SourceItemId), -} +pub struct ModuleSource(SourceItemId); /// An owned syntax node for a module. Unlike `ModuleSource`, /// this holds onto the AST for the whole file. @@ -310,45 +307,41 @@ pub struct ModuleData { } impl ModuleSource { + // precondition: item_id **must** point to module + fn new(file_id: FileId, item_id: SourceFileItemId) -> ModuleSource { + let source_item_id = SourceItemId { file_id, item_id }; + ModuleSource(source_item_id) + } + + pub(crate) fn new_file(db: &impl HirDatabase, file_id: FileId) -> ModuleSource { + let file_items = db.file_items(file_id); + let item_id = file_items.id_of_source_file(); + ModuleSource::new(file_id, item_id) + } + pub(crate) fn new_inline( db: &impl HirDatabase, file_id: FileId, - module: ast::Module, + m: ast::Module, ) -> ModuleSource { - assert!(!module.has_semi()); - let items = db.file_items(file_id); - let item_id = items.id_of(module.syntax()); - let id = SourceItemId { file_id, item_id }; - ModuleSource::Module(id) - } - - pub fn as_file(self) -> Option { - match self { - ModuleSource::SourceFile(f) => Some(f), - ModuleSource::Module(..) => None, - } + assert!(!m.has_semi()); + let file_items = db.file_items(file_id); + let item_id = file_items.id_of(m.syntax()); + ModuleSource::new(file_id, item_id) } pub fn file_id(self) -> FileId { - match self { - ModuleSource::SourceFile(f) => f, - ModuleSource::Module(source_item_id) => source_item_id.file_id, - } + self.0.file_id } pub(crate) fn resolve(self, db: &impl HirDatabase) -> ModuleSourceNode { - match self { - ModuleSource::SourceFile(file_id) => { - let syntax = db.source_file(file_id); - ModuleSourceNode::SourceFile(syntax.ast().owned()) - } - ModuleSource::Module(item_id) => { - let syntax = db.file_item(item_id); - let syntax = syntax.borrowed(); - let module = ast::Module::cast(syntax).unwrap(); - ModuleSourceNode::Module(module.owned()) - } + let syntax_node = db.file_item(self.0); + let syntax_node = syntax_node.borrowed(); + if let Some(file) = ast::SourceFile::cast(syntax_node) { + return ModuleSourceNode::SourceFile(file.owned()); } + let module = ast::Module::cast(syntax_node).unwrap(); + ModuleSourceNode::Module(module.owned()) } } -- cgit v1.2.3 From 947e3350e045aab1db9b232542425a3faa856907 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Tue, 4 Dec 2018 23:01:53 +0300 Subject: module-scoped defloc --- crates/ra_hir/src/lib.rs | 27 +++++++++++++++------------ crates/ra_hir/src/module/mod.rs | 17 ++++++++++++----- crates/ra_hir/src/module/nameres.rs | 23 ++++++++++++++++------- 3 files changed, 43 insertions(+), 24 deletions(-) diff --git a/crates/ra_hir/src/lib.rs b/crates/ra_hir/src/lib.rs index 0f84b2d61..ffc99fd5f 100644 --- a/crates/ra_hir/src/lib.rs +++ b/crates/ra_hir/src/lib.rs @@ -61,15 +61,18 @@ impl FnId { pub struct DefId(u32); ra_db::impl_numeric_id!(DefId); +#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)] +pub(crate) enum DefKind { + Module, + Item, +} + #[derive(Clone, Debug, PartialEq, Eq, Hash)] -pub enum DefLoc { - Module { - id: ModuleId, - source_root: SourceRootId, - }, - Item { - source_item_id: SourceItemId, - }, +pub struct DefLoc { + pub(crate) kind: DefKind, + source_root_id: SourceRootId, + module_id: ModuleId, + source_item_id: SourceItemId, } impl DefId { @@ -92,12 +95,12 @@ pub enum Def { impl DefId { pub fn resolve(self, db: &impl HirDatabase) -> Cancelable { let loc = self.loc(db); - let res = match loc { - DefLoc::Module { id, source_root } => { - let descr = Module::new(db, source_root, id)?; + let res = match loc.kind { + DefKind::Module => { + let descr = Module::new(db, loc.source_root_id, loc.module_id)?; Def::Module(descr) } - DefLoc::Item { .. } => Def::Item, + DefKind::Item => Def::Item, }; Ok(res) } diff --git a/crates/ra_hir/src/module/mod.rs b/crates/ra_hir/src/module/mod.rs index fa9ee94eb..08ce7c8d1 100644 --- a/crates/ra_hir/src/module/mod.rs +++ b/crates/ra_hir/src/module/mod.rs @@ -14,7 +14,7 @@ use ra_db::{SourceRootId, FileId, FilePosition, Cancelable}; use relative_path::RelativePathBuf; use crate::{ - DefLoc, DefId, Path, PathKind, HirDatabase, SourceItemId, SourceFileItemId, + DefKind, DefLoc, DefId, Path, PathKind, HirDatabase, SourceItemId, SourceFileItemId, arena::{Arena, Id}, }; @@ -127,9 +127,11 @@ impl Module { } pub fn def_id(&self, db: &impl HirDatabase) -> DefId { - let def_loc = DefLoc::Module { - id: self.module_id, - source_root: self.source_root_id, + let def_loc = DefLoc { + kind: DefKind::Module, + source_root_id: self.source_root_id, + module_id: self.module_id, + source_item_id: self.module_id.source(&self.tree).0, }; def_loc.id(db) } @@ -161,7 +163,12 @@ impl Module { let segments = path.segments; for name in segments.iter() { let module = match curr.loc(db) { - DefLoc::Module { id, source_root } => Module::new(db, source_root, id)?, + DefLoc { + kind: DefKind::Module, + source_root_id, + module_id, + .. + } => Module::new(db, source_root_id, module_id)?, _ => return Ok(None), }; let scope = module.scope(db)?; diff --git a/crates/ra_hir/src/module/nameres.rs b/crates/ra_hir/src/module/nameres.rs index 8529e16b3..c2b380a80 100644 --- a/crates/ra_hir/src/module/nameres.rs +++ b/crates/ra_hir/src/module/nameres.rs @@ -28,7 +28,7 @@ use ra_db::SourceRootId; use crate::{ Cancelable, FileId, - DefId, DefLoc, + DefId, DefLoc, DefKind, SourceItemId, SourceFileItemId, SourceFileItems, Path, PathKind, HirDatabase, @@ -247,7 +247,10 @@ where // handle submodules separatelly continue; } - let def_loc = DefLoc::Item { + let def_loc = DefLoc { + kind: DefKind::Item, + source_root_id: self.source_root, + module_id, source_item_id: SourceItemId { file_id, item_id: item.id, @@ -261,10 +264,12 @@ where module_items.items.insert(item.name.clone(), resolution); } - for (name, mod_id) in module_id.children(&self.module_tree) { - let def_loc = DefLoc::Module { - id: mod_id, - source_root: self.source_root, + for (name, module_id) in module_id.children(&self.module_tree) { + let def_loc = DefLoc { + kind: DefKind::Module, + source_root_id: self.source_root, + module_id, + source_item_id: module_id.source(&self.module_tree).0, }; let def_id = def_loc.id(self.db); let resolution = Resolution { @@ -316,7 +321,11 @@ where if !is_last { curr = match def_id.loc(self.db) { - DefLoc::Module { id, .. } => id, + DefLoc { + kind: DefKind::Module, + module_id, + .. + } => module_id, _ => return, } } else { -- cgit v1.2.3 From d8b0379e1063941331253905795699a918233ef9 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Tue, 4 Dec 2018 23:44:00 +0300 Subject: Add functions to DefId --- .../src/completion/reference_completion.rs | 2 +- crates/ra_analysis/src/db.rs | 9 +---- crates/ra_analysis/src/imp.rs | 41 ++++++++++++++-------- crates/ra_analysis/src/lib.rs | 2 +- crates/ra_hir/src/db.rs | 4 +-- crates/ra_hir/src/function/mod.rs | 41 ++++++++++++---------- crates/ra_hir/src/lib.rs | 20 ++--------- crates/ra_hir/src/mock.rs | 9 +---- crates/ra_hir/src/module/mod.rs | 23 ++++++++++-- crates/ra_hir/src/query_definitions.rs | 22 ++++++------ 10 files changed, 90 insertions(+), 83 deletions(-) diff --git a/crates/ra_analysis/src/completion/reference_completion.rs b/crates/ra_analysis/src/completion/reference_completion.rs index 8ea7478a8..f483ed045 100644 --- a/crates/ra_analysis/src/completion/reference_completion.rs +++ b/crates/ra_analysis/src/completion/reference_completion.rs @@ -163,7 +163,7 @@ fn complete_path( }; let target_module = match def_id.resolve(db)? { Def::Module(it) => it, - Def::Item => return Ok(()), + _ => return Ok(()), }; let module_scope = target_module.scope(db)?; let completions = module_scope.entries().map(|(name, _res)| CompletionItem { diff --git a/crates/ra_analysis/src/db.rs b/crates/ra_analysis/src/db.rs index df2ef293d..b8d774eb5 100644 --- a/crates/ra_analysis/src/db.rs +++ b/crates/ra_analysis/src/db.rs @@ -1,7 +1,7 @@ use std::sync::Arc; use salsa::{self, Database}; use ra_db::{LocationIntener, BaseDatabase}; -use hir::{self, DefId, DefLoc, FnId, SourceItemId}; +use hir::{self, DefId, DefLoc}; use crate::{ symbol_index, @@ -15,7 +15,6 @@ pub(crate) struct RootDatabase { #[derive(Debug, Default)] struct IdMaps { - fns: LocationIntener, defs: LocationIntener, } @@ -58,12 +57,6 @@ impl AsRef> for RootDatabase { } } -impl AsRef> for RootDatabase { - fn as_ref(&self) -> &LocationIntener { - &self.id_maps.fns - } -} - salsa::database_storage! { pub(crate) struct RootDatabaseStorage for RootDatabase { impl ra_db::FilesDatabase { diff --git a/crates/ra_analysis/src/imp.rs b/crates/ra_analysis/src/imp.rs index 942b5b945..fe1dfefea 100644 --- a/crates/ra_analysis/src/imp.rs +++ b/crates/ra_analysis/src/imp.rs @@ -210,7 +210,7 @@ impl AnalysisImpl { let syntax = file.syntax(); if let Some(name_ref) = find_node_at_offset::(syntax, position.offset) { if let Some(fn_descr) = - hir::Function::guess_for_name_ref(&*self.db, position.file_id, name_ref) + hir::Function::guess_for_name_ref(&*self.db, position.file_id, name_ref)? { let scope = fn_descr.scope(&*self.db); // First try to resolve the symbol locally @@ -257,11 +257,11 @@ impl AnalysisImpl { Ok(vec![]) } - pub fn find_all_refs(&self, position: FilePosition) -> Vec<(FileId, TextRange)> { + pub fn find_all_refs(&self, position: FilePosition) -> Cancelable> { let file = self.db.source_file(position.file_id); // Find the binding associated with the offset - let (binding, descr) = match find_binding(&self.db, &file, position) { - None => return Vec::new(), + let (binding, descr) = match find_binding(&self.db, &file, position)? { + None => return Ok(Vec::new()), Some(it) => it, }; @@ -274,25 +274,36 @@ impl AnalysisImpl { .map(|ref_desc| (position.file_id, ref_desc.range)), ); - return ret; + return Ok(ret); fn find_binding<'a>( db: &db::RootDatabase, source_file: &'a SourceFileNode, position: FilePosition, - ) -> Option<(ast::BindPat<'a>, hir::Function)> { + ) -> Cancelable, hir::Function)>> { let syntax = source_file.syntax(); if let Some(binding) = find_node_at_offset::(syntax, position.offset) { - let descr = hir::Function::guess_for_bind_pat(db, position.file_id, binding)?; - return Some((binding, descr)); + let descr = ctry!(hir::Function::guess_for_bind_pat( + db, + position.file_id, + binding + )?); + return Ok(Some((binding, descr))); }; - let name_ref = find_node_at_offset::(syntax, position.offset)?; - let descr = hir::Function::guess_for_name_ref(db, position.file_id, name_ref)?; + let name_ref = ctry!(find_node_at_offset::(syntax, position.offset)); + let descr = ctry!(hir::Function::guess_for_name_ref( + db, + position.file_id, + name_ref + )?); let scope = descr.scope(db); - let resolved = scope.resolve_local_name(name_ref)?; + let resolved = ctry!(scope.resolve_local_name(name_ref)); let resolved = resolved.ptr().resolve(source_file); - let binding = find_node_at_offset::(syntax, resolved.range().end())?; - Some((binding, descr)) + let binding = ctry!(find_node_at_offset::( + syntax, + resolved.range().end() + )); + Ok(Some((binding, descr))) } } @@ -408,7 +419,9 @@ impl AnalysisImpl { if fs.kind == FN_DEF { let fn_file = self.db.source_file(fn_file_id); if let Some(fn_def) = find_node_at_offset(fn_file.syntax(), fs.node_range.start()) { - let descr = hir::Function::guess_from_source(&*self.db, fn_file_id, fn_def); + let descr = ctry!(hir::Function::guess_from_source( + &*self.db, fn_file_id, fn_def + )?); if let Some(descriptor) = descr.signature_info(&*self.db) { // If we have a calling expression let's find which argument we are on let mut current_parameter = None; diff --git a/crates/ra_analysis/src/lib.rs b/crates/ra_analysis/src/lib.rs index 12df580ba..90528edfd 100644 --- a/crates/ra_analysis/src/lib.rs +++ b/crates/ra_analysis/src/lib.rs @@ -248,7 +248,7 @@ impl Analysis { self.imp.approximately_resolve_symbol(position) } pub fn find_all_refs(&self, position: FilePosition) -> Cancelable> { - Ok(self.imp.find_all_refs(position)) + self.imp.find_all_refs(position) } pub fn doc_comment_for( &self, diff --git a/crates/ra_hir/src/db.rs b/crates/ra_hir/src/db.rs index 2f01bae6d..ff41fd326 100644 --- a/crates/ra_hir/src/db.rs +++ b/crates/ra_hir/src/db.rs @@ -7,10 +7,11 @@ use ra_syntax::{ use ra_db::{SourceRootId, LocationIntener, SyntaxDatabase, FileId, Cancelable}; use crate::{ - DefLoc, DefId, FnId, + DefLoc, DefId, SourceFileItems, SourceItemId, query_definitions, FnScopes, + function::FnId, module::{ModuleId, ModuleTree, ModuleSource, nameres::{ItemMap, InputModuleItems}}, }; @@ -19,7 +20,6 @@ salsa::query_group! { pub trait HirDatabase: SyntaxDatabase + AsRef> - + AsRef> { fn fn_scopes(fn_id: FnId) -> Arc { type FnScopesQuery; diff --git a/crates/ra_hir/src/function/mod.rs b/crates/ra_hir/src/function/mod.rs index c8af2e54f..a6757601e 100644 --- a/crates/ra_hir/src/function/mod.rs +++ b/crates/ra_hir/src/function/mod.rs @@ -12,19 +12,15 @@ use ra_syntax::{ use ra_db::FileId; use crate::{ - FnId, HirDatabase, SourceItemId, + Cancelable, + DefLoc, DefKind, DefId, HirDatabase, SourceItemId, + Module, }; pub use self::scope::FnScopes; -impl FnId { - pub fn get(db: &impl HirDatabase, file_id: FileId, fn_def: ast::FnDef) -> FnId { - let file_items = db.file_items(file_id); - let item_id = file_items.id_of(fn_def.syntax()); - let item_id = SourceItemId { file_id, item_id }; - FnId::from_loc(db, &item_id) - } -} +#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)] +pub struct FnId(pub(crate) DefId); pub struct Function { fn_id: FnId, @@ -35,16 +31,26 @@ impl Function { db: &impl HirDatabase, file_id: FileId, fn_def: ast::FnDef, - ) -> Function { - let fn_id = FnId::get(db, file_id, fn_def); - Function { fn_id } + ) -> Cancelable> { + let module = ctry!(Module::guess_from_child_node(db, file_id, fn_def.syntax())?); + let file_items = db.file_items(file_id); + let item_id = file_items.id_of(fn_def.syntax()); + let source_item_id = SourceItemId { file_id, item_id }; + let def_loc = DefLoc { + kind: DefKind::Function, + source_root_id: module.source_root_id, + module_id: module.module_id, + source_item_id, + }; + let fn_id = FnId(def_loc.id(db)); + Ok(Some(Function { fn_id })) } pub fn guess_for_name_ref( db: &impl HirDatabase, file_id: FileId, name_ref: ast::NameRef, - ) -> Option { + ) -> Cancelable> { Function::guess_for_node(db, file_id, name_ref.syntax()) } @@ -52,7 +58,7 @@ impl Function { db: &impl HirDatabase, file_id: FileId, bind_pat: ast::BindPat, - ) -> Option { + ) -> Cancelable> { Function::guess_for_node(db, file_id, bind_pat.syntax()) } @@ -60,10 +66,9 @@ impl Function { db: &impl HirDatabase, file_id: FileId, node: SyntaxNodeRef, - ) -> Option { - let fn_def = node.ancestors().find_map(ast::FnDef::cast)?; - let res = Function::guess_from_source(db, file_id, fn_def); - Some(res) + ) -> Cancelable> { + let fn_def = ctry!(node.ancestors().find_map(ast::FnDef::cast)); + Function::guess_from_source(db, file_id, fn_def) } pub fn scope(&self, db: &impl HirDatabase) -> Arc { diff --git a/crates/ra_hir/src/lib.rs b/crates/ra_hir/src/lib.rs index ffc99fd5f..dbcc5e46d 100644 --- a/crates/ra_hir/src/lib.rs +++ b/crates/ra_hir/src/lib.rs @@ -41,22 +41,6 @@ pub use self::{ pub use self::function::FnSignatureInfo; -#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] -pub struct FnId(u32); -ra_db::impl_numeric_id!(FnId); - -impl FnId { - pub fn from_loc( - db: &impl AsRef>, - loc: &SourceItemId, - ) -> FnId { - db.as_ref().loc2id(loc) - } - pub fn loc(self, db: &impl AsRef>) -> SourceItemId { - db.as_ref().id2loc(self) - } -} - #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] pub struct DefId(u32); ra_db::impl_numeric_id!(DefId); @@ -64,6 +48,7 @@ ra_db::impl_numeric_id!(DefId); #[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)] pub(crate) enum DefKind { Module, + Function, Item, } @@ -89,6 +74,7 @@ impl DefLoc { pub enum Def { Module(Module), + Function(Function), Item, } @@ -100,7 +86,7 @@ impl DefId { let descr = Module::new(db, loc.source_root_id, loc.module_id)?; Def::Module(descr) } - DefKind::Item => Def::Item, + DefKind::Item | DefKind::Function => Def::Item, }; Ok(res) } diff --git a/crates/ra_hir/src/mock.rs b/crates/ra_hir/src/mock.rs index 8e256b89f..e855df11d 100644 --- a/crates/ra_hir/src/mock.rs +++ b/crates/ra_hir/src/mock.rs @@ -6,7 +6,7 @@ use ra_db::{LocationIntener, BaseDatabase, FilePosition, mock::FileMap, FileId, use relative_path::RelativePathBuf; use test_utils::{parse_fixture, CURSOR_MARKER, extract_offset}; -use crate::{db, DefId, DefLoc, FnId, SourceItemId}; +use crate::{db, DefId, DefLoc}; #[derive(Debug)] pub(crate) struct MockDatabase { @@ -65,7 +65,6 @@ impl MockDatabase { #[derive(Debug, Default)] struct IdMaps { - fns: LocationIntener, defs: LocationIntener, } @@ -117,12 +116,6 @@ impl AsRef> for MockDatabase { } } -impl AsRef> for MockDatabase { - fn as_ref(&self) -> &LocationIntener { - &self.id_maps.fns - } -} - impl MockDatabase { pub(crate) fn log(&self, f: impl FnOnce()) -> Vec> { *self.events.lock() = Some(Vec::new()); diff --git a/crates/ra_hir/src/module/mod.rs b/crates/ra_hir/src/module/mod.rs index 08ce7c8d1..11e6e8e75 100644 --- a/crates/ra_hir/src/module/mod.rs +++ b/crates/ra_hir/src/module/mod.rs @@ -8,7 +8,7 @@ use ra_editor::find_node_at_offset; use ra_syntax::{ algo::generate, ast::{self, AstNode, NameOwner}, - SmolStr, SyntaxNode, + SmolStr, SyntaxNode, SyntaxNodeRef, }; use ra_db::{SourceRootId, FileId, FilePosition, Cancelable}; use relative_path::RelativePathBuf; @@ -25,8 +25,8 @@ pub use self::nameres::ModuleScope; #[derive(Debug, Clone)] pub struct Module { tree: Arc, - source_root_id: SourceRootId, - module_id: ModuleId, + pub(crate) source_root_id: SourceRootId, + pub(crate) module_id: ModuleId, } impl Module { @@ -57,6 +57,23 @@ impl Module { Module::guess_from_source(db, module_source) } + pub fn guess_from_child_node( + db: &impl HirDatabase, + file_id: FileId, + node: SyntaxNodeRef, + ) -> Cancelable> { + let module_source = if let Some(m) = node + .ancestors() + .filter_map(ast::Module::cast) + .find(|it| !it.has_semi()) + { + ModuleSource::new_inline(db, file_id, m) + } else { + ModuleSource::new_file(db, file_id) + }; + Module::guess_from_source(db, module_source) + } + fn guess_from_source( db: &impl HirDatabase, module_source: ModuleSource, diff --git a/crates/ra_hir/src/query_definitions.rs b/crates/ra_hir/src/query_definitions.rs index 59318f307..e4d721601 100644 --- a/crates/ra_hir/src/query_definitions.rs +++ b/crates/ra_hir/src/query_definitions.rs @@ -11,21 +11,21 @@ use ra_syntax::{ use ra_db::{SourceRootId, FileId, Cancelable,}; use crate::{ - FnId, - SourceFileItems, SourceItemId, - db::HirDatabase, - function::FnScopes, - module::{ - ModuleSource, ModuleSourceNode, ModuleId, - imp::Submodule, - nameres::{InputModuleItems, ItemMap, Resolver}, - }, + SourceFileItems, SourceItemId, DefKind, + db::HirDatabase, + function::{FnScopes, FnId}, + module::{ + ModuleSource, ModuleSourceNode, ModuleId, + imp::Submodule, + nameres::{InputModuleItems, ItemMap, Resolver}, + }, }; /// Resolve `FnId` to the corresponding `SyntaxNode` pub(super) fn fn_syntax(db: &impl HirDatabase, fn_id: FnId) -> FnDefNode { - let item_id = fn_id.loc(db); - let syntax = db.file_item(item_id); + let def_loc = fn_id.0.loc(db); + assert!(def_loc.kind == DefKind::Function); + let syntax = db.file_item(def_loc.source_item_id); FnDef::cast(syntax.borrowed()).unwrap().owned() } -- cgit v1.2.3 From 54d053c881514b024ba399ce2edc678e3f710ab7 Mon Sep 17 00:00:00 2001 From: Aleksey Kladov Date: Tue, 4 Dec 2018 23:52:14 +0300 Subject: minor --- crates/ra_hir/src/function/mod.rs | 8 ++++++-- crates/ra_hir/src/lib.rs | 16 +++++++++++----- 2 files changed, 17 insertions(+), 7 deletions(-) diff --git a/crates/ra_hir/src/function/mod.rs b/crates/ra_hir/src/function/mod.rs index a6757601e..e00bca6e3 100644 --- a/crates/ra_hir/src/function/mod.rs +++ b/crates/ra_hir/src/function/mod.rs @@ -27,6 +27,11 @@ pub struct Function { } impl Function { + pub(crate) fn new(def_id: DefId) -> Function { + let fn_id = FnId(def_id); + Function { fn_id } + } + pub fn guess_from_source( db: &impl HirDatabase, file_id: FileId, @@ -42,8 +47,7 @@ impl Function { module_id: module.module_id, source_item_id, }; - let fn_id = FnId(def_loc.id(db)); - Ok(Some(Function { fn_id })) + Ok(Some(Function::new(def_loc.id(db)))) } pub fn guess_for_name_ref( diff --git a/crates/ra_hir/src/lib.rs b/crates/ra_hir/src/lib.rs index dbcc5e46d..9168dad3b 100644 --- a/crates/ra_hir/src/lib.rs +++ b/crates/ra_hir/src/lib.rs @@ -41,6 +41,8 @@ pub use self::{ pub use self::function::FnSignatureInfo; +/// Def's are a core concept of hir. A `Def` is an Item (function, module, etc) +/// in a specific module. #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] pub struct DefId(u32); ra_db::impl_numeric_id!(DefId); @@ -61,13 +63,13 @@ pub struct DefLoc { } impl DefId { - pub fn loc(self, db: &impl AsRef>) -> DefLoc { + pub(crate) fn loc(self, db: &impl AsRef>) -> DefLoc { db.as_ref().id2loc(self) } } impl DefLoc { - pub fn id(&self, db: &impl AsRef>) -> DefId { + pub(crate) fn id(&self, db: &impl AsRef>) -> DefId { db.as_ref().loc2id(&self) } } @@ -83,10 +85,14 @@ impl DefId { let loc = self.loc(db); let res = match loc.kind { DefKind::Module => { - let descr = Module::new(db, loc.source_root_id, loc.module_id)?; - Def::Module(descr) + let module = Module::new(db, loc.source_root_id, loc.module_id)?; + Def::Module(module) } - DefKind::Item | DefKind::Function => Def::Item, + DefKind::Function => { + let function = Function::new(self); + Def::Function(function) + } + DefKind::Item => Def::Item, }; Ok(res) } -- cgit v1.2.3