aboutsummaryrefslogtreecommitdiff
path: root/crates/ra_hir/src/code_model_impl/module.rs
diff options
context:
space:
mode:
Diffstat (limited to 'crates/ra_hir/src/code_model_impl/module.rs')
-rw-r--r--crates/ra_hir/src/code_model_impl/module.rs104
1 files changed, 69 insertions, 35 deletions
diff --git a/crates/ra_hir/src/code_model_impl/module.rs b/crates/ra_hir/src/code_model_impl/module.rs
index 437f96942..f7d15c55e 100644
--- a/crates/ra_hir/src/code_model_impl/module.rs
+++ b/crates/ra_hir/src/code_model_impl/module.rs
@@ -1,33 +1,61 @@
1use ra_syntax::{ast, SyntaxNode, TreeArc}; 1use ra_db::FileId;
2use ra_syntax::{ast, SyntaxNode, TreeArc, AstNode};
2 3
3use crate::{ 4use crate::{
4 Module, ModuleSource, Problem, 5 Module, ModuleSource, Problem, Name,
5 Name, 6 nameres::{CrateModuleId, ImportId},
6 module_tree::ModuleId,
7 nameres::lower::ImportId,
8 HirDatabase, PersistentHirDatabase, 7 HirDatabase, PersistentHirDatabase,
9 HirFileId 8 HirFileId, SourceItemId,
10}; 9};
11 10
11impl ModuleSource {
12 pub(crate) fn new(
13 db: &impl PersistentHirDatabase,
14 file_id: Option<FileId>,
15 decl_id: Option<SourceItemId>,
16 ) -> ModuleSource {
17 match (file_id, decl_id) {
18 (Some(file_id), _) => {
19 let source_file = db.parse(file_id);
20 ModuleSource::SourceFile(source_file)
21 }
22 (None, Some(item_id)) => {
23 let module = db.file_item(item_id);
24 let module = ast::Module::cast(&*module).unwrap();
25 assert!(module.item_list().is_some(), "expected inline module");
26 ModuleSource::Module(module.to_owned())
27 }
28 (None, None) => panic!(),
29 }
30 }
31}
32
12impl Module { 33impl Module {
13 fn with_module_id(&self, module_id: ModuleId) -> Module { 34 fn with_module_id(&self, module_id: CrateModuleId) -> Module {
14 Module { module_id, krate: self.krate } 35 Module { module_id, krate: self.krate }
15 } 36 }
16 37
17 pub(crate) fn name_impl(&self, db: &impl HirDatabase) -> Option<Name> { 38 pub(crate) fn name_impl(&self, db: &impl HirDatabase) -> Option<Name> {
18 let module_tree = db.module_tree(self.krate); 39 let def_map = db.crate_def_map(self.krate);
19 let link = self.module_id.parent_link(&module_tree)?; 40 let parent = def_map[self.module_id].parent?;
20 Some(link.name(&module_tree).clone()) 41 def_map[parent].children.iter().find_map(|(name, module_id)| {
42 if *module_id == self.module_id {
43 Some(name.clone())
44 } else {
45 None
46 }
47 })
21 } 48 }
22 49
23 pub(crate) fn definition_source_impl( 50 pub(crate) fn definition_source_impl(
24 &self, 51 &self,
25 db: &impl PersistentHirDatabase, 52 db: &impl PersistentHirDatabase,
26 ) -> (HirFileId, ModuleSource) { 53 ) -> (HirFileId, ModuleSource) {
27 let module_tree = db.module_tree(self.krate); 54 let def_map = db.crate_def_map(self.krate);
28 let file_id = self.module_id.file_id(&module_tree); 55 let decl_id = def_map[self.module_id].declaration;
29 let decl_id = self.module_id.decl_id(&module_tree); 56 let file_id = def_map[self.module_id].definition;
30 let module_source = ModuleSource::new(db, file_id, decl_id); 57 let module_source = ModuleSource::new(db, file_id, decl_id);
58 let file_id = file_id.map(HirFileId::from).unwrap_or_else(|| decl_id.unwrap().file_id);
31 (file_id, module_source) 59 (file_id, module_source)
32 } 60 }
33 61
@@ -35,11 +63,11 @@ impl Module {
35 &self, 63 &self,
36 db: &impl HirDatabase, 64 db: &impl HirDatabase,
37 ) -> Option<(HirFileId, TreeArc<ast::Module>)> { 65 ) -> Option<(HirFileId, TreeArc<ast::Module>)> {
38 let module_tree = db.module_tree(self.krate); 66 let def_map = db.crate_def_map(self.krate);
39 let link = self.module_id.parent_link(&module_tree)?; 67 let decl = def_map[self.module_id].declaration?;
40 let file_id = link.owner(&module_tree).file_id(&module_tree); 68 let syntax_node = db.file_item(decl);
41 let src = link.source(&module_tree, db); 69 let ast = ast::Module::cast(&syntax_node).unwrap().to_owned();
42 Some((file_id, src)) 70 Some((decl.file_id, ast))
43 } 71 }
44 72
45 pub(crate) fn import_source_impl( 73 pub(crate) fn import_source_impl(
@@ -47,22 +75,21 @@ impl Module {
47 db: &impl HirDatabase, 75 db: &impl HirDatabase,
48 import: ImportId, 76 import: ImportId,
49 ) -> TreeArc<ast::PathSegment> { 77 ) -> TreeArc<ast::PathSegment> {
50 let (_, source_map) = db.lower_module_with_source_map(*self); 78 let (file_id, source) = self.definition_source(db);
51 let (_, source) = self.definition_source(db); 79 let (_, source_map) = db.raw_items_with_source_map(file_id.original_file(db));
52 source_map.get(&source, import) 80 source_map.get(&source, import)
53 } 81 }
54 82
55 pub(crate) fn crate_root_impl(&self, db: &impl PersistentHirDatabase) -> Module { 83 pub(crate) fn crate_root_impl(&self, db: &impl PersistentHirDatabase) -> Module {
56 let module_tree = db.module_tree(self.krate); 84 let def_map = db.crate_def_map(self.krate);
57 let module_id = self.module_id.crate_root(&module_tree); 85 self.with_module_id(def_map.root())
58 self.with_module_id(module_id)
59 } 86 }
60 87
61 /// Finds a child module with the specified name. 88 /// Finds a child module with the specified name.
62 pub(crate) fn child_impl(&self, db: &impl HirDatabase, name: &Name) -> Option<Module> { 89 pub(crate) fn child_impl(&self, db: &impl HirDatabase, name: &Name) -> Option<Module> {
63 let module_tree = db.module_tree(self.krate); 90 let def_map = db.crate_def_map(self.krate);
64 let child_id = self.module_id.child(&module_tree, name)?; 91 let child_id = def_map[self.module_id].children.get(name)?;
65 Some(self.with_module_id(child_id)) 92 Some(self.with_module_id(*child_id))
66 } 93 }
67 94
68 /// Iterates over all child modules. 95 /// Iterates over all child modules.
@@ -70,18 +97,18 @@ impl Module {
70 &self, 97 &self,
71 db: &impl PersistentHirDatabase, 98 db: &impl PersistentHirDatabase,
72 ) -> impl Iterator<Item = Module> { 99 ) -> impl Iterator<Item = Module> {
73 let module_tree = db.module_tree(self.krate); 100 let def_map = db.crate_def_map(self.krate);
74 let children = self 101 let children = def_map[self.module_id]
75 .module_id 102 .children
76 .children(&module_tree) 103 .iter()
77 .map(|(_, module_id)| self.with_module_id(module_id)) 104 .map(|(_, module_id)| self.with_module_id(*module_id))
78 .collect::<Vec<_>>(); 105 .collect::<Vec<_>>();
79 children.into_iter() 106 children.into_iter()
80 } 107 }
81 108
82 pub(crate) fn parent_impl(&self, db: &impl PersistentHirDatabase) -> Option<Module> { 109 pub(crate) fn parent_impl(&self, db: &impl PersistentHirDatabase) -> Option<Module> {
83 let module_tree = db.module_tree(self.krate); 110 let def_map = db.crate_def_map(self.krate);
84 let parent_id = self.module_id.parent(&module_tree)?; 111 let parent_id = def_map[self.module_id].parent?;
85 Some(self.with_module_id(parent_id)) 112 Some(self.with_module_id(parent_id))
86 } 113 }
87 114
@@ -89,7 +116,14 @@ impl Module {
89 &self, 116 &self,
90 db: &impl HirDatabase, 117 db: &impl HirDatabase,
91 ) -> Vec<(TreeArc<SyntaxNode>, Problem)> { 118 ) -> Vec<(TreeArc<SyntaxNode>, Problem)> {
92 let module_tree = db.module_tree(self.krate); 119 let def_map = db.crate_def_map(self.krate);
93 self.module_id.problems(&module_tree, db) 120 let (my_file_id, _) = self.definition_source(db);
121 // FIXME: not entirely corret filterint by module
122 def_map
123 .problems()
124 .iter()
125 .filter(|(source_item_id, _problem)| my_file_id == source_item_id.file_id)
126 .map(|(source_item_id, problem)| (db.file_item(*source_item_id), problem.clone()))
127 .collect()
94 } 128 }
95} 129}