diff options
Diffstat (limited to 'crates/ra_hir')
-rw-r--r-- | crates/ra_hir/src/expr/validation.rs | 11 | ||||
-rw-r--r-- | crates/ra_hir/src/resolve.rs | 38 | ||||
-rw-r--r-- | crates/ra_hir/src/source_binder.rs | 11 | ||||
-rw-r--r-- | crates/ra_hir/src/ty/infer.rs | 46 | ||||
-rw-r--r-- | crates/ra_hir/src/ty/lower.rs | 2 |
5 files changed, 59 insertions, 49 deletions
diff --git a/crates/ra_hir/src/expr/validation.rs b/crates/ra_hir/src/expr/validation.rs index 6a22e1318..c985dbdad 100644 --- a/crates/ra_hir/src/expr/validation.rs +++ b/crates/ra_hir/src/expr/validation.rs | |||
@@ -11,7 +11,7 @@ use crate::{ | |||
11 | name, | 11 | name, |
12 | path::{PathKind, PathSegment}, | 12 | path::{PathKind, PathSegment}, |
13 | ty::{ApplicationTy, InferenceResult, Ty, TypeCtor}, | 13 | ty::{ApplicationTy, InferenceResult, Ty, TypeCtor}, |
14 | Function, ModuleDef, Name, Path, PerNs, Resolution, | 14 | Function, Name, Path, |
15 | }; | 15 | }; |
16 | 16 | ||
17 | use super::{Expr, ExprId, RecordLitField}; | 17 | use super::{Expr, ExprId, RecordLitField}; |
@@ -119,11 +119,10 @@ impl<'a, 'b> ExprValidator<'a, 'b> { | |||
119 | }; | 119 | }; |
120 | 120 | ||
121 | let resolver = self.func.resolver(db); | 121 | let resolver = self.func.resolver(db); |
122 | let std_result_enum = | 122 | let std_result_enum = match resolver.resolve_known_enum(db, &std_result_path) { |
123 | match resolver.resolve_path_segments(db, &std_result_path).into_fully_resolved() { | 123 | Some(it) => it, |
124 | PerNs { types: Some(Resolution::Def(ModuleDef::Enum(e))), .. } => e, | 124 | _ => return, |
125 | _ => return, | 125 | }; |
126 | }; | ||
127 | 126 | ||
128 | let std_result_ctor = TypeCtor::Adt(AdtDef::Enum(std_result_enum)); | 127 | let std_result_ctor = TypeCtor::Adt(AdtDef::Enum(std_result_enum)); |
129 | let params = match &mismatch.expected { | 128 | let params = match &mismatch.expected { |
diff --git a/crates/ra_hir/src/resolve.rs b/crates/ra_hir/src/resolve.rs index d9bdd0e22..1ed150f5a 100644 --- a/crates/ra_hir/src/resolve.rs +++ b/crates/ra_hir/src/resolve.rs | |||
@@ -15,7 +15,7 @@ use crate::{ | |||
15 | name::{Name, SELF_PARAM, SELF_TYPE}, | 15 | name::{Name, SELF_PARAM, SELF_TYPE}, |
16 | nameres::{CrateDefMap, CrateModuleId, PerNs}, | 16 | nameres::{CrateDefMap, CrateModuleId, PerNs}, |
17 | path::Path, | 17 | path::Path, |
18 | MacroDef, ModuleDef, Trait, | 18 | Enum, MacroDef, ModuleDef, Struct, Trait, |
19 | }; | 19 | }; |
20 | 20 | ||
21 | #[derive(Debug, Clone, Default)] | 21 | #[derive(Debug, Clone, Default)] |
@@ -39,6 +39,8 @@ pub(crate) struct ExprScope { | |||
39 | #[derive(Debug, Clone)] | 39 | #[derive(Debug, Clone)] |
40 | pub(crate) struct PathResult { | 40 | pub(crate) struct PathResult { |
41 | /// The actual path resolution | 41 | /// The actual path resolution |
42 | // FIXME: `PerNs<Resolution>` type doesn't make sense, as not every | ||
43 | // Resolution variant can appear in every namespace | ||
42 | resolution: PerNs<Resolution>, | 44 | resolution: PerNs<Resolution>, |
43 | /// The first index in the path that we | 45 | /// The first index in the path that we |
44 | /// were unable to resolve. | 46 | /// were unable to resolve. |
@@ -113,6 +115,9 @@ pub(crate) enum Scope { | |||
113 | pub enum Resolution { | 115 | pub enum Resolution { |
114 | /// An item | 116 | /// An item |
115 | Def(ModuleDef), | 117 | Def(ModuleDef), |
118 | |||
119 | // FIXME: there's no way we can syntactically confuse a local with generic | ||
120 | // param, so these two should not be members of the single enum | ||
116 | /// A local binding (only value namespace) | 121 | /// A local binding (only value namespace) |
117 | LocalBinding(PatId), | 122 | LocalBinding(PatId), |
118 | /// A generic parameter | 123 | /// A generic parameter |
@@ -121,6 +126,37 @@ pub enum Resolution { | |||
121 | } | 126 | } |
122 | 127 | ||
123 | impl Resolver { | 128 | impl Resolver { |
129 | /// Resolve known trait from std, like `std::futures::Future` | ||
130 | pub(crate) fn resolve_known_trait(&self, db: &impl HirDatabase, path: &Path) -> Option<Trait> { | ||
131 | let res = self.resolve_path_segments(db, path).into_fully_resolved().take_types()?; | ||
132 | match res { | ||
133 | Resolution::Def(ModuleDef::Trait(it)) => Some(it), | ||
134 | _ => None, | ||
135 | } | ||
136 | } | ||
137 | |||
138 | /// Resolve known struct from std, like `std::boxed::Box` | ||
139 | pub(crate) fn resolve_known_struct( | ||
140 | &self, | ||
141 | db: &impl HirDatabase, | ||
142 | path: &Path, | ||
143 | ) -> Option<Struct> { | ||
144 | let res = self.resolve_path_segments(db, path).into_fully_resolved().take_types()?; | ||
145 | match res { | ||
146 | Resolution::Def(ModuleDef::Struct(it)) => Some(it), | ||
147 | _ => None, | ||
148 | } | ||
149 | } | ||
150 | |||
151 | /// Resolve known enum from std, like `std::result::Result` | ||
152 | pub(crate) fn resolve_known_enum(&self, db: &impl HirDatabase, path: &Path) -> Option<Enum> { | ||
153 | let res = self.resolve_path_segments(db, path).into_fully_resolved().take_types()?; | ||
154 | match res { | ||
155 | Resolution::Def(ModuleDef::Enum(it)) => Some(it), | ||
156 | _ => None, | ||
157 | } | ||
158 | } | ||
159 | |||
124 | pub(crate) fn resolve_name(&self, db: &impl HirDatabase, name: &Name) -> PerNs<Resolution> { | 160 | pub(crate) fn resolve_name(&self, db: &impl HirDatabase, name: &Name) -> PerNs<Resolution> { |
125 | let mut resolution = PerNs::none(); | 161 | let mut resolution = PerNs::none(); |
126 | for scope in self.scopes.iter().rev() { | 162 | for scope in self.scopes.iter().rev() { |
diff --git a/crates/ra_hir/src/source_binder.rs b/crates/ra_hir/src/source_binder.rs index afdcd5415..65b304b43 100644 --- a/crates/ra_hir/src/source_binder.rs +++ b/crates/ra_hir/src/source_binder.rs | |||
@@ -29,7 +29,7 @@ use crate::{ | |||
29 | path::{PathKind, PathSegment}, | 29 | path::{PathKind, PathSegment}, |
30 | ty::method_resolution::implements_trait, | 30 | ty::method_resolution::implements_trait, |
31 | AsName, AstId, Const, Crate, DefWithBody, Either, Enum, Function, HasBody, HirFileId, MacroDef, | 31 | AsName, AstId, Const, Crate, DefWithBody, Either, Enum, Function, HasBody, HirFileId, MacroDef, |
32 | Module, ModuleDef, Name, Path, PerNs, Resolution, Resolver, Static, Struct, Trait, Ty, | 32 | Module, Name, Path, PerNs, Resolver, Static, Struct, Trait, Ty, |
33 | }; | 33 | }; |
34 | 34 | ||
35 | /// Locates the module by `FileId`. Picks topmost module in the file. | 35 | /// Locates the module by `FileId`. Picks topmost module in the file. |
@@ -426,11 +426,10 @@ impl SourceAnalyzer { | |||
426 | ], | 426 | ], |
427 | }; | 427 | }; |
428 | 428 | ||
429 | let std_future_trait = | 429 | let std_future_trait = match self.resolver.resolve_known_trait(db, &std_future_path) { |
430 | match self.resolver.resolve_path_segments(db, &std_future_path).into_fully_resolved() { | 430 | Some(it) => it, |
431 | PerNs { types: Some(Resolution::Def(ModuleDef::Trait(trait_))), .. } => trait_, | 431 | _ => return false, |
432 | _ => return false, | 432 | }; |
433 | }; | ||
434 | 433 | ||
435 | let krate = match self.resolver.krate() { | 434 | let krate = match self.resolver.krate() { |
436 | Some(krate) => krate, | 435 | Some(krate) => krate, |
diff --git a/crates/ra_hir/src/ty/infer.rs b/crates/ra_hir/src/ty/infer.rs index 1057bbbec..3970c49e3 100644 --- a/crates/ra_hir/src/ty/infer.rs +++ b/crates/ra_hir/src/ty/infer.rs | |||
@@ -34,7 +34,7 @@ use super::{ | |||
34 | }; | 34 | }; |
35 | use crate::{ | 35 | use crate::{ |
36 | adt::VariantDef, | 36 | adt::VariantDef, |
37 | code_model::{ModuleDef::Trait, TypeAlias}, | 37 | code_model::TypeAlias, |
38 | db::HirDatabase, | 38 | db::HirDatabase, |
39 | diagnostics::DiagnosticSink, | 39 | diagnostics::DiagnosticSink, |
40 | expr::{ | 40 | expr::{ |
@@ -43,12 +43,9 @@ use crate::{ | |||
43 | }, | 43 | }, |
44 | generics::{GenericParams, HasGenericParams}, | 44 | generics::{GenericParams, HasGenericParams}, |
45 | name, | 45 | name, |
46 | nameres::{Namespace, PerNs}, | 46 | nameres::Namespace, |
47 | path::{GenericArg, GenericArgs, PathKind, PathSegment}, | 47 | path::{GenericArg, GenericArgs, PathKind, PathSegment}, |
48 | resolve::{ | 48 | resolve::{Resolution, Resolver}, |
49 | Resolution::{self, Def}, | ||
50 | Resolver, | ||
51 | }, | ||
52 | ty::infer::diagnostics::InferenceDiagnostic, | 49 | ty::infer::diagnostics::InferenceDiagnostic, |
53 | type_ref::{Mutability, TypeRef}, | 50 | type_ref::{Mutability, TypeRef}, |
54 | AdtDef, ConstData, DefWithBody, FnData, Function, HasBody, ImplItem, ModuleDef, Name, Path, | 51 | AdtDef, ConstData, DefWithBody, FnData, Function, HasBody, ImplItem, ModuleDef, Name, Path, |
@@ -1460,12 +1457,8 @@ impl<'a, D: HirDatabase> InferenceContext<'a, D> { | |||
1460 | ], | 1457 | ], |
1461 | }; | 1458 | }; |
1462 | 1459 | ||
1463 | match self.resolver.resolve_path_segments(self.db, &into_iter_path).into_fully_resolved() { | 1460 | let trait_ = self.resolver.resolve_known_trait(self.db, &into_iter_path)?; |
1464 | PerNs { types: Some(Def(Trait(trait_))), .. } => { | 1461 | trait_.associated_type_by_name(self.db, &name::ITEM) |
1465 | Some(trait_.associated_type_by_name(self.db, &name::ITEM)?) | ||
1466 | } | ||
1467 | _ => None, | ||
1468 | } | ||
1469 | } | 1462 | } |
1470 | 1463 | ||
1471 | fn resolve_ops_try_ok(&self) -> Option<TypeAlias> { | 1464 | fn resolve_ops_try_ok(&self) -> Option<TypeAlias> { |
@@ -1478,12 +1471,8 @@ impl<'a, D: HirDatabase> InferenceContext<'a, D> { | |||
1478 | ], | 1471 | ], |
1479 | }; | 1472 | }; |
1480 | 1473 | ||
1481 | match self.resolver.resolve_path_segments(self.db, &ops_try_path).into_fully_resolved() { | 1474 | let trait_ = self.resolver.resolve_known_trait(self.db, &ops_try_path)?; |
1482 | PerNs { types: Some(Def(Trait(trait_))), .. } => { | 1475 | trait_.associated_type_by_name(self.db, &name::OK) |
1483 | Some(trait_.associated_type_by_name(self.db, &name::OK)?) | ||
1484 | } | ||
1485 | _ => None, | ||
1486 | } | ||
1487 | } | 1476 | } |
1488 | 1477 | ||
1489 | fn resolve_future_future_output(&self) -> Option<TypeAlias> { | 1478 | fn resolve_future_future_output(&self) -> Option<TypeAlias> { |
@@ -1496,16 +1485,8 @@ impl<'a, D: HirDatabase> InferenceContext<'a, D> { | |||
1496 | ], | 1485 | ], |
1497 | }; | 1486 | }; |
1498 | 1487 | ||
1499 | match self | 1488 | let trait_ = self.resolver.resolve_known_trait(self.db, &future_future_path)?; |
1500 | .resolver | 1489 | trait_.associated_type_by_name(self.db, &name::OUTPUT) |
1501 | .resolve_path_segments(self.db, &future_future_path) | ||
1502 | .into_fully_resolved() | ||
1503 | { | ||
1504 | PerNs { types: Some(Def(Trait(trait_))), .. } => { | ||
1505 | Some(trait_.associated_type_by_name(self.db, &name::OUTPUT)?) | ||
1506 | } | ||
1507 | _ => None, | ||
1508 | } | ||
1509 | } | 1490 | } |
1510 | 1491 | ||
1511 | fn resolve_boxed_box(&self) -> Option<AdtDef> { | 1492 | fn resolve_boxed_box(&self) -> Option<AdtDef> { |
@@ -1517,13 +1498,8 @@ impl<'a, D: HirDatabase> InferenceContext<'a, D> { | |||
1517 | PathSegment { name: name::BOX_TYPE, args_and_bindings: None }, | 1498 | PathSegment { name: name::BOX_TYPE, args_and_bindings: None }, |
1518 | ], | 1499 | ], |
1519 | }; | 1500 | }; |
1520 | 1501 | let struct_ = self.resolver.resolve_known_struct(self.db, &boxed_box_path)?; | |
1521 | match self.resolver.resolve_path_segments(self.db, &boxed_box_path).into_fully_resolved() { | 1502 | Some(AdtDef::Struct(struct_)) |
1522 | PerNs { types: Some(Def(ModuleDef::Struct(struct_))), .. } => { | ||
1523 | Some(AdtDef::Struct(struct_)) | ||
1524 | } | ||
1525 | _ => None, | ||
1526 | } | ||
1527 | } | 1503 | } |
1528 | } | 1504 | } |
1529 | 1505 | ||
diff --git a/crates/ra_hir/src/ty/lower.rs b/crates/ra_hir/src/ty/lower.rs index 061229842..e67525a74 100644 --- a/crates/ra_hir/src/ty/lower.rs +++ b/crates/ra_hir/src/ty/lower.rs | |||
@@ -86,7 +86,7 @@ impl Ty { | |||
86 | } | 86 | } |
87 | } | 87 | } |
88 | 88 | ||
89 | pub(crate) fn from_hir_path(db: &impl HirDatabase, resolver: &Resolver, path: &Path) -> Self { | 89 | pub(crate) fn from_hir_path(db: &impl HirDatabase, resolver: &Resolver, path: &Path) -> Ty { |
90 | // Resolve the path (in type namespace) | 90 | // Resolve the path (in type namespace) |
91 | let (resolution, remaining_index) = resolver.resolve_path_segments(db, path).into_inner(); | 91 | let (resolution, remaining_index) = resolver.resolve_path_segments(db, path).into_inner(); |
92 | let resolution = resolution.take_types(); | 92 | let resolution = resolution.take_types(); |