aboutsummaryrefslogtreecommitdiff
path: root/crates/ra_hir/src
diff options
context:
space:
mode:
Diffstat (limited to 'crates/ra_hir/src')
-rw-r--r--crates/ra_hir/src/code_model.rs35
-rw-r--r--crates/ra_hir/src/db.rs4
-rw-r--r--crates/ra_hir/src/from_source.rs93
-rw-r--r--crates/ra_hir/src/has_source.rs16
-rw-r--r--crates/ra_hir/src/lib.rs4
-rw-r--r--crates/ra_hir/src/source_binder.rs11
6 files changed, 89 insertions, 74 deletions
diff --git a/crates/ra_hir/src/code_model.rs b/crates/ra_hir/src/code_model.rs
index 8dbc0d667..4cd28eb4e 100644
--- a/crates/ra_hir/src/code_model.rs
+++ b/crates/ra_hir/src/code_model.rs
@@ -12,8 +12,8 @@ use hir_def::{
12 resolver::HasResolver, 12 resolver::HasResolver,
13 type_ref::{Mutability, TypeRef}, 13 type_ref::{Mutability, TypeRef},
14 AdtId, ConstId, DefWithBodyId, EnumId, FunctionId, HasModule, ImplId, LocalEnumVariantId, 14 AdtId, ConstId, DefWithBodyId, EnumId, FunctionId, HasModule, ImplId, LocalEnumVariantId,
15 LocalImportId, LocalModuleId, LocalStructFieldId, Lookup, ModuleId, StaticId, StructId, 15 LocalModuleId, LocalStructFieldId, Lookup, ModuleId, StaticId, StructId, TraitId, TypeAliasId,
16 TraitId, TypeAliasId, TypeParamId, UnionId, 16 TypeParamId, UnionId,
17}; 17};
18use hir_expand::{ 18use hir_expand::{
19 diagnostics::DiagnosticSink, 19 diagnostics::DiagnosticSink,
@@ -180,13 +180,11 @@ impl Module {
180 } 180 }
181 181
182 /// Returns a `ModuleScope`: a set of items, visible in this module. 182 /// Returns a `ModuleScope`: a set of items, visible in this module.
183 pub fn scope(self, db: &impl HirDatabase) -> Vec<(Name, ScopeDef, Option<Import>)> { 183 pub fn scope(self, db: &impl HirDatabase) -> Vec<(Name, ScopeDef)> {
184 db.crate_def_map(self.id.krate)[self.id.local_id] 184 db.crate_def_map(self.id.krate)[self.id.local_id]
185 .scope 185 .scope
186 .entries() 186 .entries()
187 .map(|(name, res)| { 187 .map(|(name, res)| (name.clone(), res.def.into()))
188 (name.clone(), res.def.into(), res.import.map(|id| Import { parent: self, id }))
189 })
190 .collect() 188 .collect()
191 } 189 }
192 190
@@ -221,7 +219,7 @@ impl Module {
221 219
222 pub fn impl_blocks(self, db: &impl DefDatabase) -> Vec<ImplBlock> { 220 pub fn impl_blocks(self, db: &impl DefDatabase) -> Vec<ImplBlock> {
223 let def_map = db.crate_def_map(self.id.krate); 221 let def_map = db.crate_def_map(self.id.krate);
224 def_map[self.id.local_id].impls.iter().copied().map(ImplBlock::from).collect() 222 def_map[self.id.local_id].scope.impls().map(ImplBlock::from).collect()
225 } 223 }
226 224
227 pub(crate) fn with_module_id(self, module_id: LocalModuleId) -> Module { 225 pub(crate) fn with_module_id(self, module_id: LocalModuleId) -> Module {
@@ -229,11 +227,6 @@ impl Module {
229 } 227 }
230} 228}
231 229
232pub struct Import {
233 pub(crate) parent: Module,
234 pub(crate) id: LocalImportId,
235}
236
237#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] 230#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
238pub struct StructField { 231pub struct StructField {
239 pub(crate) parent: VariantDef, 232 pub(crate) parent: VariantDef,
@@ -269,7 +262,7 @@ pub struct Struct {
269 262
270impl Struct { 263impl Struct {
271 pub fn module(self, db: &impl DefDatabase) -> Module { 264 pub fn module(self, db: &impl DefDatabase) -> Module {
272 Module { id: self.id.lookup(db).container } 265 Module { id: self.id.lookup(db).container.module(db) }
273 } 266 }
274 267
275 pub fn krate(self, db: &impl DefDatabase) -> Option<Crate> { 268 pub fn krate(self, db: &impl DefDatabase) -> Option<Crate> {
@@ -290,7 +283,7 @@ impl Struct {
290 } 283 }
291 284
292 pub fn ty(self, db: &impl HirDatabase) -> Type { 285 pub fn ty(self, db: &impl HirDatabase) -> Type {
293 Type::from_def(db, self.id.lookup(db).container.krate, self.id) 286 Type::from_def(db, self.id.lookup(db).container.module(db).krate, self.id)
294 } 287 }
295 288
296 fn variant_data(self, db: &impl DefDatabase) -> Arc<VariantData> { 289 fn variant_data(self, db: &impl DefDatabase) -> Arc<VariantData> {
@@ -309,11 +302,11 @@ impl Union {
309 } 302 }
310 303
311 pub fn module(self, db: &impl DefDatabase) -> Module { 304 pub fn module(self, db: &impl DefDatabase) -> Module {
312 Module { id: self.id.lookup(db).container } 305 Module { id: self.id.lookup(db).container.module(db) }
313 } 306 }
314 307
315 pub fn ty(self, db: &impl HirDatabase) -> Type { 308 pub fn ty(self, db: &impl HirDatabase) -> Type {
316 Type::from_def(db, self.id.lookup(db).container.krate, self.id) 309 Type::from_def(db, self.id.lookup(db).container.module(db).krate, self.id)
317 } 310 }
318 311
319 pub fn fields(self, db: &impl HirDatabase) -> Vec<StructField> { 312 pub fn fields(self, db: &impl HirDatabase) -> Vec<StructField> {
@@ -337,7 +330,7 @@ pub struct Enum {
337 330
338impl Enum { 331impl Enum {
339 pub fn module(self, db: &impl DefDatabase) -> Module { 332 pub fn module(self, db: &impl DefDatabase) -> Module {
340 Module { id: self.id.lookup(db).container } 333 Module { id: self.id.lookup(db).container.module(db) }
341 } 334 }
342 335
343 pub fn krate(self, db: &impl DefDatabase) -> Option<Crate> { 336 pub fn krate(self, db: &impl DefDatabase) -> Option<Crate> {
@@ -357,7 +350,7 @@ impl Enum {
357 } 350 }
358 351
359 pub fn ty(self, db: &impl HirDatabase) -> Type { 352 pub fn ty(self, db: &impl HirDatabase) -> Type {
360 Type::from_def(db, self.id.lookup(db).container.krate, self.id) 353 Type::from_def(db, self.id.lookup(db).container.module(db).krate, self.id)
361 } 354 }
362} 355}
363 356
@@ -553,7 +546,7 @@ pub struct Trait {
553 546
554impl Trait { 547impl Trait {
555 pub fn module(self, db: &impl DefDatabase) -> Module { 548 pub fn module(self, db: &impl DefDatabase) -> Module {
556 Module { id: self.id.lookup(db).container } 549 Module { id: self.id.lookup(db).container.module(db) }
557 } 550 }
558 551
559 pub fn name(self, db: &impl DefDatabase) -> Name { 552 pub fn name(self, db: &impl DefDatabase) -> Name {
@@ -754,7 +747,7 @@ impl ImplBlock {
754 let environment = TraitEnvironment::lower(db, &resolver); 747 let environment = TraitEnvironment::lower(db, &resolver);
755 let ty = Ty::from_hir(db, &resolver, &impl_data.target_type); 748 let ty = Ty::from_hir(db, &resolver, &impl_data.target_type);
756 Type { 749 Type {
757 krate: self.id.lookup(db).container.krate, 750 krate: self.id.lookup(db).container.module(db).krate,
758 ty: InEnvironment { value: ty, environment }, 751 ty: InEnvironment { value: ty, environment },
759 } 752 }
760 } 753 }
@@ -768,7 +761,7 @@ impl ImplBlock {
768 } 761 }
769 762
770 pub fn module(&self, db: &impl DefDatabase) -> Module { 763 pub fn module(&self, db: &impl DefDatabase) -> Module {
771 self.id.lookup(db).container.into() 764 self.id.lookup(db).container.module(db).into()
772 } 765 }
773 766
774 pub fn krate(&self, db: &impl DefDatabase) -> Crate { 767 pub fn krate(&self, db: &impl DefDatabase) -> Crate {
diff --git a/crates/ra_hir/src/db.rs b/crates/ra_hir/src/db.rs
index bfae3660b..f5ffd64fa 100644
--- a/crates/ra_hir/src/db.rs
+++ b/crates/ra_hir/src/db.rs
@@ -4,8 +4,8 @@ pub use hir_def::db::{
4 BodyQuery, BodyWithSourceMapQuery, ConstDataQuery, CrateDefMapQuery, CrateLangItemsQuery, 4 BodyQuery, BodyWithSourceMapQuery, ConstDataQuery, CrateDefMapQuery, CrateLangItemsQuery,
5 DefDatabase, DefDatabaseStorage, DocumentationQuery, EnumDataQuery, ExprScopesQuery, 5 DefDatabase, DefDatabaseStorage, DocumentationQuery, EnumDataQuery, ExprScopesQuery,
6 FunctionDataQuery, GenericParamsQuery, ImplDataQuery, InternDatabase, InternDatabaseStorage, 6 FunctionDataQuery, GenericParamsQuery, ImplDataQuery, InternDatabase, InternDatabaseStorage,
7 LangItemQuery, ModuleLangItemsQuery, RawItemsQuery, RawItemsWithSourceMapQuery, 7 LangItemQuery, ModuleLangItemsQuery, RawItemsQuery, StaticDataQuery, StructDataQuery,
8 StaticDataQuery, StructDataQuery, TraitDataQuery, TypeAliasDataQuery, 8 TraitDataQuery, TypeAliasDataQuery,
9}; 9};
10pub use hir_expand::db::{ 10pub use hir_expand::db::{
11 AstDatabase, AstDatabaseStorage, AstIdMapQuery, MacroArgQuery, MacroDefQuery, MacroExpandQuery, 11 AstDatabase, AstDatabaseStorage, AstIdMapQuery, MacroArgQuery, MacroDefQuery, MacroExpandQuery,
diff --git a/crates/ra_hir/src/from_source.rs b/crates/ra_hir/src/from_source.rs
index 7abb4bd75..6314be8d4 100644
--- a/crates/ra_hir/src/from_source.rs
+++ b/crates/ra_hir/src/from_source.rs
@@ -1,24 +1,28 @@
1//! FIXME: write short doc here 1//! Finds a corresponding hir data structure for a syntax node in a specific
2//! file.
3
2use hir_def::{ 4use hir_def::{
3 child_by_source::ChildBySource, dyn_map::DynMap, keys, keys::Key, nameres::ModuleSource, 5 child_by_source::ChildBySource, dyn_map::DynMap, keys, keys::Key, nameres::ModuleSource,
4 ConstId, EnumId, EnumVariantId, FunctionId, GenericDefId, ImplId, ModuleId, StaticId, StructId, 6 ConstId, DefWithBodyId, EnumId, EnumVariantId, FunctionId, GenericDefId, ImplId, ModuleId,
5 TraitId, TypeAliasId, UnionId, VariantId, 7 StaticId, StructId, TraitId, TypeAliasId, UnionId, VariantId,
6}; 8};
7use hir_expand::{name::AsName, AstId, MacroDefId, MacroDefKind}; 9use hir_expand::{name::AsName, AstId, MacroDefId, MacroDefKind};
10use ra_db::FileId;
11use ra_prof::profile;
8use ra_syntax::{ 12use ra_syntax::{
9 ast::{self, AstNode, NameOwner}, 13 ast::{self, AstNode, NameOwner},
10 match_ast, SyntaxNode, 14 match_ast, SyntaxNode,
11}; 15};
12 16
13use crate::{ 17use crate::{
14 db::{AstDatabase, DefDatabase, HirDatabase}, 18 db::{DefDatabase, HirDatabase},
15 Const, DefWithBody, Enum, EnumVariant, FieldSource, Function, ImplBlock, InFile, Local, 19 Const, DefWithBody, Enum, EnumVariant, FieldSource, Function, ImplBlock, InFile, Local,
16 MacroDef, Module, Static, Struct, StructField, Trait, TypeAlias, TypeParam, Union, 20 MacroDef, Module, Static, Struct, StructField, Trait, TypeAlias, TypeParam, Union,
17}; 21};
18 22
19pub trait FromSource: Sized { 23pub trait FromSource: Sized {
20 type Ast; 24 type Ast;
21 fn from_source(db: &(impl DefDatabase + AstDatabase), src: InFile<Self::Ast>) -> Option<Self>; 25 fn from_source(db: &impl DefDatabase, src: InFile<Self::Ast>) -> Option<Self>;
22} 26}
23 27
24pub trait FromSourceByContainer: Sized { 28pub trait FromSourceByContainer: Sized {
@@ -32,7 +36,7 @@ where
32 T: From<<T as FromSourceByContainer>::Id>, 36 T: From<<T as FromSourceByContainer>::Id>,
33{ 37{
34 type Ast = <T as FromSourceByContainer>::Ast; 38 type Ast = <T as FromSourceByContainer>::Ast;
35 fn from_source(db: &(impl DefDatabase + AstDatabase), src: InFile<Self::Ast>) -> Option<Self> { 39 fn from_source(db: &impl DefDatabase, src: InFile<Self::Ast>) -> Option<Self> {
36 analyze_container(db, src.as_ref().map(|it| it.syntax()))[T::KEY] 40 analyze_container(db, src.as_ref().map(|it| it.syntax()))[T::KEY]
37 .get(&src) 41 .get(&src)
38 .copied() 42 .copied()
@@ -64,7 +68,7 @@ from_source_by_container_impls![
64 68
65impl FromSource for MacroDef { 69impl FromSource for MacroDef {
66 type Ast = ast::MacroCall; 70 type Ast = ast::MacroCall;
67 fn from_source(db: &(impl DefDatabase + AstDatabase), src: InFile<Self::Ast>) -> Option<Self> { 71 fn from_source(db: &impl DefDatabase, src: InFile<Self::Ast>) -> Option<Self> {
68 let kind = MacroDefKind::Declarative; 72 let kind = MacroDefKind::Declarative;
69 73
70 let module_src = ModuleSource::from_child_node(db, src.as_ref().map(|it| it.syntax())); 74 let module_src = ModuleSource::from_child_node(db, src.as_ref().map(|it| it.syntax()));
@@ -80,7 +84,7 @@ impl FromSource for MacroDef {
80 84
81impl FromSource for EnumVariant { 85impl FromSource for EnumVariant {
82 type Ast = ast::EnumVariant; 86 type Ast = ast::EnumVariant;
83 fn from_source(db: &(impl DefDatabase + AstDatabase), src: InFile<Self::Ast>) -> Option<Self> { 87 fn from_source(db: &impl DefDatabase, src: InFile<Self::Ast>) -> Option<Self> {
84 let parent_enum = src.value.parent_enum(); 88 let parent_enum = src.value.parent_enum();
85 let src_enum = InFile { file_id: src.file_id, value: parent_enum }; 89 let src_enum = InFile { file_id: src.file_id, value: parent_enum };
86 let parent_enum = Enum::from_source(db, src_enum)?; 90 let parent_enum = Enum::from_source(db, src_enum)?;
@@ -93,7 +97,7 @@ impl FromSource for EnumVariant {
93 97
94impl FromSource for StructField { 98impl FromSource for StructField {
95 type Ast = FieldSource; 99 type Ast = FieldSource;
96 fn from_source(db: &(impl DefDatabase + AstDatabase), src: InFile<Self::Ast>) -> Option<Self> { 100 fn from_source(db: &impl DefDatabase, src: InFile<Self::Ast>) -> Option<Self> {
97 let src = src.as_ref(); 101 let src = src.as_ref();
98 102
99 // FIXME this is buggy 103 // FIXME this is buggy
@@ -167,6 +171,7 @@ impl TypeParam {
167 171
168impl Module { 172impl Module {
169 pub fn from_declaration(db: &impl DefDatabase, src: InFile<ast::Module>) -> Option<Self> { 173 pub fn from_declaration(db: &impl DefDatabase, src: InFile<ast::Module>) -> Option<Self> {
174 let _p = profile("Module::from_declaration");
170 let parent_declaration = src.value.syntax().ancestors().skip(1).find_map(ast::Module::cast); 175 let parent_declaration = src.value.syntax().ancestors().skip(1).find_map(ast::Module::cast);
171 176
172 let parent_module = match parent_declaration { 177 let parent_module = match parent_declaration {
@@ -189,6 +194,7 @@ impl Module {
189 } 194 }
190 195
191 pub fn from_definition(db: &impl DefDatabase, src: InFile<ModuleSource>) -> Option<Self> { 196 pub fn from_definition(db: &impl DefDatabase, src: InFile<ModuleSource>) -> Option<Self> {
197 let _p = profile("Module::from_definition");
192 match src.value { 198 match src.value {
193 ModuleSource::Module(ref module) => { 199 ModuleSource::Module(ref module) => {
194 assert!(!module.has_semi()); 200 assert!(!module.has_semi());
@@ -201,10 +207,14 @@ impl Module {
201 }; 207 };
202 208
203 let original_file = src.file_id.original_file(db); 209 let original_file = src.file_id.original_file(db);
210 Module::from_file(db, original_file)
211 }
204 212
205 let (krate, local_id) = db.relevant_crates(original_file).iter().find_map(|&crate_id| { 213 fn from_file(db: &impl DefDatabase, file: FileId) -> Option<Self> {
214 let _p = profile("Module::from_file");
215 let (krate, local_id) = db.relevant_crates(file).iter().find_map(|&crate_id| {
206 let crate_def_map = db.crate_def_map(crate_id); 216 let crate_def_map = db.crate_def_map(crate_id);
207 let local_id = crate_def_map.modules_for_file(original_file).next()?; 217 let local_id = crate_def_map.modules_for_file(file).next()?;
208 Some((crate_id, local_id)) 218 Some((crate_id, local_id))
209 })?; 219 })?;
210 Some(Module { id: ModuleId { krate, local_id } }) 220 Some(Module { id: ModuleId { krate, local_id } })
@@ -212,29 +222,44 @@ impl Module {
212} 222}
213 223
214fn analyze_container(db: &impl DefDatabase, src: InFile<&SyntaxNode>) -> DynMap { 224fn analyze_container(db: &impl DefDatabase, src: InFile<&SyntaxNode>) -> DynMap {
215 _analyze_container(db, src).unwrap_or_default() 225 let _p = profile("analyze_container");
216} 226 return child_by_source(db, src).unwrap_or_default();
217 227
218fn _analyze_container(db: &impl DefDatabase, src: InFile<&SyntaxNode>) -> Option<DynMap> { 228 fn child_by_source(db: &impl DefDatabase, src: InFile<&SyntaxNode>) -> Option<DynMap> {
219 // FIXME: this doesn't try to handle nested declarations 229 for container in src.value.ancestors().skip(1) {
220 for container in src.value.ancestors().skip(1) { 230 let res = match_ast! {
221 let res = match_ast! { 231 match container {
222 match container { 232 ast::TraitDef(it) => {
223 ast::TraitDef(it) => { 233 let def = Trait::from_source(db, src.with_value(it))?;
224 let c = Trait::from_source(db, src.with_value(it))?; 234 def.id.child_by_source(db)
225 c.id.child_by_source(db) 235 },
226 }, 236 ast::ImplBlock(it) => {
227 ast::ImplBlock(it) => { 237 let def = ImplBlock::from_source(db, src.with_value(it))?;
228 let c = ImplBlock::from_source(db, src.with_value(it))?; 238 def.id.child_by_source(db)
229 c.id.child_by_source(db) 239 },
230 }, 240 ast::FnDef(it) => {
231 _ => { continue }, 241 let def = Function::from_source(db, src.with_value(it))?;
232 } 242 DefWithBodyId::from(def.id)
233 }; 243 .child_by_source(db)
234 return Some(res); 244 },
235 } 245 ast::StaticDef(it) => {
246 let def = Static::from_source(db, src.with_value(it))?;
247 DefWithBodyId::from(def.id)
248 .child_by_source(db)
249 },
250 ast::ConstDef(it) => {
251 let def = Const::from_source(db, src.with_value(it))?;
252 DefWithBodyId::from(def.id)
253 .child_by_source(db)
254 },
255 _ => { continue },
256 }
257 };
258 return Some(res);
259 }
236 260
237 let module_source = ModuleSource::from_child_node(db, src); 261 let module_source = ModuleSource::from_child_node(db, src);
238 let c = Module::from_definition(db, src.with_value(module_source))?; 262 let c = Module::from_definition(db, src.with_value(module_source))?;
239 Some(c.id.child_by_source(db)) 263 Some(c.id.child_by_source(db))
264 }
240} 265}
diff --git a/crates/ra_hir/src/has_source.rs b/crates/ra_hir/src/has_source.rs
index 72afecf26..5541266e2 100644
--- a/crates/ra_hir/src/has_source.rs
+++ b/crates/ra_hir/src/has_source.rs
@@ -9,8 +9,8 @@ use hir_def::{
9use ra_syntax::ast; 9use ra_syntax::ast;
10 10
11use crate::{ 11use crate::{
12 db::DefDatabase, Const, Enum, EnumVariant, FieldSource, Function, ImplBlock, Import, MacroDef, 12 db::DefDatabase, Const, Enum, EnumVariant, FieldSource, Function, ImplBlock, MacroDef, Module,
13 Module, Static, Struct, StructField, Trait, TypeAlias, TypeParam, Union, 13 Static, Struct, StructField, Trait, TypeAlias, TypeParam, Union,
14}; 14};
15 15
16pub use hir_expand::InFile; 16pub use hir_expand::InFile;
@@ -117,18 +117,6 @@ impl HasSource for ImplBlock {
117 self.id.lookup(db).source(db) 117 self.id.lookup(db).source(db)
118 } 118 }
119} 119}
120impl HasSource for Import {
121 type Ast = Either<ast::UseTree, ast::ExternCrateItem>;
122
123 /// Returns the syntax of the last path segment corresponding to this import
124 fn source(self, db: &impl DefDatabase) -> InFile<Self::Ast> {
125 let src = self.parent.definition_source(db);
126 let (_, source_map) = db.raw_items_with_source_map(src.file_id);
127 let root = db.parse_or_expand(src.file_id).unwrap();
128 let ptr = source_map.get(self.id);
129 src.with_value(ptr.map_left(|it| it.to_node(&root)).map_right(|it| it.to_node(&root)))
130 }
131}
132 120
133impl HasSource for TypeParam { 121impl HasSource for TypeParam {
134 type Ast = Either<ast::TraitDef, ast::TypeParam>; 122 type Ast = Either<ast::TraitDef, ast::TypeParam>;
diff --git a/crates/ra_hir/src/lib.rs b/crates/ra_hir/src/lib.rs
index 7f9aef770..0008a8858 100644
--- a/crates/ra_hir/src/lib.rs
+++ b/crates/ra_hir/src/lib.rs
@@ -40,8 +40,8 @@ mod from_source;
40pub use crate::{ 40pub use crate::{
41 code_model::{ 41 code_model::{
42 Adt, AssocItem, AttrDef, Const, Crate, CrateDependency, DefWithBody, Docs, Enum, 42 Adt, AssocItem, AttrDef, Const, Crate, CrateDependency, DefWithBody, Docs, Enum,
43 EnumVariant, FieldSource, Function, GenericDef, HasAttrs, ImplBlock, Import, Local, 43 EnumVariant, FieldSource, Function, GenericDef, HasAttrs, ImplBlock, Local, MacroDef,
44 MacroDef, Module, ModuleDef, ScopeDef, Static, Struct, StructField, Trait, Type, TypeAlias, 44 Module, ModuleDef, ScopeDef, Static, Struct, StructField, Trait, Type, TypeAlias,
45 TypeParam, Union, VariantDef, 45 TypeParam, Union, VariantDef,
46 }, 46 },
47 from_source::FromSource, 47 from_source::FromSource,
diff --git a/crates/ra_hir/src/source_binder.rs b/crates/ra_hir/src/source_binder.rs
index d326169b3..85b378483 100644
--- a/crates/ra_hir/src/source_binder.rs
+++ b/crates/ra_hir/src/source_binder.rs
@@ -26,6 +26,7 @@ use hir_ty::{
26 method_resolution::{self, implements_trait}, 26 method_resolution::{self, implements_trait},
27 Canonical, InEnvironment, InferenceResult, TraitEnvironment, Ty, 27 Canonical, InEnvironment, InferenceResult, TraitEnvironment, Ty,
28}; 28};
29use ra_prof::profile;
29use ra_syntax::{ 30use ra_syntax::{
30 ast::{self, AstNode}, 31 ast::{self, AstNode},
31 match_ast, AstPtr, 32 match_ast, AstPtr,
@@ -83,6 +84,7 @@ fn def_with_body_from_child_node(
83 db: &impl HirDatabase, 84 db: &impl HirDatabase,
84 child: InFile<&SyntaxNode>, 85 child: InFile<&SyntaxNode>,
85) -> Option<DefWithBody> { 86) -> Option<DefWithBody> {
87 let _p = profile("def_with_body_from_child_node");
86 child.cloned().ancestors_with_macros(db).find_map(|node| { 88 child.cloned().ancestors_with_macros(db).find_map(|node| {
87 let n = &node.value; 89 let n = &node.value;
88 match_ast! { 90 match_ast! {
@@ -169,6 +171,7 @@ impl SourceAnalyzer {
169 node: InFile<&SyntaxNode>, 171 node: InFile<&SyntaxNode>,
170 offset: Option<TextUnit>, 172 offset: Option<TextUnit>,
171 ) -> SourceAnalyzer { 173 ) -> SourceAnalyzer {
174 let _p = profile("SourceAnalyzer::new");
172 let def_with_body = def_with_body_from_child_node(db, node); 175 let def_with_body = def_with_body_from_child_node(db, node);
173 if let Some(def) = def_with_body { 176 if let Some(def) = def_with_body {
174 let (_body, source_map) = db.body_with_source_map(def.into()); 177 let (_body, source_map) = db.body_with_source_map(def.into());
@@ -237,7 +240,13 @@ impl SourceAnalyzer {
237 } 240 }
238 241
239 pub fn resolve_record_field(&self, field: &ast::RecordField) -> Option<crate::StructField> { 242 pub fn resolve_record_field(&self, field: &ast::RecordField) -> Option<crate::StructField> {
240 let expr_id = self.expr_id(&field.expr()?)?; 243 let expr_id = match field.expr() {
244 Some(it) => self.expr_id(&it)?,
245 None => {
246 let src = InFile { file_id: self.file_id, value: field };
247 self.body_source_map.as_ref()?.field_init_shorthand_expr(src)?
248 }
249 };
241 self.infer.as_ref()?.record_field_resolution(expr_id).map(|it| it.into()) 250 self.infer.as_ref()?.record_field_resolution(expr_id).map(|it| it.into())
242 } 251 }
243 252