diff options
Diffstat (limited to 'crates/hir')
-rw-r--r-- | crates/hir/src/attrs.rs | 6 | ||||
-rw-r--r-- | crates/hir/src/code_model.rs | 297 | ||||
-rw-r--r-- | crates/hir/src/db.rs | 14 | ||||
-rw-r--r-- | crates/hir/src/diagnostics.rs | 6 | ||||
-rw-r--r-- | crates/hir/src/from_id.rs | 21 | ||||
-rw-r--r-- | crates/hir/src/has_source.rs | 6 | ||||
-rw-r--r-- | crates/hir/src/semantics.rs | 12 | ||||
-rw-r--r-- | crates/hir/src/semantics/source_to_def.rs | 14 | ||||
-rw-r--r-- | crates/hir/src/source_analyzer.rs | 89 |
9 files changed, 261 insertions, 204 deletions
diff --git a/crates/hir/src/attrs.rs b/crates/hir/src/attrs.rs index 99fb65bac..9e6a3e155 100644 --- a/crates/hir/src/attrs.rs +++ b/crates/hir/src/attrs.rs | |||
@@ -2,6 +2,7 @@ | |||
2 | use hir_def::{ | 2 | use hir_def::{ |
3 | attr::{Attrs, Documentation}, | 3 | attr::{Attrs, Documentation}, |
4 | path::ModPath, | 4 | path::ModPath, |
5 | per_ns::PerNs, | ||
5 | resolver::HasResolver, | 6 | resolver::HasResolver, |
6 | AttrDefId, GenericParamId, ModuleDefId, | 7 | AttrDefId, GenericParamId, ModuleDefId, |
7 | }; | 8 | }; |
@@ -112,6 +113,11 @@ fn resolve_doc_path( | |||
112 | let path = ast::Path::parse(link).ok()?; | 113 | let path = ast::Path::parse(link).ok()?; |
113 | let modpath = ModPath::from_src(path, &Hygiene::new_unhygienic()).unwrap(); | 114 | let modpath = ModPath::from_src(path, &Hygiene::new_unhygienic()).unwrap(); |
114 | let resolved = resolver.resolve_module_path_in_items(db.upcast(), &modpath); | 115 | let resolved = resolver.resolve_module_path_in_items(db.upcast(), &modpath); |
116 | if resolved == PerNs::none() { | ||
117 | if let Some(trait_id) = resolver.resolve_module_path_in_trait_items(db.upcast(), &modpath) { | ||
118 | return Some(ModuleDefId::TraitId(trait_id)); | ||
119 | }; | ||
120 | } | ||
115 | let def = match ns { | 121 | let def = match ns { |
116 | Some(Namespace::Types) => resolved.take_types()?, | 122 | Some(Namespace::Types) => resolved.take_types()?, |
117 | Some(Namespace::Values) => resolved.take_values()?, | 123 | Some(Namespace::Values) => resolved.take_values()?, |
diff --git a/crates/hir/src/code_model.rs b/crates/hir/src/code_model.rs index 6cbf5cecf..fc1a74641 100644 --- a/crates/hir/src/code_model.rs +++ b/crates/hir/src/code_model.rs | |||
@@ -6,7 +6,6 @@ use base_db::{CrateDisplayName, CrateId, Edition, FileId}; | |||
6 | use either::Either; | 6 | use either::Either; |
7 | use hir_def::{ | 7 | use hir_def::{ |
8 | adt::{ReprKind, StructKind, VariantData}, | 8 | adt::{ReprKind, StructKind, VariantData}, |
9 | builtin_type::BuiltinType, | ||
10 | expr::{BindingAnnotation, LabelId, Pat, PatId}, | 9 | expr::{BindingAnnotation, LabelId, Pat, PatId}, |
11 | import_map, | 10 | import_map, |
12 | item_tree::ItemTreeNode, | 11 | item_tree::ItemTreeNode, |
@@ -15,11 +14,11 @@ use hir_def::{ | |||
15 | per_ns::PerNs, | 14 | per_ns::PerNs, |
16 | resolver::{HasResolver, Resolver}, | 15 | resolver::{HasResolver, Resolver}, |
17 | src::HasSource as _, | 16 | src::HasSource as _, |
18 | type_ref::{Mutability, TypeRef}, | 17 | type_ref::TypeRef, |
19 | AdtId, AssocContainerId, AssocItemId, AssocItemLoc, AttrDefId, ConstId, ConstParamId, | 18 | AdtId, AssocContainerId, AssocItemId, AssocItemLoc, AttrDefId, ConstId, ConstParamId, |
20 | DefWithBodyId, EnumId, FunctionId, GenericDefId, HasModule, ImplId, LifetimeParamId, | 19 | DefWithBodyId, EnumId, FunctionId, GenericDefId, HasModule, ImplId, LifetimeParamId, |
21 | LocalEnumVariantId, LocalFieldId, LocalModuleId, Lookup, ModuleId, StaticId, StructId, TraitId, | 20 | LocalEnumVariantId, LocalFieldId, Lookup, ModuleId, StaticId, StructId, TraitId, TypeAliasId, |
22 | TypeAliasId, TypeParamId, UnionId, | 21 | TypeParamId, UnionId, |
23 | }; | 22 | }; |
24 | use hir_def::{find_path::PrefixKind, item_scope::ItemInNs, visibility::Visibility}; | 23 | use hir_def::{find_path::PrefixKind, item_scope::ItemInNs, visibility::Visibility}; |
25 | use hir_expand::{ | 24 | use hir_expand::{ |
@@ -29,12 +28,12 @@ use hir_expand::{ | |||
29 | }; | 28 | }; |
30 | use hir_ty::{ | 29 | use hir_ty::{ |
31 | autoderef, | 30 | autoderef, |
32 | display::{write_bounds_like_dyn_trait, HirDisplayError, HirFormatter}, | 31 | display::{write_bounds_like_dyn_trait_with_prefix, HirDisplayError, HirFormatter}, |
33 | method_resolution, | 32 | method_resolution, |
34 | traits::{FnTrait, Solution, SolutionVariables}, | 33 | traits::{FnTrait, Solution, SolutionVariables}, |
35 | ApplicationTy, BoundVar, CallableDefId, Canonical, DebruijnIndex, FnSig, GenericPredicate, | 34 | AliasTy, BoundVar, CallableDefId, CallableSig, Canonical, DebruijnIndex, GenericPredicate, |
36 | InEnvironment, Obligation, ProjectionPredicate, ProjectionTy, Substs, TraitEnvironment, Ty, | 35 | InEnvironment, Mutability, Obligation, ProjectionPredicate, ProjectionTy, Scalar, Substs, |
37 | TyDefId, TyKind, TypeCtor, | 36 | TraitEnvironment, Ty, TyDefId, TyVariableKind, |
38 | }; | 37 | }; |
39 | use rustc_hash::FxHashSet; | 38 | use rustc_hash::FxHashSet; |
40 | use stdx::{format_to, impl_from}; | 39 | use stdx::{format_to, impl_from}; |
@@ -90,8 +89,8 @@ impl Crate { | |||
90 | } | 89 | } |
91 | 90 | ||
92 | pub fn root_module(self, db: &dyn HirDatabase) -> Module { | 91 | pub fn root_module(self, db: &dyn HirDatabase) -> Module { |
93 | let module_id = db.crate_def_map(self.id).root; | 92 | let def_map = db.crate_def_map(self.id); |
94 | Module::new(self, module_id) | 93 | Module { id: def_map.module_id(def_map.root()) } |
95 | } | 94 | } |
96 | 95 | ||
97 | pub fn root_file(self, db: &dyn HirDatabase) -> FileId { | 96 | pub fn root_file(self, db: &dyn HirDatabase) -> FileId { |
@@ -245,7 +244,7 @@ impl ModuleDef { | |||
245 | ModuleDef::Const(it) => it.name(db), | 244 | ModuleDef::Const(it) => it.name(db), |
246 | ModuleDef::Static(it) => it.name(db), | 245 | ModuleDef::Static(it) => it.name(db), |
247 | 246 | ||
248 | ModuleDef::BuiltinType(it) => Some(it.as_name()), | 247 | ModuleDef::BuiltinType(it) => Some(it.name()), |
249 | } | 248 | } |
250 | } | 249 | } |
251 | 250 | ||
@@ -270,18 +269,14 @@ impl ModuleDef { | |||
270 | None => return, | 269 | None => return, |
271 | }; | 270 | }; |
272 | 271 | ||
273 | hir_ty::diagnostics::validate_module_item(db, module.id.krate, id, sink) | 272 | hir_ty::diagnostics::validate_module_item(db, module.id.krate(), id, sink) |
274 | } | 273 | } |
275 | } | 274 | } |
276 | 275 | ||
277 | impl Module { | 276 | impl Module { |
278 | pub(crate) fn new(krate: Crate, crate_module_id: LocalModuleId) -> Module { | ||
279 | Module { id: ModuleId { krate: krate.id, local_id: crate_module_id } } | ||
280 | } | ||
281 | |||
282 | /// Name of this module. | 277 | /// Name of this module. |
283 | pub fn name(self, db: &dyn HirDatabase) -> Option<Name> { | 278 | pub fn name(self, db: &dyn HirDatabase) -> Option<Name> { |
284 | let def_map = db.crate_def_map(self.id.krate); | 279 | let def_map = self.id.def_map(db.upcast()); |
285 | let parent = def_map[self.id.local_id].parent?; | 280 | let parent = def_map[self.id.local_id].parent?; |
286 | def_map[parent].children.iter().find_map(|(name, module_id)| { | 281 | def_map[parent].children.iter().find_map(|(name, module_id)| { |
287 | if *module_id == self.id.local_id { | 282 | if *module_id == self.id.local_id { |
@@ -294,33 +289,34 @@ impl Module { | |||
294 | 289 | ||
295 | /// Returns the crate this module is part of. | 290 | /// Returns the crate this module is part of. |
296 | pub fn krate(self) -> Crate { | 291 | pub fn krate(self) -> Crate { |
297 | Crate { id: self.id.krate } | 292 | Crate { id: self.id.krate() } |
298 | } | 293 | } |
299 | 294 | ||
300 | /// Topmost parent of this module. Every module has a `crate_root`, but some | 295 | /// Topmost parent of this module. Every module has a `crate_root`, but some |
301 | /// might be missing `krate`. This can happen if a module's file is not included | 296 | /// might be missing `krate`. This can happen if a module's file is not included |
302 | /// in the module tree of any target in `Cargo.toml`. | 297 | /// in the module tree of any target in `Cargo.toml`. |
303 | pub fn crate_root(self, db: &dyn HirDatabase) -> Module { | 298 | pub fn crate_root(self, db: &dyn HirDatabase) -> Module { |
304 | let def_map = db.crate_def_map(self.id.krate); | 299 | let def_map = db.crate_def_map(self.id.krate()); |
305 | self.with_module_id(def_map.root) | 300 | Module { id: def_map.module_id(def_map.root()) } |
306 | } | 301 | } |
307 | 302 | ||
308 | /// Iterates over all child modules. | 303 | /// Iterates over all child modules. |
309 | pub fn children(self, db: &dyn HirDatabase) -> impl Iterator<Item = Module> { | 304 | pub fn children(self, db: &dyn HirDatabase) -> impl Iterator<Item = Module> { |
310 | let def_map = db.crate_def_map(self.id.krate); | 305 | let def_map = self.id.def_map(db.upcast()); |
311 | let children = def_map[self.id.local_id] | 306 | let children = def_map[self.id.local_id] |
312 | .children | 307 | .children |
313 | .iter() | 308 | .iter() |
314 | .map(|(_, module_id)| self.with_module_id(*module_id)) | 309 | .map(|(_, module_id)| Module { id: def_map.module_id(*module_id) }) |
315 | .collect::<Vec<_>>(); | 310 | .collect::<Vec<_>>(); |
316 | children.into_iter() | 311 | children.into_iter() |
317 | } | 312 | } |
318 | 313 | ||
319 | /// Finds a parent module. | 314 | /// Finds a parent module. |
320 | pub fn parent(self, db: &dyn HirDatabase) -> Option<Module> { | 315 | pub fn parent(self, db: &dyn HirDatabase) -> Option<Module> { |
321 | let def_map = db.crate_def_map(self.id.krate); | 316 | // FIXME: handle block expressions as modules (their parent is in a different DefMap) |
317 | let def_map = self.id.def_map(db.upcast()); | ||
322 | let parent_id = def_map[self.id.local_id].parent?; | 318 | let parent_id = def_map[self.id.local_id].parent?; |
323 | Some(self.with_module_id(parent_id)) | 319 | Some(Module { id: def_map.module_id(parent_id) }) |
324 | } | 320 | } |
325 | 321 | ||
326 | pub fn path_to_root(self, db: &dyn HirDatabase) -> Vec<Module> { | 322 | pub fn path_to_root(self, db: &dyn HirDatabase) -> Vec<Module> { |
@@ -339,7 +335,7 @@ impl Module { | |||
339 | db: &dyn HirDatabase, | 335 | db: &dyn HirDatabase, |
340 | visible_from: Option<Module>, | 336 | visible_from: Option<Module>, |
341 | ) -> Vec<(Name, ScopeDef)> { | 337 | ) -> Vec<(Name, ScopeDef)> { |
342 | db.crate_def_map(self.id.krate)[self.id.local_id] | 338 | self.id.def_map(db.upcast())[self.id.local_id] |
343 | .scope | 339 | .scope |
344 | .entries() | 340 | .entries() |
345 | .filter_map(|(name, def)| { | 341 | .filter_map(|(name, def)| { |
@@ -362,14 +358,14 @@ impl Module { | |||
362 | } | 358 | } |
363 | 359 | ||
364 | pub fn visibility_of(self, db: &dyn HirDatabase, def: &ModuleDef) -> Option<Visibility> { | 360 | pub fn visibility_of(self, db: &dyn HirDatabase, def: &ModuleDef) -> Option<Visibility> { |
365 | db.crate_def_map(self.id.krate)[self.id.local_id].scope.visibility_of(def.clone().into()) | 361 | self.id.def_map(db.upcast())[self.id.local_id].scope.visibility_of(def.clone().into()) |
366 | } | 362 | } |
367 | 363 | ||
368 | pub fn diagnostics(self, db: &dyn HirDatabase, sink: &mut DiagnosticSink) { | 364 | pub fn diagnostics(self, db: &dyn HirDatabase, sink: &mut DiagnosticSink) { |
369 | let _p = profile::span("Module::diagnostics").detail(|| { | 365 | let _p = profile::span("Module::diagnostics").detail(|| { |
370 | format!("{:?}", self.name(db).map_or("<unknown>".into(), |name| name.to_string())) | 366 | format!("{:?}", self.name(db).map_or("<unknown>".into(), |name| name.to_string())) |
371 | }); | 367 | }); |
372 | let crate_def_map = db.crate_def_map(self.id.krate); | 368 | let crate_def_map = self.id.def_map(db.upcast()); |
373 | crate_def_map.add_diagnostics(db.upcast(), self.id.local_id, sink); | 369 | crate_def_map.add_diagnostics(db.upcast(), self.id.local_id, sink); |
374 | for decl in self.declarations(db) { | 370 | for decl in self.declarations(db) { |
375 | match decl { | 371 | match decl { |
@@ -396,19 +392,15 @@ impl Module { | |||
396 | } | 392 | } |
397 | 393 | ||
398 | pub fn declarations(self, db: &dyn HirDatabase) -> Vec<ModuleDef> { | 394 | pub fn declarations(self, db: &dyn HirDatabase) -> Vec<ModuleDef> { |
399 | let def_map = db.crate_def_map(self.id.krate); | 395 | let def_map = self.id.def_map(db.upcast()); |
400 | def_map[self.id.local_id].scope.declarations().map(ModuleDef::from).collect() | 396 | def_map[self.id.local_id].scope.declarations().map(ModuleDef::from).collect() |
401 | } | 397 | } |
402 | 398 | ||
403 | pub fn impl_defs(self, db: &dyn HirDatabase) -> Vec<Impl> { | 399 | pub fn impl_defs(self, db: &dyn HirDatabase) -> Vec<Impl> { |
404 | let def_map = db.crate_def_map(self.id.krate); | 400 | let def_map = self.id.def_map(db.upcast()); |
405 | def_map[self.id.local_id].scope.impls().map(Impl::from).collect() | 401 | def_map[self.id.local_id].scope.impls().map(Impl::from).collect() |
406 | } | 402 | } |
407 | 403 | ||
408 | pub(crate) fn with_module_id(self, module_id: LocalModuleId) -> Module { | ||
409 | Module::new(self.krate(), module_id) | ||
410 | } | ||
411 | |||
412 | /// Finds a path that can be used to refer to the given item from within | 404 | /// Finds a path that can be used to refer to the given item from within |
413 | /// this module, if possible. | 405 | /// this module, if possible. |
414 | pub fn find_use_path(self, db: &dyn DefDatabase, item: impl Into<ItemInNs>) -> Option<ModPath> { | 406 | pub fn find_use_path(self, db: &dyn DefDatabase, item: impl Into<ItemInNs>) -> Option<ModPath> { |
@@ -457,7 +449,7 @@ impl Field { | |||
457 | }; | 449 | }; |
458 | let substs = Substs::type_params(db, generic_def_id); | 450 | let substs = Substs::type_params(db, generic_def_id); |
459 | let ty = db.field_types(var_id)[self.id].clone().subst(&substs); | 451 | let ty = db.field_types(var_id)[self.id].clone().subst(&substs); |
460 | Type::new(db, self.parent.module(db).id.krate, var_id, ty) | 452 | Type::new(db, self.parent.module(db).id.krate(), var_id, ty) |
461 | } | 453 | } |
462 | 454 | ||
463 | pub fn parent_def(&self, _db: &dyn HirDatabase) -> VariantDef { | 455 | pub fn parent_def(&self, _db: &dyn HirDatabase) -> VariantDef { |
@@ -502,7 +494,11 @@ impl Struct { | |||
502 | } | 494 | } |
503 | 495 | ||
504 | pub fn ty(self, db: &dyn HirDatabase) -> Type { | 496 | pub fn ty(self, db: &dyn HirDatabase) -> Type { |
505 | Type::from_def(db, self.id.lookup(db.upcast()).container.module(db.upcast()).krate, self.id) | 497 | Type::from_def( |
498 | db, | ||
499 | self.id.lookup(db.upcast()).container.module(db.upcast()).krate(), | ||
500 | self.id, | ||
501 | ) | ||
506 | } | 502 | } |
507 | 503 | ||
508 | pub fn repr(self, db: &dyn HirDatabase) -> Option<ReprKind> { | 504 | pub fn repr(self, db: &dyn HirDatabase) -> Option<ReprKind> { |
@@ -533,7 +529,11 @@ impl Union { | |||
533 | } | 529 | } |
534 | 530 | ||
535 | pub fn ty(self, db: &dyn HirDatabase) -> Type { | 531 | pub fn ty(self, db: &dyn HirDatabase) -> Type { |
536 | Type::from_def(db, self.id.lookup(db.upcast()).container.module(db.upcast()).krate, self.id) | 532 | Type::from_def( |
533 | db, | ||
534 | self.id.lookup(db.upcast()).container.module(db.upcast()).krate(), | ||
535 | self.id, | ||
536 | ) | ||
537 | } | 537 | } |
538 | 538 | ||
539 | pub fn fields(self, db: &dyn HirDatabase) -> Vec<Field> { | 539 | pub fn fields(self, db: &dyn HirDatabase) -> Vec<Field> { |
@@ -573,7 +573,11 @@ impl Enum { | |||
573 | } | 573 | } |
574 | 574 | ||
575 | pub fn ty(self, db: &dyn HirDatabase) -> Type { | 575 | pub fn ty(self, db: &dyn HirDatabase) -> Type { |
576 | Type::from_def(db, self.id.lookup(db.upcast()).container.module(db.upcast()).krate, self.id) | 576 | Type::from_def( |
577 | db, | ||
578 | self.id.lookup(db.upcast()).container.module(db.upcast()).krate(), | ||
579 | self.id, | ||
580 | ) | ||
577 | } | 581 | } |
578 | } | 582 | } |
579 | 583 | ||
@@ -632,7 +636,7 @@ impl Adt { | |||
632 | /// general set of completions, but will not look very nice when printed. | 636 | /// general set of completions, but will not look very nice when printed. |
633 | pub fn ty(self, db: &dyn HirDatabase) -> Type { | 637 | pub fn ty(self, db: &dyn HirDatabase) -> Type { |
634 | let id = AdtId::from(self); | 638 | let id = AdtId::from(self); |
635 | Type::from_def(db, id.module(db.upcast()).krate, id) | 639 | Type::from_def(db, id.module(db.upcast()).krate(), id) |
636 | } | 640 | } |
637 | 641 | ||
638 | pub fn module(self, db: &dyn HirDatabase) -> Module { | 642 | pub fn module(self, db: &dyn HirDatabase) -> Module { |
@@ -750,7 +754,7 @@ impl Function { | |||
750 | let ctx = hir_ty::TyLoweringContext::new(db, &resolver); | 754 | let ctx = hir_ty::TyLoweringContext::new(db, &resolver); |
751 | let environment = TraitEnvironment::lower(db, &resolver); | 755 | let environment = TraitEnvironment::lower(db, &resolver); |
752 | Type { | 756 | Type { |
753 | krate: self.id.lookup(db.upcast()).container.module(db.upcast()).krate, | 757 | krate: self.id.lookup(db.upcast()).container.module(db.upcast()).krate(), |
754 | ty: InEnvironment { value: Ty::from_hir_ext(&ctx, ret_type).0, environment }, | 758 | ty: InEnvironment { value: Ty::from_hir_ext(&ctx, ret_type).0, environment }, |
755 | } | 759 | } |
756 | } | 760 | } |
@@ -771,7 +775,7 @@ impl Function { | |||
771 | .iter() | 775 | .iter() |
772 | .map(|type_ref| { | 776 | .map(|type_ref| { |
773 | let ty = Type { | 777 | let ty = Type { |
774 | krate: self.id.lookup(db.upcast()).container.module(db.upcast()).krate, | 778 | krate: self.id.lookup(db.upcast()).container.module(db.upcast()).krate(), |
775 | ty: InEnvironment { | 779 | ty: InEnvironment { |
776 | value: Ty::from_hir_ext(&ctx, type_ref).0, | 780 | value: Ty::from_hir_ext(&ctx, type_ref).0, |
777 | environment: environment.clone(), | 781 | environment: environment.clone(), |
@@ -795,7 +799,7 @@ impl Function { | |||
795 | } | 799 | } |
796 | 800 | ||
797 | pub fn diagnostics(self, db: &dyn HirDatabase, sink: &mut DiagnosticSink) { | 801 | pub fn diagnostics(self, db: &dyn HirDatabase, sink: &mut DiagnosticSink) { |
798 | let krate = self.module(db).id.krate; | 802 | let krate = self.module(db).id.krate(); |
799 | hir_def::diagnostics::validate_body(db.upcast(), self.id.into(), sink); | 803 | hir_def::diagnostics::validate_body(db.upcast(), self.id.into(), sink); |
800 | hir_ty::diagnostics::validate_module_item(db, krate, self.id.into(), sink); | 804 | hir_ty::diagnostics::validate_module_item(db, krate, self.id.into(), sink); |
801 | hir_ty::diagnostics::validate_body(db, self.id.into(), sink); | 805 | hir_ty::diagnostics::validate_body(db, self.id.into(), sink); |
@@ -832,7 +836,7 @@ pub enum Access { | |||
832 | impl From<Mutability> for Access { | 836 | impl From<Mutability> for Access { |
833 | fn from(mutability: Mutability) -> Access { | 837 | fn from(mutability: Mutability) -> Access { |
834 | match mutability { | 838 | match mutability { |
835 | Mutability::Shared => Access::Shared, | 839 | Mutability::Not => Access::Shared, |
836 | Mutability::Mut => Access::Exclusive, | 840 | Mutability::Mut => Access::Exclusive, |
837 | } | 841 | } |
838 | } | 842 | } |
@@ -861,7 +865,10 @@ impl SelfParam { | |||
861 | .params | 865 | .params |
862 | .first() | 866 | .first() |
863 | .map(|param| match *param { | 867 | .map(|param| match *param { |
864 | TypeRef::Reference(.., mutability) => mutability.into(), | 868 | TypeRef::Reference(.., mutability) => match mutability { |
869 | hir_def::type_ref::Mutability::Shared => Access::Shared, | ||
870 | hir_def::type_ref::Mutability::Mut => Access::Exclusive, | ||
871 | }, | ||
865 | _ => Access::Owned, | 872 | _ => Access::Owned, |
866 | }) | 873 | }) |
867 | .unwrap_or(Access::Owned) | 874 | .unwrap_or(Access::Owned) |
@@ -973,7 +980,7 @@ impl TypeAlias { | |||
973 | } | 980 | } |
974 | 981 | ||
975 | pub fn ty(self, db: &dyn HirDatabase) -> Type { | 982 | pub fn ty(self, db: &dyn HirDatabase) -> Type { |
976 | Type::from_def(db, self.id.lookup(db.upcast()).module(db.upcast()).krate, self.id) | 983 | Type::from_def(db, self.id.lookup(db.upcast()).module(db.upcast()).krate(), self.id) |
977 | } | 984 | } |
978 | 985 | ||
979 | pub fn name(self, db: &dyn HirDatabase) -> Name { | 986 | pub fn name(self, db: &dyn HirDatabase) -> Name { |
@@ -990,6 +997,23 @@ impl HasVisibility for TypeAlias { | |||
990 | } | 997 | } |
991 | 998 | ||
992 | #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] | 999 | #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] |
1000 | pub struct BuiltinType { | ||
1001 | pub(crate) inner: hir_def::builtin_type::BuiltinType, | ||
1002 | } | ||
1003 | |||
1004 | impl BuiltinType { | ||
1005 | pub fn ty(self, db: &dyn HirDatabase, module: Module) -> Type { | ||
1006 | let resolver = module.id.resolver(db.upcast()); | ||
1007 | Type::new_with_resolver(db, &resolver, Ty::builtin(self.inner)) | ||
1008 | .expect("crate not present in resolver") | ||
1009 | } | ||
1010 | |||
1011 | pub fn name(self) -> Name { | ||
1012 | self.inner.as_name() | ||
1013 | } | ||
1014 | } | ||
1015 | |||
1016 | #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] | ||
993 | pub struct MacroDef { | 1017 | pub struct MacroDef { |
994 | pub(crate) id: MacroDefId, | 1018 | pub(crate) id: MacroDefId, |
995 | } | 1019 | } |
@@ -1000,8 +1024,9 @@ impl MacroDef { | |||
1000 | /// early, in `hir_expand`, where modules simply do not exist yet. | 1024 | /// early, in `hir_expand`, where modules simply do not exist yet. |
1001 | pub fn module(self, db: &dyn HirDatabase) -> Option<Module> { | 1025 | pub fn module(self, db: &dyn HirDatabase) -> Option<Module> { |
1002 | let krate = self.id.krate; | 1026 | let krate = self.id.krate; |
1003 | let module_id = db.crate_def_map(krate).root; | 1027 | let def_map = db.crate_def_map(krate); |
1004 | Some(Module::new(Crate { id: krate }, module_id)) | 1028 | let module_id = def_map.root(); |
1029 | Some(Module { id: def_map.module_id(module_id) }) | ||
1005 | } | 1030 | } |
1006 | 1031 | ||
1007 | /// XXX: this parses the file | 1032 | /// XXX: this parses the file |
@@ -1051,6 +1076,16 @@ impl AsAssocItem for TypeAlias { | |||
1051 | as_assoc_item(db, AssocItem::TypeAlias, self.id) | 1076 | as_assoc_item(db, AssocItem::TypeAlias, self.id) |
1052 | } | 1077 | } |
1053 | } | 1078 | } |
1079 | impl AsAssocItem for ModuleDef { | ||
1080 | fn as_assoc_item(self, db: &dyn HirDatabase) -> Option<AssocItem> { | ||
1081 | match self { | ||
1082 | ModuleDef::Function(it) => it.as_assoc_item(db), | ||
1083 | ModuleDef::Const(it) => it.as_assoc_item(db), | ||
1084 | ModuleDef::TypeAlias(it) => it.as_assoc_item(db), | ||
1085 | _ => None, | ||
1086 | } | ||
1087 | } | ||
1088 | } | ||
1054 | fn as_assoc_item<ID, DEF, CTOR, AST>(db: &dyn HirDatabase, ctor: CTOR, id: ID) -> Option<AssocItem> | 1089 | fn as_assoc_item<ID, DEF, CTOR, AST>(db: &dyn HirDatabase, ctor: CTOR, id: ID) -> Option<AssocItem> |
1055 | where | 1090 | where |
1056 | ID: Lookup<Data = AssocItemLoc<AST>>, | 1091 | ID: Lookup<Data = AssocItemLoc<AST>>, |
@@ -1091,6 +1126,13 @@ impl AssocItem { | |||
1091 | AssocContainerId::ContainerId(_) => panic!("invalid AssocItem"), | 1126 | AssocContainerId::ContainerId(_) => panic!("invalid AssocItem"), |
1092 | } | 1127 | } |
1093 | } | 1128 | } |
1129 | |||
1130 | pub fn containing_trait(self, db: &dyn HirDatabase) -> Option<Trait> { | ||
1131 | match self.container(db) { | ||
1132 | AssocItemContainer::Trait(t) => Some(t), | ||
1133 | _ => None, | ||
1134 | } | ||
1135 | } | ||
1094 | } | 1136 | } |
1095 | 1137 | ||
1096 | impl HasVisibility for AssocItem { | 1138 | impl HasVisibility for AssocItem { |
@@ -1213,7 +1255,7 @@ impl Local { | |||
1213 | let def = DefWithBodyId::from(self.parent); | 1255 | let def = DefWithBodyId::from(self.parent); |
1214 | let infer = db.infer(def); | 1256 | let infer = db.infer(def); |
1215 | let ty = infer[self.pat_id].clone(); | 1257 | let ty = infer[self.pat_id].clone(); |
1216 | let krate = def.module(db.upcast()).krate; | 1258 | let krate = def.module(db.upcast()).krate(); |
1217 | Type::new(db, krate, def, ty) | 1259 | Type::new(db, krate, def, ty) |
1218 | } | 1260 | } |
1219 | 1261 | ||
@@ -1301,7 +1343,7 @@ impl TypeParam { | |||
1301 | let environment = TraitEnvironment::lower(db, &resolver); | 1343 | let environment = TraitEnvironment::lower(db, &resolver); |
1302 | let ty = Ty::Placeholder(self.id); | 1344 | let ty = Ty::Placeholder(self.id); |
1303 | Type { | 1345 | Type { |
1304 | krate: self.id.parent.module(db.upcast()).krate, | 1346 | krate: self.id.parent.module(db.upcast()).krate(), |
1305 | ty: InEnvironment { value: ty, environment }, | 1347 | ty: InEnvironment { value: ty, environment }, |
1306 | } | 1348 | } |
1307 | } | 1349 | } |
@@ -1327,7 +1369,7 @@ impl TypeParam { | |||
1327 | let subst = Substs::type_params(db, self.id.parent); | 1369 | let subst = Substs::type_params(db, self.id.parent); |
1328 | let ty = ty.subst(&subst.prefix(local_idx)); | 1370 | let ty = ty.subst(&subst.prefix(local_idx)); |
1329 | Some(Type { | 1371 | Some(Type { |
1330 | krate: self.id.parent.module(db.upcast()).krate, | 1372 | krate: self.id.parent.module(db.upcast()).krate(), |
1331 | ty: InEnvironment { value: ty, environment }, | 1373 | ty: InEnvironment { value: ty, environment }, |
1332 | }) | 1374 | }) |
1333 | } | 1375 | } |
@@ -1340,8 +1382,7 @@ impl HirDisplay for TypeParam { | |||
1340 | let substs = Substs::type_params(f.db, self.id.parent); | 1382 | let substs = Substs::type_params(f.db, self.id.parent); |
1341 | let predicates = bounds.iter().cloned().map(|b| b.subst(&substs)).collect::<Vec<_>>(); | 1383 | let predicates = bounds.iter().cloned().map(|b| b.subst(&substs)).collect::<Vec<_>>(); |
1342 | if !(predicates.is_empty() || f.omit_verbose_types()) { | 1384 | if !(predicates.is_empty() || f.omit_verbose_types()) { |
1343 | write!(f, ": ")?; | 1385 | write_bounds_like_dyn_trait_with_prefix(":", &predicates, f)?; |
1344 | write_bounds_like_dyn_trait(&predicates, f)?; | ||
1345 | } | 1386 | } |
1346 | Ok(()) | 1387 | Ok(()) |
1347 | } | 1388 | } |
@@ -1388,7 +1429,7 @@ impl ConstParam { | |||
1388 | 1429 | ||
1389 | pub fn ty(self, db: &dyn HirDatabase) -> Type { | 1430 | pub fn ty(self, db: &dyn HirDatabase) -> Type { |
1390 | let def = self.id.parent; | 1431 | let def = self.id.parent; |
1391 | let krate = def.module(db.upcast()).krate; | 1432 | let krate = def.module(db.upcast()).krate(); |
1392 | Type::new(db, krate, def, db.const_param_ty(self.id)) | 1433 | Type::new(db, krate, def, db.const_param_ty(self.id)) |
1393 | } | 1434 | } |
1394 | } | 1435 | } |
@@ -1423,7 +1464,7 @@ impl Impl { | |||
1423 | let environment = TraitEnvironment::lower(db, &resolver); | 1464 | let environment = TraitEnvironment::lower(db, &resolver); |
1424 | let ty = Ty::from_hir(&ctx, &impl_data.target_type); | 1465 | let ty = Ty::from_hir(&ctx, &impl_data.target_type); |
1425 | Type { | 1466 | Type { |
1426 | krate: self.id.lookup(db.upcast()).container.module(db.upcast()).krate, | 1467 | krate: self.id.lookup(db.upcast()).container.module(db.upcast()).krate(), |
1427 | ty: InEnvironment { value: ty, environment }, | 1468 | ty: InEnvironment { value: ty, environment }, |
1428 | } | 1469 | } |
1429 | } | 1470 | } |
@@ -1441,7 +1482,7 @@ impl Impl { | |||
1441 | } | 1482 | } |
1442 | 1483 | ||
1443 | pub fn krate(self, db: &dyn HirDatabase) -> Crate { | 1484 | pub fn krate(self, db: &dyn HirDatabase) -> Crate { |
1444 | Crate { id: self.module(db).id.krate } | 1485 | Crate { id: self.module(db).id.krate() } |
1445 | } | 1486 | } |
1446 | 1487 | ||
1447 | pub fn is_builtin_derive(self, db: &dyn HirDatabase) -> Option<InFile<ast::Attr>> { | 1488 | pub fn is_builtin_derive(self, db: &dyn HirDatabase) -> Option<InFile<ast::Attr>> { |
@@ -1509,25 +1550,19 @@ impl Type { | |||
1509 | } | 1550 | } |
1510 | 1551 | ||
1511 | pub fn is_unit(&self) -> bool { | 1552 | pub fn is_unit(&self) -> bool { |
1512 | matches!( | 1553 | matches!(self.ty.value, Ty::Tuple(0, ..)) |
1513 | self.ty.value, | ||
1514 | Ty::Apply(ApplicationTy { ctor: TypeCtor::Tuple { cardinality: 0 }, .. }) | ||
1515 | ) | ||
1516 | } | 1554 | } |
1517 | pub fn is_bool(&self) -> bool { | 1555 | pub fn is_bool(&self) -> bool { |
1518 | matches!(self.ty.value, Ty::Apply(ApplicationTy { ctor: TypeCtor::Bool, .. })) | 1556 | matches!(self.ty.value, Ty::Scalar(Scalar::Bool)) |
1519 | } | 1557 | } |
1520 | 1558 | ||
1521 | pub fn is_mutable_reference(&self) -> bool { | 1559 | pub fn is_mutable_reference(&self) -> bool { |
1522 | matches!( | 1560 | matches!(self.ty.value, Ty::Ref(Mutability::Mut, ..)) |
1523 | self.ty.value, | ||
1524 | Ty::Apply(ApplicationTy { ctor: TypeCtor::Ref(Mutability::Mut), .. }) | ||
1525 | ) | ||
1526 | } | 1561 | } |
1527 | 1562 | ||
1528 | pub fn remove_ref(&self) -> Option<Type> { | 1563 | pub fn remove_ref(&self) -> Option<Type> { |
1529 | if let Ty::Apply(ApplicationTy { ctor: TypeCtor::Ref(_), .. }) = self.ty.value { | 1564 | if let Ty::Ref(.., substs) = &self.ty.value { |
1530 | self.ty.value.substs().map(|substs| self.derived(substs[0].clone())) | 1565 | Some(self.derived(substs[0].clone())) |
1531 | } else { | 1566 | } else { |
1532 | None | 1567 | None |
1533 | } | 1568 | } |
@@ -1616,14 +1651,14 @@ impl Type { | |||
1616 | .build(); | 1651 | .build(); |
1617 | let predicate = ProjectionPredicate { | 1652 | let predicate = ProjectionPredicate { |
1618 | projection_ty: ProjectionTy { associated_ty: alias.id, parameters: subst }, | 1653 | projection_ty: ProjectionTy { associated_ty: alias.id, parameters: subst }, |
1619 | ty: Ty::Bound(BoundVar::new(DebruijnIndex::INNERMOST, 0)), | 1654 | ty: Ty::BoundVar(BoundVar::new(DebruijnIndex::INNERMOST, 0)), |
1620 | }; | 1655 | }; |
1621 | let goal = Canonical { | 1656 | let goal = Canonical { |
1622 | value: InEnvironment::new( | 1657 | value: InEnvironment::new( |
1623 | self.ty.environment.clone(), | 1658 | self.ty.environment.clone(), |
1624 | Obligation::Projection(predicate), | 1659 | Obligation::Projection(predicate), |
1625 | ), | 1660 | ), |
1626 | kinds: Arc::new([TyKind::General]), | 1661 | kinds: Arc::new([TyVariableKind::General]), |
1627 | }; | 1662 | }; |
1628 | 1663 | ||
1629 | match db.trait_solve(self.krate, goal)? { | 1664 | match db.trait_solve(self.krate, goal)? { |
@@ -1647,7 +1682,7 @@ impl Type { | |||
1647 | 1682 | ||
1648 | pub fn as_callable(&self, db: &dyn HirDatabase) -> Option<Callable> { | 1683 | pub fn as_callable(&self, db: &dyn HirDatabase) -> Option<Callable> { |
1649 | let def = match self.ty.value { | 1684 | let def = match self.ty.value { |
1650 | Ty::Apply(ApplicationTy { ctor: TypeCtor::FnDef(def), parameters: _ }) => Some(def), | 1685 | Ty::FnDef(def, _) => Some(def), |
1651 | _ => None, | 1686 | _ => None, |
1652 | }; | 1687 | }; |
1653 | 1688 | ||
@@ -1656,20 +1691,16 @@ impl Type { | |||
1656 | } | 1691 | } |
1657 | 1692 | ||
1658 | pub fn is_closure(&self) -> bool { | 1693 | pub fn is_closure(&self) -> bool { |
1659 | matches!(&self.ty.value, Ty::Apply(ApplicationTy { ctor: TypeCtor::Closure { .. }, .. })) | 1694 | matches!(&self.ty.value, Ty::Closure { .. }) |
1660 | } | 1695 | } |
1661 | 1696 | ||
1662 | pub fn is_fn(&self) -> bool { | 1697 | pub fn is_fn(&self) -> bool { |
1663 | matches!( | 1698 | matches!(&self.ty.value, Ty::FnDef(..) | Ty::Function { .. }) |
1664 | &self.ty.value, | ||
1665 | Ty::Apply(ApplicationTy { ctor: TypeCtor::FnDef(..), .. }) | ||
1666 | | Ty::Apply(ApplicationTy { ctor: TypeCtor::FnPtr { .. }, .. }) | ||
1667 | ) | ||
1668 | } | 1699 | } |
1669 | 1700 | ||
1670 | pub fn is_packed(&self, db: &dyn HirDatabase) -> bool { | 1701 | pub fn is_packed(&self, db: &dyn HirDatabase) -> bool { |
1671 | let adt_id = match self.ty.value { | 1702 | let adt_id = match self.ty.value { |
1672 | Ty::Apply(ApplicationTy { ctor: TypeCtor::Adt(adt_id), .. }) => adt_id, | 1703 | Ty::Adt(adt_id, ..) => adt_id, |
1673 | _ => return false, | 1704 | _ => return false, |
1674 | }; | 1705 | }; |
1675 | 1706 | ||
@@ -1681,7 +1712,7 @@ impl Type { | |||
1681 | } | 1712 | } |
1682 | 1713 | ||
1683 | pub fn is_raw_ptr(&self) -> bool { | 1714 | pub fn is_raw_ptr(&self) -> bool { |
1684 | matches!(&self.ty.value, Ty::Apply(ApplicationTy { ctor: TypeCtor::RawPtr(..), .. })) | 1715 | matches!(&self.ty.value, Ty::Raw(..)) |
1685 | } | 1716 | } |
1686 | 1717 | ||
1687 | pub fn contains_unknown(&self) -> bool { | 1718 | pub fn contains_unknown(&self) -> bool { |
@@ -1690,44 +1721,34 @@ impl Type { | |||
1690 | fn go(ty: &Ty) -> bool { | 1721 | fn go(ty: &Ty) -> bool { |
1691 | match ty { | 1722 | match ty { |
1692 | Ty::Unknown => true, | 1723 | Ty::Unknown => true, |
1693 | Ty::Apply(a_ty) => a_ty.parameters.iter().any(go), | 1724 | _ => ty.substs().map_or(false, |substs| substs.iter().any(go)), |
1694 | _ => false, | ||
1695 | } | 1725 | } |
1696 | } | 1726 | } |
1697 | } | 1727 | } |
1698 | 1728 | ||
1699 | pub fn fields(&self, db: &dyn HirDatabase) -> Vec<(Field, Type)> { | 1729 | pub fn fields(&self, db: &dyn HirDatabase) -> Vec<(Field, Type)> { |
1700 | if let Ty::Apply(a_ty) = &self.ty.value { | 1730 | let (variant_id, substs) = match self.ty.value { |
1701 | let variant_id = match a_ty.ctor { | 1731 | Ty::Adt(AdtId::StructId(s), ref substs) => (s.into(), substs), |
1702 | TypeCtor::Adt(AdtId::StructId(s)) => s.into(), | 1732 | Ty::Adt(AdtId::UnionId(u), ref substs) => (u.into(), substs), |
1703 | TypeCtor::Adt(AdtId::UnionId(u)) => u.into(), | 1733 | _ => return Vec::new(), |
1704 | _ => return Vec::new(), | ||
1705 | }; | ||
1706 | |||
1707 | return db | ||
1708 | .field_types(variant_id) | ||
1709 | .iter() | ||
1710 | .map(|(local_id, ty)| { | ||
1711 | let def = Field { parent: variant_id.into(), id: local_id }; | ||
1712 | let ty = ty.clone().subst(&a_ty.parameters); | ||
1713 | (def, self.derived(ty)) | ||
1714 | }) | ||
1715 | .collect(); | ||
1716 | }; | 1734 | }; |
1717 | Vec::new() | 1735 | |
1736 | db.field_types(variant_id) | ||
1737 | .iter() | ||
1738 | .map(|(local_id, ty)| { | ||
1739 | let def = Field { parent: variant_id.into(), id: local_id }; | ||
1740 | let ty = ty.clone().subst(substs); | ||
1741 | (def, self.derived(ty)) | ||
1742 | }) | ||
1743 | .collect() | ||
1718 | } | 1744 | } |
1719 | 1745 | ||
1720 | pub fn tuple_fields(&self, _db: &dyn HirDatabase) -> Vec<Type> { | 1746 | pub fn tuple_fields(&self, _db: &dyn HirDatabase) -> Vec<Type> { |
1721 | let mut res = Vec::new(); | 1747 | if let Ty::Tuple(_, substs) = &self.ty.value { |
1722 | if let Ty::Apply(a_ty) = &self.ty.value { | 1748 | substs.iter().map(|ty| self.derived(ty.clone())).collect() |
1723 | if let TypeCtor::Tuple { .. } = a_ty.ctor { | 1749 | } else { |
1724 | for ty in a_ty.parameters.iter() { | 1750 | Vec::new() |
1725 | let ty = ty.clone(); | 1751 | } |
1726 | res.push(self.derived(ty)); | ||
1727 | } | ||
1728 | } | ||
1729 | }; | ||
1730 | res | ||
1731 | } | 1752 | } |
1732 | 1753 | ||
1733 | pub fn autoderef<'a>(&'a self, db: &'a dyn HirDatabase) -> impl Iterator<Item = Type> + 'a { | 1754 | pub fn autoderef<'a>(&'a self, db: &'a dyn HirDatabase) -> impl Iterator<Item = Type> + 'a { |
@@ -1763,6 +1784,16 @@ impl Type { | |||
1763 | None | 1784 | None |
1764 | } | 1785 | } |
1765 | 1786 | ||
1787 | pub fn type_parameters(&self) -> impl Iterator<Item = Type> + '_ { | ||
1788 | self.ty | ||
1789 | .value | ||
1790 | .strip_references() | ||
1791 | .substs() | ||
1792 | .into_iter() | ||
1793 | .flat_map(|substs| substs.iter()) | ||
1794 | .map(move |ty| self.derived(ty.clone())) | ||
1795 | } | ||
1796 | |||
1766 | pub fn iterate_method_candidates<T>( | 1797 | pub fn iterate_method_candidates<T>( |
1767 | &self, | 1798 | &self, |
1768 | db: &dyn HirDatabase, | 1799 | db: &dyn HirDatabase, |
@@ -1850,17 +1881,8 @@ impl Type { | |||
1850 | 1881 | ||
1851 | // FIXME: provide required accessors such that it becomes implementable from outside. | 1882 | // FIXME: provide required accessors such that it becomes implementable from outside. |
1852 | pub fn is_equal_for_find_impls(&self, other: &Type) -> bool { | 1883 | pub fn is_equal_for_find_impls(&self, other: &Type) -> bool { |
1853 | match (&self.ty.value, &other.ty.value) { | 1884 | let rref = other.remove_ref(); |
1854 | (Ty::Apply(a_original_ty), Ty::Apply(ApplicationTy { ctor, parameters })) => match ctor | 1885 | self.ty.value.equals_ctor(rref.as_ref().map_or(&other.ty.value, |it| &it.ty.value)) |
1855 | { | ||
1856 | TypeCtor::Ref(..) => match parameters.as_single() { | ||
1857 | Ty::Apply(a_ty) => a_original_ty.ctor == a_ty.ctor, | ||
1858 | _ => false, | ||
1859 | }, | ||
1860 | _ => a_original_ty.ctor == *ctor, | ||
1861 | }, | ||
1862 | _ => false, | ||
1863 | } | ||
1864 | } | 1886 | } |
1865 | 1887 | ||
1866 | fn derived(&self, ty: Ty) -> Type { | 1888 | fn derived(&self, ty: Ty) -> Type { |
@@ -1905,28 +1927,20 @@ impl Type { | |||
1905 | fn walk_type(db: &dyn HirDatabase, type_: &Type, cb: &mut impl FnMut(Type)) { | 1927 | fn walk_type(db: &dyn HirDatabase, type_: &Type, cb: &mut impl FnMut(Type)) { |
1906 | let ty = type_.ty.value.strip_references(); | 1928 | let ty = type_.ty.value.strip_references(); |
1907 | match ty { | 1929 | match ty { |
1908 | Ty::Apply(ApplicationTy { ctor, parameters }) => { | 1930 | Ty::Adt(..) => { |
1909 | match ctor { | 1931 | cb(type_.derived(ty.clone())); |
1910 | TypeCtor::Adt(_) => { | 1932 | } |
1911 | cb(type_.derived(ty.clone())); | 1933 | Ty::AssociatedType(..) => { |
1912 | } | 1934 | if let Some(_) = ty.associated_type_parent_trait(db) { |
1913 | TypeCtor::AssociatedType(_) => { | 1935 | cb(type_.derived(ty.clone())); |
1914 | if let Some(_) = ty.associated_type_parent_trait(db) { | ||
1915 | cb(type_.derived(ty.clone())); | ||
1916 | } | ||
1917 | } | ||
1918 | TypeCtor::OpaqueType(..) => { | ||
1919 | if let Some(bounds) = ty.impl_trait_bounds(db) { | ||
1920 | walk_bounds(db, &type_.derived(ty.clone()), &bounds, cb); | ||
1921 | } | ||
1922 | } | ||
1923 | _ => (), | ||
1924 | } | 1936 | } |
1925 | |||
1926 | // adt params, tuples, etc... | ||
1927 | walk_substs(db, type_, parameters, cb); | ||
1928 | } | 1937 | } |
1929 | Ty::Opaque(opaque_ty) => { | 1938 | Ty::OpaqueType(..) => { |
1939 | if let Some(bounds) = ty.impl_trait_bounds(db) { | ||
1940 | walk_bounds(db, &type_.derived(ty.clone()), &bounds, cb); | ||
1941 | } | ||
1942 | } | ||
1943 | Ty::Alias(AliasTy::Opaque(opaque_ty)) => { | ||
1930 | if let Some(bounds) = ty.impl_trait_bounds(db) { | 1944 | if let Some(bounds) = ty.impl_trait_bounds(db) { |
1931 | walk_bounds(db, &type_.derived(ty.clone()), &bounds, cb); | 1945 | walk_bounds(db, &type_.derived(ty.clone()), &bounds, cb); |
1932 | } | 1946 | } |
@@ -1942,7 +1956,10 @@ impl Type { | |||
1942 | walk_bounds(db, &type_.derived(ty.clone()), bounds.as_ref(), cb); | 1956 | walk_bounds(db, &type_.derived(ty.clone()), bounds.as_ref(), cb); |
1943 | } | 1957 | } |
1944 | 1958 | ||
1945 | _ => (), | 1959 | _ => {} |
1960 | } | ||
1961 | if let Some(substs) = ty.substs() { | ||
1962 | walk_substs(db, type_, &substs, cb); | ||
1946 | } | 1963 | } |
1947 | } | 1964 | } |
1948 | 1965 | ||
@@ -1960,7 +1977,7 @@ impl HirDisplay for Type { | |||
1960 | #[derive(Debug)] | 1977 | #[derive(Debug)] |
1961 | pub struct Callable { | 1978 | pub struct Callable { |
1962 | ty: Type, | 1979 | ty: Type, |
1963 | sig: FnSig, | 1980 | sig: CallableSig, |
1964 | def: Option<CallableDefId>, | 1981 | def: Option<CallableDefId>, |
1965 | pub(crate) is_bound_method: bool, | 1982 | pub(crate) is_bound_method: bool, |
1966 | } | 1983 | } |
@@ -2025,11 +2042,11 @@ impl Callable { | |||
2025 | } | 2042 | } |
2026 | 2043 | ||
2027 | /// For IDE only | 2044 | /// For IDE only |
2028 | #[derive(Debug)] | 2045 | #[derive(Debug, PartialEq, Eq, Hash)] |
2029 | pub enum ScopeDef { | 2046 | pub enum ScopeDef { |
2030 | ModuleDef(ModuleDef), | 2047 | ModuleDef(ModuleDef), |
2031 | MacroDef(MacroDef), | 2048 | MacroDef(MacroDef), |
2032 | GenericParam(TypeParam), | 2049 | GenericParam(GenericParam), |
2033 | ImplSelfType(Impl), | 2050 | ImplSelfType(Impl), |
2034 | AdtSelfType(Adt), | 2051 | AdtSelfType(Adt), |
2035 | Local(Local), | 2052 | Local(Local), |
diff --git a/crates/hir/src/db.rs b/crates/hir/src/db.rs index d5d4cf5b6..d444f4bbb 100644 --- a/crates/hir/src/db.rs +++ b/crates/hir/src/db.rs | |||
@@ -1,13 +1,13 @@ | |||
1 | //! FIXME: write short doc here | 1 | //! FIXME: write short doc here |
2 | 2 | ||
3 | pub use hir_def::db::{ | 3 | pub use hir_def::db::{ |
4 | AttrsQuery, BodyQuery, BodyWithSourceMapQuery, ConstDataQuery, CrateDefMapQueryQuery, | 4 | AttrsQuery, BlockDefMapQuery, BodyQuery, BodyWithSourceMapQuery, ConstDataQuery, |
5 | CrateLangItemsQuery, DefDatabase, DefDatabaseStorage, EnumDataQuery, ExprScopesQuery, | 5 | CrateDefMapQueryQuery, CrateLangItemsQuery, DefDatabase, DefDatabaseStorage, EnumDataQuery, |
6 | FunctionDataQuery, GenericParamsQuery, ImplDataQuery, ImportMapQuery, InternConstQuery, | 6 | ExprScopesQuery, FunctionDataQuery, GenericParamsQuery, ImplDataQuery, ImportMapQuery, |
7 | InternDatabase, InternDatabaseStorage, InternEnumQuery, InternFunctionQuery, InternImplQuery, | 7 | InternConstQuery, InternDatabase, InternDatabaseStorage, InternEnumQuery, InternFunctionQuery, |
8 | InternStaticQuery, InternStructQuery, InternTraitQuery, InternTypeAliasQuery, InternUnionQuery, | 8 | InternImplQuery, InternStaticQuery, InternStructQuery, InternTraitQuery, InternTypeAliasQuery, |
9 | ItemTreeQuery, LangItemQuery, StaticDataQuery, StructDataQuery, TraitDataQuery, | 9 | InternUnionQuery, ItemTreeQuery, LangItemQuery, StaticDataQuery, StructDataQuery, |
10 | TypeAliasDataQuery, UnionDataQuery, | 10 | TraitDataQuery, TypeAliasDataQuery, UnionDataQuery, |
11 | }; | 11 | }; |
12 | pub use hir_expand::db::{ | 12 | pub use hir_expand::db::{ |
13 | AstDatabase, AstDatabaseStorage, AstIdMapQuery, HygieneFrameQuery, InternEagerExpansionQuery, | 13 | AstDatabase, AstDatabaseStorage, AstIdMapQuery, HygieneFrameQuery, InternEagerExpansionQuery, |
diff --git a/crates/hir/src/diagnostics.rs b/crates/hir/src/diagnostics.rs index 447faa04f..b1ebba516 100644 --- a/crates/hir/src/diagnostics.rs +++ b/crates/hir/src/diagnostics.rs | |||
@@ -1,9 +1,11 @@ | |||
1 | //! FIXME: write short doc here | 1 | //! FIXME: write short doc here |
2 | pub use hir_def::diagnostics::{InactiveCode, UnresolvedModule, UnresolvedProcMacro}; | 2 | pub use hir_def::diagnostics::{ |
3 | InactiveCode, UnresolvedMacroCall, UnresolvedModule, UnresolvedProcMacro, | ||
4 | }; | ||
3 | pub use hir_expand::diagnostics::{ | 5 | pub use hir_expand::diagnostics::{ |
4 | Diagnostic, DiagnosticCode, DiagnosticSink, DiagnosticSinkBuilder, | 6 | Diagnostic, DiagnosticCode, DiagnosticSink, DiagnosticSinkBuilder, |
5 | }; | 7 | }; |
6 | pub use hir_ty::diagnostics::{ | 8 | pub use hir_ty::diagnostics::{ |
7 | IncorrectCase, MismatchedArgCount, MissingFields, MissingMatchArms, MissingOkOrSomeInTailExpr, | 9 | IncorrectCase, MismatchedArgCount, MissingFields, MissingMatchArms, MissingOkOrSomeInTailExpr, |
8 | NoSuchField, RemoveThisSemicolon, | 10 | NoSuchField, RemoveThisSemicolon, ReplaceFilterMapNextWithFindMap, |
9 | }; | 11 | }; |
diff --git a/crates/hir/src/from_id.rs b/crates/hir/src/from_id.rs index c8c5fecd7..b5814da11 100644 --- a/crates/hir/src/from_id.rs +++ b/crates/hir/src/from_id.rs | |||
@@ -11,8 +11,9 @@ use hir_def::{ | |||
11 | }; | 11 | }; |
12 | 12 | ||
13 | use crate::{ | 13 | use crate::{ |
14 | code_model::GenericParam, Adt, AssocItem, DefWithBody, Field, GenericDef, Label, Local, | 14 | code_model::{BuiltinType, GenericParam}, |
15 | MacroDef, ModuleDef, Variant, VariantDef, | 15 | Adt, AssocItem, DefWithBody, Field, GenericDef, Label, Local, MacroDef, ModuleDef, Variant, |
16 | VariantDef, | ||
16 | }; | 17 | }; |
17 | 18 | ||
18 | macro_rules! from_id { | 19 | macro_rules! from_id { |
@@ -111,7 +112,7 @@ impl From<ModuleDefId> for ModuleDef { | |||
111 | ModuleDefId::StaticId(it) => ModuleDef::Static(it.into()), | 112 | ModuleDefId::StaticId(it) => ModuleDef::Static(it.into()), |
112 | ModuleDefId::TraitId(it) => ModuleDef::Trait(it.into()), | 113 | ModuleDefId::TraitId(it) => ModuleDef::Trait(it.into()), |
113 | ModuleDefId::TypeAliasId(it) => ModuleDef::TypeAlias(it.into()), | 114 | ModuleDefId::TypeAliasId(it) => ModuleDef::TypeAlias(it.into()), |
114 | ModuleDefId::BuiltinType(it) => ModuleDef::BuiltinType(it), | 115 | ModuleDefId::BuiltinType(it) => ModuleDef::BuiltinType(it.into()), |
115 | } | 116 | } |
116 | } | 117 | } |
117 | } | 118 | } |
@@ -127,7 +128,7 @@ impl From<ModuleDef> for ModuleDefId { | |||
127 | ModuleDef::Static(it) => ModuleDefId::StaticId(it.into()), | 128 | ModuleDef::Static(it) => ModuleDefId::StaticId(it.into()), |
128 | ModuleDef::Trait(it) => ModuleDefId::TraitId(it.into()), | 129 | ModuleDef::Trait(it) => ModuleDefId::TraitId(it.into()), |
129 | ModuleDef::TypeAlias(it) => ModuleDefId::TypeAliasId(it.into()), | 130 | ModuleDef::TypeAlias(it) => ModuleDefId::TypeAliasId(it.into()), |
130 | ModuleDef::BuiltinType(it) => ModuleDefId::BuiltinType(it), | 131 | ModuleDef::BuiltinType(it) => ModuleDefId::BuiltinType(it.into()), |
131 | } | 132 | } |
132 | } | 133 | } |
133 | } | 134 | } |
@@ -274,3 +275,15 @@ impl From<ModuleDef> for ItemInNs { | |||
274 | } | 275 | } |
275 | } | 276 | } |
276 | } | 277 | } |
278 | |||
279 | impl From<hir_def::builtin_type::BuiltinType> for BuiltinType { | ||
280 | fn from(inner: hir_def::builtin_type::BuiltinType) -> Self { | ||
281 | Self { inner } | ||
282 | } | ||
283 | } | ||
284 | |||
285 | impl From<BuiltinType> for hir_def::builtin_type::BuiltinType { | ||
286 | fn from(it: BuiltinType) -> Self { | ||
287 | it.inner | ||
288 | } | ||
289 | } | ||
diff --git a/crates/hir/src/has_source.rs b/crates/hir/src/has_source.rs index 7c57d8378..262002671 100644 --- a/crates/hir/src/has_source.rs +++ b/crates/hir/src/has_source.rs | |||
@@ -24,12 +24,12 @@ pub trait HasSource { | |||
24 | impl Module { | 24 | impl Module { |
25 | /// Returns a node which defines this module. That is, a file or a `mod foo {}` with items. | 25 | /// Returns a node which defines this module. That is, a file or a `mod foo {}` with items. |
26 | pub fn definition_source(self, db: &dyn HirDatabase) -> InFile<ModuleSource> { | 26 | pub fn definition_source(self, db: &dyn HirDatabase) -> InFile<ModuleSource> { |
27 | let def_map = db.crate_def_map(self.id.krate); | 27 | let def_map = self.id.def_map(db.upcast()); |
28 | def_map[self.id.local_id].definition_source(db.upcast()) | 28 | def_map[self.id.local_id].definition_source(db.upcast()) |
29 | } | 29 | } |
30 | 30 | ||
31 | pub fn is_mod_rs(self, db: &dyn HirDatabase) -> bool { | 31 | pub fn is_mod_rs(self, db: &dyn HirDatabase) -> bool { |
32 | let def_map = db.crate_def_map(self.id.krate); | 32 | let def_map = self.id.def_map(db.upcast()); |
33 | match def_map[self.id.local_id].origin { | 33 | match def_map[self.id.local_id].origin { |
34 | ModuleOrigin::File { is_mod_rs, .. } => is_mod_rs, | 34 | ModuleOrigin::File { is_mod_rs, .. } => is_mod_rs, |
35 | _ => false, | 35 | _ => false, |
@@ -39,7 +39,7 @@ impl Module { | |||
39 | /// Returns a node which declares this module, either a `mod foo;` or a `mod foo {}`. | 39 | /// Returns a node which declares this module, either a `mod foo;` or a `mod foo {}`. |
40 | /// `None` for the crate root. | 40 | /// `None` for the crate root. |
41 | pub fn declaration_source(self, db: &dyn HirDatabase) -> Option<InFile<ast::Module>> { | 41 | pub fn declaration_source(self, db: &dyn HirDatabase) -> Option<InFile<ast::Module>> { |
42 | let def_map = db.crate_def_map(self.id.krate); | 42 | let def_map = self.id.def_map(db.upcast()); |
43 | def_map[self.id.local_id].declaration_source(db.upcast()) | 43 | def_map[self.id.local_id].declaration_source(db.upcast()) |
44 | } | 44 | } |
45 | } | 45 | } |
diff --git a/crates/hir/src/semantics.rs b/crates/hir/src/semantics.rs index ab213e04c..144851f83 100644 --- a/crates/hir/src/semantics.rs +++ b/crates/hir/src/semantics.rs | |||
@@ -16,13 +16,12 @@ use rustc_hash::{FxHashMap, FxHashSet}; | |||
16 | use syntax::{ | 16 | use syntax::{ |
17 | algo::find_node_at_offset, | 17 | algo::find_node_at_offset, |
18 | ast::{self, GenericParamsOwner, LoopBodyOwner}, | 18 | ast::{self, GenericParamsOwner, LoopBodyOwner}, |
19 | match_ast, AstNode, SyntaxNode, SyntaxToken, TextSize, | 19 | match_ast, AstNode, SyntaxNode, SyntaxNodePtr, SyntaxToken, TextSize, |
20 | }; | 20 | }; |
21 | 21 | ||
22 | use crate::{ | 22 | use crate::{ |
23 | code_model::Access, | 23 | code_model::Access, |
24 | db::HirDatabase, | 24 | db::HirDatabase, |
25 | diagnostics::Diagnostic, | ||
26 | semantics::source_to_def::{ChildContainer, SourceToDefCache, SourceToDefCtx}, | 25 | semantics::source_to_def::{ChildContainer, SourceToDefCache, SourceToDefCtx}, |
27 | source_analyzer::{resolve_hir_path, SourceAnalyzer}, | 26 | source_analyzer::{resolve_hir_path, SourceAnalyzer}, |
28 | AssocItem, Callable, ConstParam, Crate, Field, Function, HirFileId, Impl, InFile, Label, | 27 | AssocItem, Callable, ConstParam, Crate, Field, Function, HirFileId, Impl, InFile, Label, |
@@ -49,7 +48,7 @@ impl PathResolution { | |||
49 | match self { | 48 | match self { |
50 | PathResolution::Def(ModuleDef::Adt(adt)) => Some(TypeNs::AdtId((*adt).into())), | 49 | PathResolution::Def(ModuleDef::Adt(adt)) => Some(TypeNs::AdtId((*adt).into())), |
51 | PathResolution::Def(ModuleDef::BuiltinType(builtin)) => { | 50 | PathResolution::Def(ModuleDef::BuiltinType(builtin)) => { |
52 | Some(TypeNs::BuiltinType(*builtin)) | 51 | Some(TypeNs::BuiltinType((*builtin).into())) |
53 | } | 52 | } |
54 | PathResolution::Def(ModuleDef::Const(_)) | 53 | PathResolution::Def(ModuleDef::Const(_)) |
55 | | PathResolution::Def(ModuleDef::Variant(_)) | 54 | | PathResolution::Def(ModuleDef::Variant(_)) |
@@ -141,7 +140,7 @@ impl<'db, DB: HirDatabase> Semantics<'db, DB> { | |||
141 | self.imp.original_range(node) | 140 | self.imp.original_range(node) |
142 | } | 141 | } |
143 | 142 | ||
144 | pub fn diagnostics_display_range(&self, diagnostics: &dyn Diagnostic) -> FileRange { | 143 | pub fn diagnostics_display_range(&self, diagnostics: InFile<SyntaxNodePtr>) -> FileRange { |
145 | self.imp.diagnostics_display_range(diagnostics) | 144 | self.imp.diagnostics_display_range(diagnostics) |
146 | } | 145 | } |
147 | 146 | ||
@@ -385,8 +384,7 @@ impl<'db> SemanticsImpl<'db> { | |||
385 | node.as_ref().original_file_range(self.db.upcast()) | 384 | node.as_ref().original_file_range(self.db.upcast()) |
386 | } | 385 | } |
387 | 386 | ||
388 | fn diagnostics_display_range(&self, diagnostics: &dyn Diagnostic) -> FileRange { | 387 | fn diagnostics_display_range(&self, src: InFile<SyntaxNodePtr>) -> FileRange { |
389 | let src = diagnostics.display_source(); | ||
390 | let root = self.db.parse_or_expand(src.file_id).unwrap(); | 388 | let root = self.db.parse_or_expand(src.file_id).unwrap(); |
391 | let node = src.value.to_node(&root); | 389 | let node = src.value.to_node(&root); |
392 | self.cache(root, src.file_id); | 390 | self.cache(root, src.file_id); |
@@ -814,7 +812,7 @@ impl<'a> SemanticsScope<'a> { | |||
814 | } | 812 | } |
815 | resolver::ScopeDef::ImplSelfType(it) => ScopeDef::ImplSelfType(it.into()), | 813 | resolver::ScopeDef::ImplSelfType(it) => ScopeDef::ImplSelfType(it.into()), |
816 | resolver::ScopeDef::AdtSelfType(it) => ScopeDef::AdtSelfType(it.into()), | 814 | resolver::ScopeDef::AdtSelfType(it) => ScopeDef::AdtSelfType(it.into()), |
817 | resolver::ScopeDef::GenericParam(id) => ScopeDef::GenericParam(TypeParam { id }), | 815 | resolver::ScopeDef::GenericParam(id) => ScopeDef::GenericParam(id.into()), |
818 | resolver::ScopeDef::Local(pat_id) => { | 816 | resolver::ScopeDef::Local(pat_id) => { |
819 | let parent = resolver.body_owner().unwrap().into(); | 817 | let parent = resolver.body_owner().unwrap().into(); |
820 | ScopeDef::Local(Local { parent, pat_id }) | 818 | ScopeDef::Local(Local { parent, pat_id }) |
diff --git a/crates/hir/src/semantics/source_to_def.rs b/crates/hir/src/semantics/source_to_def.rs index 9bf60c72a..6c612ee86 100644 --- a/crates/hir/src/semantics/source_to_def.rs +++ b/crates/hir/src/semantics/source_to_def.rs | |||
@@ -30,12 +30,12 @@ pub(super) struct SourceToDefCtx<'a, 'b> { | |||
30 | impl SourceToDefCtx<'_, '_> { | 30 | impl SourceToDefCtx<'_, '_> { |
31 | pub(super) fn file_to_def(&mut self, file: FileId) -> Option<ModuleId> { | 31 | pub(super) fn file_to_def(&mut self, file: FileId) -> Option<ModuleId> { |
32 | let _p = profile::span("SourceBinder::to_module_def"); | 32 | let _p = profile::span("SourceBinder::to_module_def"); |
33 | let (krate, local_id) = self.db.relevant_crates(file).iter().find_map(|&crate_id| { | 33 | self.db.relevant_crates(file).iter().find_map(|&crate_id| { |
34 | // FIXME: inner items | ||
34 | let crate_def_map = self.db.crate_def_map(crate_id); | 35 | let crate_def_map = self.db.crate_def_map(crate_id); |
35 | let local_id = crate_def_map.modules_for_file(file).next()?; | 36 | let local_id = crate_def_map.modules_for_file(file).next()?; |
36 | Some((crate_id, local_id)) | 37 | Some(crate_def_map.module_id(local_id)) |
37 | })?; | 38 | }) |
38 | Some(ModuleId { krate, local_id }) | ||
39 | } | 39 | } |
40 | 40 | ||
41 | pub(super) fn module_to_def(&mut self, src: InFile<ast::Module>) -> Option<ModuleId> { | 41 | pub(super) fn module_to_def(&mut self, src: InFile<ast::Module>) -> Option<ModuleId> { |
@@ -60,9 +60,9 @@ impl SourceToDefCtx<'_, '_> { | |||
60 | }?; | 60 | }?; |
61 | 61 | ||
62 | let child_name = src.value.name()?.as_name(); | 62 | let child_name = src.value.name()?.as_name(); |
63 | let def_map = self.db.crate_def_map(parent_module.krate); | 63 | let def_map = parent_module.def_map(self.db.upcast()); |
64 | let child_id = *def_map[parent_module.local_id].children.get(&child_name)?; | 64 | let child_id = *def_map[parent_module.local_id].children.get(&child_name)?; |
65 | Some(ModuleId { krate: parent_module.krate, local_id: child_id }) | 65 | Some(def_map.module_id(child_id)) |
66 | } | 66 | } |
67 | 67 | ||
68 | pub(super) fn trait_to_def(&mut self, src: InFile<ast::Trait>) -> Option<TraitId> { | 68 | pub(super) fn trait_to_def(&mut self, src: InFile<ast::Trait>) -> Option<TraitId> { |
@@ -185,7 +185,7 @@ impl SourceToDefCtx<'_, '_> { | |||
185 | ) -> Option<MacroDefId> { | 185 | ) -> Option<MacroDefId> { |
186 | let kind = MacroDefKind::Declarative; | 186 | let kind = MacroDefKind::Declarative; |
187 | let file_id = src.file_id.original_file(self.db.upcast()); | 187 | let file_id = src.file_id.original_file(self.db.upcast()); |
188 | let krate = self.file_to_def(file_id)?.krate; | 188 | let krate = self.file_to_def(file_id)?.krate(); |
189 | let file_ast_id = self.db.ast_id_map(src.file_id).ast_id(&src.value); | 189 | let file_ast_id = self.db.ast_id_map(src.file_id).ast_id(&src.value); |
190 | let ast_id = Some(AstId::new(src.file_id, file_ast_id.upcast())); | 190 | let ast_id = Some(AstId::new(src.file_id, file_ast_id.upcast())); |
191 | Some(MacroDefId { krate, ast_id, kind, local_inner: false }) | 191 | Some(MacroDefId { krate, ast_id, kind, local_inner: false }) |
diff --git a/crates/hir/src/source_analyzer.rs b/crates/hir/src/source_analyzer.rs index 30a8e513d..64ce4add1 100644 --- a/crates/hir/src/source_analyzer.rs +++ b/crates/hir/src/source_analyzer.rs | |||
@@ -20,7 +20,7 @@ use hir_def::{ | |||
20 | use hir_expand::{hygiene::Hygiene, name::AsName, HirFileId, InFile}; | 20 | use hir_expand::{hygiene::Hygiene, name::AsName, HirFileId, InFile}; |
21 | use hir_ty::{ | 21 | use hir_ty::{ |
22 | diagnostics::{record_literal_missing_fields, record_pattern_missing_fields}, | 22 | diagnostics::{record_literal_missing_fields, record_pattern_missing_fields}, |
23 | InferenceResult, Substs, Ty, | 23 | InferenceResult, Substs, |
24 | }; | 24 | }; |
25 | use syntax::{ | 25 | use syntax::{ |
26 | ast::{self, AstNode}, | 26 | ast::{self, AstNode}, |
@@ -28,8 +28,9 @@ use syntax::{ | |||
28 | }; | 28 | }; |
29 | 29 | ||
30 | use crate::{ | 30 | use crate::{ |
31 | db::HirDatabase, semantics::PathResolution, Adt, Const, Field, Function, Local, MacroDef, | 31 | code_model::BuiltinType, db::HirDatabase, semantics::PathResolution, Adt, Const, Field, |
32 | ModuleDef, Static, Struct, Trait, Type, TypeAlias, TypeParam, Variant, | 32 | Function, Local, MacroDef, ModuleDef, Static, Struct, Trait, Type, TypeAlias, TypeParam, |
33 | Variant, | ||
33 | }; | 34 | }; |
34 | use base_db::CrateId; | 35 | use base_db::CrateId; |
35 | 36 | ||
@@ -222,19 +223,23 @@ impl SourceAnalyzer { | |||
222 | db: &dyn HirDatabase, | 223 | db: &dyn HirDatabase, |
223 | path: &ast::Path, | 224 | path: &ast::Path, |
224 | ) -> Option<PathResolution> { | 225 | ) -> Option<PathResolution> { |
225 | if let Some(path_expr) = path.syntax().parent().and_then(ast::PathExpr::cast) { | 226 | let parent = || path.syntax().parent(); |
227 | let mut prefer_value_ns = false; | ||
228 | if let Some(path_expr) = parent().and_then(ast::PathExpr::cast) { | ||
226 | let expr_id = self.expr_id(db, &path_expr.into())?; | 229 | let expr_id = self.expr_id(db, &path_expr.into())?; |
227 | if let Some(assoc) = self.infer.as_ref()?.assoc_resolutions_for_expr(expr_id) { | 230 | let infer = self.infer.as_ref()?; |
231 | if let Some(assoc) = infer.assoc_resolutions_for_expr(expr_id) { | ||
228 | return Some(PathResolution::AssocItem(assoc.into())); | 232 | return Some(PathResolution::AssocItem(assoc.into())); |
229 | } | 233 | } |
230 | if let Some(VariantId::EnumVariantId(variant)) = | 234 | if let Some(VariantId::EnumVariantId(variant)) = |
231 | self.infer.as_ref()?.variant_resolution_for_expr(expr_id) | 235 | infer.variant_resolution_for_expr(expr_id) |
232 | { | 236 | { |
233 | return Some(PathResolution::Def(ModuleDef::Variant(variant.into()))); | 237 | return Some(PathResolution::Def(ModuleDef::Variant(variant.into()))); |
234 | } | 238 | } |
239 | prefer_value_ns = true; | ||
235 | } | 240 | } |
236 | 241 | ||
237 | if let Some(path_pat) = path.syntax().parent().and_then(ast::PathPat::cast) { | 242 | if let Some(path_pat) = parent().and_then(ast::PathPat::cast) { |
238 | let pat_id = self.pat_id(&path_pat.into())?; | 243 | let pat_id = self.pat_id(&path_pat.into())?; |
239 | if let Some(assoc) = self.infer.as_ref()?.assoc_resolutions_for_pat(pat_id) { | 244 | if let Some(assoc) = self.infer.as_ref()?.assoc_resolutions_for_pat(pat_id) { |
240 | return Some(PathResolution::AssocItem(assoc.into())); | 245 | return Some(PathResolution::AssocItem(assoc.into())); |
@@ -246,7 +251,7 @@ impl SourceAnalyzer { | |||
246 | } | 251 | } |
247 | } | 252 | } |
248 | 253 | ||
249 | if let Some(rec_lit) = path.syntax().parent().and_then(ast::RecordExpr::cast) { | 254 | if let Some(rec_lit) = parent().and_then(ast::RecordExpr::cast) { |
250 | let expr_id = self.expr_id(db, &rec_lit.into())?; | 255 | let expr_id = self.expr_id(db, &rec_lit.into())?; |
251 | if let Some(VariantId::EnumVariantId(variant)) = | 256 | if let Some(VariantId::EnumVariantId(variant)) = |
252 | self.infer.as_ref()?.variant_resolution_for_expr(expr_id) | 257 | self.infer.as_ref()?.variant_resolution_for_expr(expr_id) |
@@ -255,8 +260,12 @@ impl SourceAnalyzer { | |||
255 | } | 260 | } |
256 | } | 261 | } |
257 | 262 | ||
258 | if let Some(rec_pat) = path.syntax().parent().and_then(ast::RecordPat::cast) { | 263 | if let Some(pat) = parent() |
259 | let pat_id = self.pat_id(&rec_pat.into())?; | 264 | .and_then(ast::RecordPat::cast) |
265 | .map(ast::Pat::from) | ||
266 | .or_else(|| parent().and_then(ast::TupleStructPat::cast).map(ast::Pat::from)) | ||
267 | { | ||
268 | let pat_id = self.pat_id(&pat)?; | ||
260 | if let Some(VariantId::EnumVariantId(variant)) = | 269 | if let Some(VariantId::EnumVariantId(variant)) = |
261 | self.infer.as_ref()?.variant_resolution_for_pat(pat_id) | 270 | self.infer.as_ref()?.variant_resolution_for_pat(pat_id) |
262 | { | 271 | { |
@@ -269,7 +278,7 @@ impl SourceAnalyzer { | |||
269 | 278 | ||
270 | // Case where path is a qualifier of another path, e.g. foo::bar::Baz where we | 279 | // Case where path is a qualifier of another path, e.g. foo::bar::Baz where we |
271 | // trying to resolve foo::bar. | 280 | // trying to resolve foo::bar. |
272 | if let Some(outer_path) = path.syntax().parent().and_then(ast::Path::cast) { | 281 | if let Some(outer_path) = parent().and_then(ast::Path::cast) { |
273 | if let Some(qualifier) = outer_path.qualifier() { | 282 | if let Some(qualifier) = outer_path.qualifier() { |
274 | if path == &qualifier { | 283 | if path == &qualifier { |
275 | return resolve_hir_path_qualifier(db, &self.resolver, &hir_path); | 284 | return resolve_hir_path_qualifier(db, &self.resolver, &hir_path); |
@@ -277,7 +286,7 @@ impl SourceAnalyzer { | |||
277 | } | 286 | } |
278 | } | 287 | } |
279 | 288 | ||
280 | resolve_hir_path(db, &self.resolver, &hir_path) | 289 | resolve_hir_path_(db, &self.resolver, &hir_path, prefer_value_ns) |
281 | } | 290 | } |
282 | 291 | ||
283 | pub(crate) fn record_literal_missing_fields( | 292 | pub(crate) fn record_literal_missing_fields( |
@@ -290,14 +299,11 @@ impl SourceAnalyzer { | |||
290 | let infer = self.infer.as_ref()?; | 299 | let infer = self.infer.as_ref()?; |
291 | 300 | ||
292 | let expr_id = self.expr_id(db, &literal.clone().into())?; | 301 | let expr_id = self.expr_id(db, &literal.clone().into())?; |
293 | let substs = match &infer.type_of_expr[expr_id] { | 302 | let substs = infer.type_of_expr[expr_id].substs()?; |
294 | Ty::Apply(a_ty) => &a_ty.parameters, | ||
295 | _ => return None, | ||
296 | }; | ||
297 | 303 | ||
298 | let (variant, missing_fields, _exhaustive) = | 304 | let (variant, missing_fields, _exhaustive) = |
299 | record_literal_missing_fields(db, infer, expr_id, &body[expr_id])?; | 305 | record_literal_missing_fields(db, infer, expr_id, &body[expr_id])?; |
300 | let res = self.missing_fields(db, krate, substs, variant, missing_fields); | 306 | let res = self.missing_fields(db, krate, &substs, variant, missing_fields); |
301 | Some(res) | 307 | Some(res) |
302 | } | 308 | } |
303 | 309 | ||
@@ -311,14 +317,11 @@ impl SourceAnalyzer { | |||
311 | let infer = self.infer.as_ref()?; | 317 | let infer = self.infer.as_ref()?; |
312 | 318 | ||
313 | let pat_id = self.pat_id(&pattern.clone().into())?; | 319 | let pat_id = self.pat_id(&pattern.clone().into())?; |
314 | let substs = match &infer.type_of_pat[pat_id] { | 320 | let substs = infer.type_of_pat[pat_id].substs()?; |
315 | Ty::Apply(a_ty) => &a_ty.parameters, | ||
316 | _ => return None, | ||
317 | }; | ||
318 | 321 | ||
319 | let (variant, missing_fields, _exhaustive) = | 322 | let (variant, missing_fields, _exhaustive) = |
320 | record_pattern_missing_fields(db, infer, pat_id, &body[pat_id])?; | 323 | record_pattern_missing_fields(db, infer, pat_id, &body[pat_id])?; |
321 | let res = self.missing_fields(db, krate, substs, variant, missing_fields); | 324 | let res = self.missing_fields(db, krate, &substs, variant, missing_fields); |
322 | Some(res) | 325 | Some(res) |
323 | } | 326 | } |
324 | 327 | ||
@@ -447,12 +450,22 @@ fn adjust( | |||
447 | .map(|(_ptr, scope)| *scope) | 450 | .map(|(_ptr, scope)| *scope) |
448 | } | 451 | } |
449 | 452 | ||
453 | #[inline] | ||
450 | pub(crate) fn resolve_hir_path( | 454 | pub(crate) fn resolve_hir_path( |
451 | db: &dyn HirDatabase, | 455 | db: &dyn HirDatabase, |
452 | resolver: &Resolver, | 456 | resolver: &Resolver, |
453 | path: &Path, | 457 | path: &Path, |
454 | ) -> Option<PathResolution> { | 458 | ) -> Option<PathResolution> { |
455 | let types = | 459 | resolve_hir_path_(db, resolver, path, false) |
460 | } | ||
461 | |||
462 | fn resolve_hir_path_( | ||
463 | db: &dyn HirDatabase, | ||
464 | resolver: &Resolver, | ||
465 | path: &Path, | ||
466 | prefer_value_ns: bool, | ||
467 | ) -> Option<PathResolution> { | ||
468 | let types = || { | ||
456 | resolver.resolve_path_in_type_ns_fully(db.upcast(), path.mod_path()).map(|ty| match ty { | 469 | resolver.resolve_path_in_type_ns_fully(db.upcast(), path.mod_path()).map(|ty| match ty { |
457 | TypeNs::SelfType(it) => PathResolution::SelfType(it.into()), | 470 | TypeNs::SelfType(it) => PathResolution::SelfType(it.into()), |
458 | TypeNs::GenericParam(id) => PathResolution::TypeParam(TypeParam { id }), | 471 | TypeNs::GenericParam(id) => PathResolution::TypeParam(TypeParam { id }), |
@@ -461,12 +474,13 @@ pub(crate) fn resolve_hir_path( | |||
461 | } | 474 | } |
462 | TypeNs::EnumVariantId(it) => PathResolution::Def(Variant::from(it).into()), | 475 | TypeNs::EnumVariantId(it) => PathResolution::Def(Variant::from(it).into()), |
463 | TypeNs::TypeAliasId(it) => PathResolution::Def(TypeAlias::from(it).into()), | 476 | TypeNs::TypeAliasId(it) => PathResolution::Def(TypeAlias::from(it).into()), |
464 | TypeNs::BuiltinType(it) => PathResolution::Def(it.into()), | 477 | TypeNs::BuiltinType(it) => PathResolution::Def(BuiltinType::from(it).into()), |
465 | TypeNs::TraitId(it) => PathResolution::Def(Trait::from(it).into()), | 478 | TypeNs::TraitId(it) => PathResolution::Def(Trait::from(it).into()), |
466 | }); | 479 | }) |
480 | }; | ||
467 | 481 | ||
468 | let body_owner = resolver.body_owner(); | 482 | let body_owner = resolver.body_owner(); |
469 | let values = | 483 | let values = || { |
470 | resolver.resolve_path_in_value_ns_fully(db.upcast(), path.mod_path()).and_then(|val| { | 484 | resolver.resolve_path_in_value_ns_fully(db.upcast(), path.mod_path()).and_then(|val| { |
471 | let res = match val { | 485 | let res = match val { |
472 | ValueNs::LocalBinding(pat_id) => { | 486 | ValueNs::LocalBinding(pat_id) => { |
@@ -482,18 +496,25 @@ pub(crate) fn resolve_hir_path( | |||
482 | ValueNs::GenericParam(it) => PathResolution::ConstParam(it.into()), | 496 | ValueNs::GenericParam(it) => PathResolution::ConstParam(it.into()), |
483 | }; | 497 | }; |
484 | Some(res) | 498 | Some(res) |
485 | }); | 499 | }) |
500 | }; | ||
486 | 501 | ||
487 | let items = resolver | 502 | let items = || { |
488 | .resolve_module_path_in_items(db.upcast(), path.mod_path()) | 503 | resolver |
489 | .take_types() | 504 | .resolve_module_path_in_items(db.upcast(), path.mod_path()) |
490 | .map(|it| PathResolution::Def(it.into())); | 505 | .take_types() |
506 | .map(|it| PathResolution::Def(it.into())) | ||
507 | }; | ||
491 | 508 | ||
492 | types.or(values).or(items).or_else(|| { | 509 | let macros = || { |
493 | resolver | 510 | resolver |
494 | .resolve_path_as_macro(db.upcast(), path.mod_path()) | 511 | .resolve_path_as_macro(db.upcast(), path.mod_path()) |
495 | .map(|def| PathResolution::Macro(def.into())) | 512 | .map(|def| PathResolution::Macro(def.into())) |
496 | }) | 513 | }; |
514 | |||
515 | if prefer_value_ns { values().or_else(types) } else { types().or_else(values) } | ||
516 | .or_else(items) | ||
517 | .or_else(macros) | ||
497 | } | 518 | } |
498 | 519 | ||
499 | /// Resolves a path where we know it is a qualifier of another path. | 520 | /// Resolves a path where we know it is a qualifier of another path. |
@@ -529,7 +550,7 @@ fn resolve_hir_path_qualifier( | |||
529 | TypeNs::AdtSelfType(it) | TypeNs::AdtId(it) => PathResolution::Def(Adt::from(it).into()), | 550 | TypeNs::AdtSelfType(it) | TypeNs::AdtId(it) => PathResolution::Def(Adt::from(it).into()), |
530 | TypeNs::EnumVariantId(it) => PathResolution::Def(Variant::from(it).into()), | 551 | TypeNs::EnumVariantId(it) => PathResolution::Def(Variant::from(it).into()), |
531 | TypeNs::TypeAliasId(it) => PathResolution::Def(TypeAlias::from(it).into()), | 552 | TypeNs::TypeAliasId(it) => PathResolution::Def(TypeAlias::from(it).into()), |
532 | TypeNs::BuiltinType(it) => PathResolution::Def(it.into()), | 553 | TypeNs::BuiltinType(it) => PathResolution::Def(BuiltinType::from(it).into()), |
533 | TypeNs::TraitId(it) => PathResolution::Def(Trait::from(it).into()), | 554 | TypeNs::TraitId(it) => PathResolution::Def(Trait::from(it).into()), |
534 | }) | 555 | }) |
535 | } | 556 | } |