aboutsummaryrefslogtreecommitdiff
path: root/crates/ra_hir/src/code_model_impl
diff options
context:
space:
mode:
Diffstat (limited to 'crates/ra_hir/src/code_model_impl')
-rw-r--r--crates/ra_hir/src/code_model_impl/function.rs7
-rw-r--r--crates/ra_hir/src/code_model_impl/krate.rs10
-rw-r--r--crates/ra_hir/src/code_model_impl/module.rs118
3 files changed, 61 insertions, 74 deletions
diff --git a/crates/ra_hir/src/code_model_impl/function.rs b/crates/ra_hir/src/code_model_impl/function.rs
index 8d6b7fc19..66d7e1713 100644
--- a/crates/ra_hir/src/code_model_impl/function.rs
+++ b/crates/ra_hir/src/code_model_impl/function.rs
@@ -2,7 +2,6 @@ mod scope;
2 2
3use std::sync::Arc; 3use std::sync::Arc;
4 4
5use ra_db::Cancelable;
6use ra_syntax::{TreeArc, ast::{self, NameOwner}}; 5use ra_syntax::{TreeArc, ast::{self, NameOwner}};
7 6
8use crate::{ 7use crate::{
@@ -20,16 +19,16 @@ impl Function {
20 Function { def_id } 19 Function { def_id }
21 } 20 }
22 21
23 pub(crate) fn body(&self, db: &impl HirDatabase) -> Cancelable<Arc<Body>> { 22 pub(crate) fn body(&self, db: &impl HirDatabase) -> Arc<Body> {
24 db.body_hir(self.def_id) 23 db.body_hir(self.def_id)
25 } 24 }
26 25
27 pub(crate) fn module(&self, db: &impl HirDatabase) -> Cancelable<Module> { 26 pub(crate) fn module(&self, db: &impl HirDatabase) -> Module {
28 self.def_id.module(db) 27 self.def_id.module(db)
29 } 28 }
30 29
31 /// The containing impl block, if this is a method. 30 /// The containing impl block, if this is a method.
32 pub(crate) fn impl_block(&self, db: &impl HirDatabase) -> Cancelable<Option<ImplBlock>> { 31 pub(crate) fn impl_block(&self, db: &impl HirDatabase) -> Option<ImplBlock> {
33 self.def_id.impl_block(db) 32 self.def_id.impl_block(db)
34 } 33 }
35} 34}
diff --git a/crates/ra_hir/src/code_model_impl/krate.rs b/crates/ra_hir/src/code_model_impl/krate.rs
index 3275eafed..8c6e34873 100644
--- a/crates/ra_hir/src/code_model_impl/krate.rs
+++ b/crates/ra_hir/src/code_model_impl/krate.rs
@@ -1,4 +1,4 @@
1use ra_db::{CrateId, Cancelable}; 1use ra_db::CrateId;
2 2
3use crate::{ 3use crate::{
4 HirFileId, Crate, CrateDependency, AsName, DefLoc, DefKind, Module, SourceItemId, 4 HirFileId, Crate, CrateDependency, AsName, DefLoc, DefKind, Module, SourceItemId,
@@ -20,18 +20,18 @@ impl Crate {
20 }) 20 })
21 .collect() 21 .collect()
22 } 22 }
23 pub(crate) fn root_module_impl(&self, db: &impl HirDatabase) -> Cancelable<Option<Module>> { 23 pub(crate) fn root_module_impl(&self, db: &impl HirDatabase) -> Option<Module> {
24 let crate_graph = db.crate_graph(); 24 let crate_graph = db.crate_graph();
25 let file_id = crate_graph.crate_root(self.crate_id); 25 let file_id = crate_graph.crate_root(self.crate_id);
26 let source_root_id = db.file_source_root(file_id); 26 let source_root_id = db.file_source_root(file_id);
27 let file_id = HirFileId::from(file_id); 27 let file_id = HirFileId::from(file_id);
28 let module_tree = db.module_tree(source_root_id)?; 28 let module_tree = db.module_tree(source_root_id);
29 // FIXME: teach module tree about crate roots instead of guessing 29 // FIXME: teach module tree about crate roots instead of guessing
30 let source = SourceItemId { 30 let source = SourceItemId {
31 file_id, 31 file_id,
32 item_id: None, 32 item_id: None,
33 }; 33 };
34 let module_id = ctry!(module_tree.find_module_by_source(source)); 34 let module_id = module_tree.find_module_by_source(source)?;
35 35
36 let def_loc = DefLoc { 36 let def_loc = DefLoc {
37 kind: DefKind::Module, 37 kind: DefKind::Module,
@@ -42,6 +42,6 @@ impl Crate {
42 let def_id = def_loc.id(db); 42 let def_id = def_loc.id(db);
43 43
44 let module = Module::new(def_id); 44 let module = Module::new(def_id);
45 Ok(Some(module)) 45 Some(module)
46 } 46 }
47} 47}
diff --git a/crates/ra_hir/src/code_model_impl/module.rs b/crates/ra_hir/src/code_model_impl/module.rs
index 775dd6709..a5c032d69 100644
--- a/crates/ra_hir/src/code_model_impl/module.rs
+++ b/crates/ra_hir/src/code_model_impl/module.rs
@@ -1,4 +1,4 @@
1use ra_db::{Cancelable, SourceRootId, FileId}; 1use ra_db::{SourceRootId, FileId};
2use ra_syntax::{ast, SyntaxNode, AstNode, TreeArc}; 2use ra_syntax::{ast, SyntaxNode, AstNode, TreeArc};
3 3
4use crate::{ 4use crate::{
@@ -18,8 +18,8 @@ impl Module {
18 db: &impl HirDatabase, 18 db: &impl HirDatabase,
19 source_root_id: SourceRootId, 19 source_root_id: SourceRootId,
20 module_id: ModuleId, 20 module_id: ModuleId,
21 ) -> Cancelable<Self> { 21 ) -> Self {
22 let module_tree = db.module_tree(source_root_id)?; 22 let module_tree = db.module_tree(source_root_id);
23 let def_loc = DefLoc { 23 let def_loc = DefLoc {
24 kind: DefKind::Module, 24 kind: DefKind::Module,
25 source_root_id, 25 source_root_id,
@@ -27,21 +27,17 @@ impl Module {
27 source_item_id: module_id.source(&module_tree), 27 source_item_id: module_id.source(&module_tree),
28 }; 28 };
29 let def_id = def_loc.id(db); 29 let def_id = def_loc.id(db);
30 let module = Module::new(def_id); 30 Module::new(def_id)
31 Ok(module)
32 } 31 }
33 32
34 pub(crate) fn name_impl(&self, db: &impl HirDatabase) -> Cancelable<Option<Name>> { 33 pub(crate) fn name_impl(&self, db: &impl HirDatabase) -> Option<Name> {
35 let loc = self.def_id.loc(db); 34 let loc = self.def_id.loc(db);
36 let module_tree = db.module_tree(loc.source_root_id)?; 35 let module_tree = db.module_tree(loc.source_root_id);
37 let link = ctry!(loc.module_id.parent_link(&module_tree)); 36 let link = loc.module_id.parent_link(&module_tree)?;
38 Ok(Some(link.name(&module_tree).clone())) 37 Some(link.name(&module_tree).clone())
39 } 38 }
40 39
41 pub fn definition_source_impl( 40 pub fn definition_source_impl(&self, db: &impl HirDatabase) -> (FileId, ModuleSource) {
42 &self,
43 db: &impl HirDatabase,
44 ) -> Cancelable<(FileId, ModuleSource)> {
45 let loc = self.def_id.loc(db); 41 let loc = self.def_id.loc(db);
46 let file_id = loc.source_item_id.file_id.as_original_file(); 42 let file_id = loc.source_item_id.file_id.as_original_file();
47 let syntax_node = db.file_item(loc.source_item_id); 43 let syntax_node = db.file_item(loc.source_item_id);
@@ -51,94 +47,89 @@ impl Module {
51 let module = ast::Module::cast(&syntax_node).unwrap(); 47 let module = ast::Module::cast(&syntax_node).unwrap();
52 ModuleSource::Module(module.to_owned()) 48 ModuleSource::Module(module.to_owned())
53 }; 49 };
54 Ok((file_id, module_source)) 50 (file_id, module_source)
55 } 51 }
56 52
57 pub fn declaration_source_impl( 53 pub fn declaration_source_impl(
58 &self, 54 &self,
59 db: &impl HirDatabase, 55 db: &impl HirDatabase,
60 ) -> Cancelable<Option<(FileId, TreeArc<ast::Module>)>> { 56 ) -> Option<(FileId, TreeArc<ast::Module>)> {
61 let loc = self.def_id.loc(db); 57 let loc = self.def_id.loc(db);
62 let module_tree = db.module_tree(loc.source_root_id)?; 58 let module_tree = db.module_tree(loc.source_root_id);
63 let link = ctry!(loc.module_id.parent_link(&module_tree)); 59 let link = loc.module_id.parent_link(&module_tree)?;
64 let file_id = link 60 let file_id = link
65 .owner(&module_tree) 61 .owner(&module_tree)
66 .source(&module_tree) 62 .source(&module_tree)
67 .file_id 63 .file_id
68 .as_original_file(); 64 .as_original_file();
69 let src = link.source(&module_tree, db); 65 let src = link.source(&module_tree, db);
70 Ok(Some((file_id, src))) 66 Some((file_id, src))
71 } 67 }
72 68
73 pub(crate) fn krate_impl(&self, db: &impl HirDatabase) -> Cancelable<Option<Crate>> { 69 pub(crate) fn krate_impl(&self, db: &impl HirDatabase) -> Option<Crate> {
74 let root = self.crate_root(db)?; 70 let root = self.crate_root(db);
75 let loc = root.def_id.loc(db); 71 let loc = root.def_id.loc(db);
76 let file_id = loc.source_item_id.file_id.as_original_file(); 72 let file_id = loc.source_item_id.file_id.as_original_file();
77 73
78 let crate_graph = db.crate_graph(); 74 let crate_graph = db.crate_graph();
79 let crate_id = ctry!(crate_graph.crate_id_for_crate_root(file_id)); 75 let crate_id = crate_graph.crate_id_for_crate_root(file_id)?;
80 Ok(Some(Crate::new(crate_id))) 76 Some(Crate::new(crate_id))
81 } 77 }
82 78
83 pub(crate) fn crate_root_impl(&self, db: &impl HirDatabase) -> Cancelable<Module> { 79 pub(crate) fn crate_root_impl(&self, db: &impl HirDatabase) -> Module {
84 let loc = self.def_id.loc(db); 80 let loc = self.def_id.loc(db);
85 let module_tree = db.module_tree(loc.source_root_id)?; 81 let module_tree = db.module_tree(loc.source_root_id);
86 let module_id = loc.module_id.crate_root(&module_tree); 82 let module_id = loc.module_id.crate_root(&module_tree);
87 Module::from_module_id(db, loc.source_root_id, module_id) 83 Module::from_module_id(db, loc.source_root_id, module_id)
88 } 84 }
89 85
90 /// Finds a child module with the specified name. 86 /// Finds a child module with the specified name.
91 pub fn child_impl(&self, db: &impl HirDatabase, name: &Name) -> Cancelable<Option<Module>> { 87 pub fn child_impl(&self, db: &impl HirDatabase, name: &Name) -> Option<Module> {
92 let loc = self.def_id.loc(db); 88 let loc = self.def_id.loc(db);
93 let module_tree = db.module_tree(loc.source_root_id)?; 89 let module_tree = db.module_tree(loc.source_root_id);
94 let child_id = ctry!(loc.module_id.child(&module_tree, name)); 90 let child_id = loc.module_id.child(&module_tree, name)?;
95 Module::from_module_id(db, loc.source_root_id, child_id).map(Some) 91 Some(Module::from_module_id(db, loc.source_root_id, child_id))
96 } 92 }
97 93
98 /// Iterates over all child modules. 94 /// Iterates over all child modules.
99 pub fn children_impl(&self, db: &impl HirDatabase) -> Cancelable<impl Iterator<Item = Module>> { 95 pub fn children_impl(&self, db: &impl HirDatabase) -> impl Iterator<Item = Module> {
100 // FIXME this should be implementable without collecting into a vec, but 96 // FIXME this should be implementable without collecting into a vec, but
101 // it's kind of hard since the iterator needs to keep a reference to the 97 // it's kind of hard since the iterator needs to keep a reference to the
102 // module tree. 98 // module tree.
103 let loc = self.def_id.loc(db); 99 let loc = self.def_id.loc(db);
104 let module_tree = db.module_tree(loc.source_root_id)?; 100 let module_tree = db.module_tree(loc.source_root_id);
105 let children = loc 101 let children = loc
106 .module_id 102 .module_id
107 .children(&module_tree) 103 .children(&module_tree)
108 .map(|(_, module_id)| Module::from_module_id(db, loc.source_root_id, module_id)) 104 .map(|(_, module_id)| Module::from_module_id(db, loc.source_root_id, module_id))
109 .collect::<Cancelable<Vec<_>>>()?; 105 .collect::<Vec<_>>();
110 Ok(children.into_iter()) 106 children.into_iter()
111 } 107 }
112 108
113 pub fn parent_impl(&self, db: &impl HirDatabase) -> Cancelable<Option<Module>> { 109 pub fn parent_impl(&self, db: &impl HirDatabase) -> Option<Module> {
114 let loc = self.def_id.loc(db); 110 let loc = self.def_id.loc(db);
115 let module_tree = db.module_tree(loc.source_root_id)?; 111 let module_tree = db.module_tree(loc.source_root_id);
116 let parent_id = ctry!(loc.module_id.parent(&module_tree)); 112 let parent_id = loc.module_id.parent(&module_tree)?;
117 Module::from_module_id(db, loc.source_root_id, parent_id).map(Some) 113 Some(Module::from_module_id(db, loc.source_root_id, parent_id))
118 } 114 }
119 115
120 /// Returns a `ModuleScope`: a set of items, visible in this module. 116 /// Returns a `ModuleScope`: a set of items, visible in this module.
121 pub fn scope_impl(&self, db: &impl HirDatabase) -> Cancelable<ModuleScope> { 117 pub fn scope_impl(&self, db: &impl HirDatabase) -> ModuleScope {
122 let loc = self.def_id.loc(db); 118 let loc = self.def_id.loc(db);
123 let item_map = db.item_map(loc.source_root_id)?; 119 let item_map = db.item_map(loc.source_root_id);
124 let res = item_map.per_module[&loc.module_id].clone(); 120 item_map.per_module[&loc.module_id].clone()
125 Ok(res)
126 } 121 }
127 122
128 pub fn resolve_path_impl( 123 pub fn resolve_path_impl(&self, db: &impl HirDatabase, path: &Path) -> PerNs<DefId> {
129 &self,
130 db: &impl HirDatabase,
131 path: &Path,
132 ) -> Cancelable<PerNs<DefId>> {
133 let mut curr_per_ns = PerNs::types( 124 let mut curr_per_ns = PerNs::types(
134 match path.kind { 125 match path.kind {
135 PathKind::Crate => self.crate_root(db)?, 126 PathKind::Crate => self.crate_root(db),
136 PathKind::Self_ | PathKind::Plain => self.clone(), 127 PathKind::Self_ | PathKind::Plain => self.clone(),
137 PathKind::Super => { 128 PathKind::Super => {
138 if let Some(p) = self.parent(db)? { 129 if let Some(p) = self.parent(db) {
139 p 130 p
140 } else { 131 } else {
141 return Ok(PerNs::none()); 132 return PerNs::none();
142 } 133 }
143 } 134 }
144 } 135 }
@@ -150,47 +141,44 @@ impl Module {
150 let curr = if let Some(r) = curr_per_ns.as_ref().take_types() { 141 let curr = if let Some(r) = curr_per_ns.as_ref().take_types() {
151 r 142 r
152 } else { 143 } else {
153 return Ok(PerNs::none()); 144 return PerNs::none();
154 }; 145 };
155 let module = match curr.resolve(db)? { 146 let module = match curr.resolve(db) {
156 Def::Module(it) => it, 147 Def::Module(it) => it,
157 Def::Enum(e) => { 148 Def::Enum(e) => {
158 if segments.len() == idx + 1 { 149 if segments.len() == idx + 1 {
159 // enum variant 150 // enum variant
160 let matching_variant = 151 let matching_variant =
161 e.variants(db)?.into_iter().find(|(n, _variant)| n == name); 152 e.variants(db).into_iter().find(|(n, _variant)| n == name);
162 153
163 if let Some((_n, variant)) = matching_variant { 154 if let Some((_n, variant)) = matching_variant {
164 return Ok(PerNs::both(variant.def_id(), e.def_id())); 155 return PerNs::both(variant.def_id(), e.def_id());
165 } else { 156 } else {
166 return Ok(PerNs::none()); 157 return PerNs::none();
167 } 158 }
168 } else if segments.len() == idx { 159 } else if segments.len() == idx {
169 // enum 160 // enum
170 return Ok(PerNs::types(e.def_id())); 161 return PerNs::types(e.def_id());
171 } else { 162 } else {
172 // malformed enum? 163 // malformed enum?
173 return Ok(PerNs::none()); 164 return PerNs::none();
174 } 165 }
175 } 166 }
176 _ => return Ok(PerNs::none()), 167 _ => return PerNs::none(),
177 }; 168 };
178 let scope = module.scope(db)?; 169 let scope = module.scope(db);
179 curr_per_ns = if let Some(r) = scope.get(&name) { 170 curr_per_ns = if let Some(r) = scope.get(&name) {
180 r.def_id 171 r.def_id
181 } else { 172 } else {
182 return Ok(PerNs::none()); 173 return PerNs::none();
183 }; 174 };
184 } 175 }
185 Ok(curr_per_ns) 176 curr_per_ns
186 } 177 }
187 178
188 pub fn problems_impl( 179 pub fn problems_impl(&self, db: &impl HirDatabase) -> Vec<(TreeArc<SyntaxNode>, Problem)> {
189 &self,
190 db: &impl HirDatabase,
191 ) -> Cancelable<Vec<(TreeArc<SyntaxNode>, Problem)>> {
192 let loc = self.def_id.loc(db); 180 let loc = self.def_id.loc(db);
193 let module_tree = db.module_tree(loc.source_root_id)?; 181 let module_tree = db.module_tree(loc.source_root_id);
194 Ok(loc.module_id.problems(&module_tree, db)) 182 loc.module_id.problems(&module_tree, db)
195 } 183 }
196} 184}