aboutsummaryrefslogtreecommitdiff
path: root/crates
diff options
context:
space:
mode:
Diffstat (limited to 'crates')
-rw-r--r--crates/hir/src/lib.rs6
-rw-r--r--crates/hir_ty/src/infer.rs10
-rw-r--r--crates/hir_ty/src/infer/path.rs10
-rw-r--r--crates/hir_ty/src/lower.rs510
-rw-r--r--crates/hir_ty/src/traits/chalk.rs2
5 files changed, 249 insertions, 289 deletions
diff --git a/crates/hir/src/lib.rs b/crates/hir/src/lib.rs
index cda050a7d..10b8171be 100644
--- a/crates/hir/src/lib.rs
+++ b/crates/hir/src/lib.rs
@@ -802,7 +802,7 @@ impl Function {
802 let krate = self.id.lookup(db.upcast()).container.module(db.upcast()).krate(); 802 let krate = self.id.lookup(db.upcast()).container.module(db.upcast()).krate();
803 let ret_type = &db.function_data(self.id).ret_type; 803 let ret_type = &db.function_data(self.id).ret_type;
804 let ctx = hir_ty::TyLoweringContext::new(db, &resolver); 804 let ctx = hir_ty::TyLoweringContext::new(db, &resolver);
805 let ty = Ty::from_hir_ext(&ctx, ret_type).0; 805 let ty = ctx.lower_ty(ret_type);
806 Type::new_with_resolver_inner(db, krate, &resolver, ty) 806 Type::new_with_resolver_inner(db, krate, &resolver, ty)
807 } 807 }
808 808
@@ -825,7 +825,7 @@ impl Function {
825 let ty = Type { 825 let ty = Type {
826 krate, 826 krate,
827 ty: InEnvironment { 827 ty: InEnvironment {
828 value: Ty::from_hir_ext(&ctx, type_ref).0, 828 value: ctx.lower_ty(type_ref),
829 environment: environment.clone(), 829 environment: environment.clone(),
830 }, 830 },
831 }; 831 };
@@ -1499,7 +1499,7 @@ impl Impl {
1499 let resolver = self.id.resolver(db.upcast()); 1499 let resolver = self.id.resolver(db.upcast());
1500 let krate = self.id.lookup(db.upcast()).container.krate(); 1500 let krate = self.id.lookup(db.upcast()).container.krate();
1501 let ctx = hir_ty::TyLoweringContext::new(db, &resolver); 1501 let ctx = hir_ty::TyLoweringContext::new(db, &resolver);
1502 let ty = Ty::from_hir(&ctx, &impl_data.target_type); 1502 let ty = ctx.lower_ty(&impl_data.target_type);
1503 Type::new_with_resolver_inner(db, krate, &resolver, ty) 1503 Type::new_with_resolver_inner(db, krate, &resolver, ty)
1504 } 1504 }
1505 1505
diff --git a/crates/hir_ty/src/infer.rs b/crates/hir_ty/src/infer.rs
index bc52f447d..8cf59821f 100644
--- a/crates/hir_ty/src/infer.rs
+++ b/crates/hir_ty/src/infer.rs
@@ -294,7 +294,7 @@ impl<'a> InferenceContext<'a> {
294 // FIXME use right resolver for block 294 // FIXME use right resolver for block
295 let ctx = crate::lower::TyLoweringContext::new(self.db, &self.resolver) 295 let ctx = crate::lower::TyLoweringContext::new(self.db, &self.resolver)
296 .with_impl_trait_mode(impl_trait_mode); 296 .with_impl_trait_mode(impl_trait_mode);
297 let ty = Ty::from_hir(&ctx, type_ref); 297 let ty = ctx.lower_ty(type_ref);
298 let ty = self.insert_type_vars(ty); 298 let ty = self.insert_type_vars(ty);
299 self.normalize_associated_types_in(ty) 299 self.normalize_associated_types_in(ty)
300 } 300 }
@@ -437,19 +437,19 @@ impl<'a> InferenceContext<'a> {
437 }; 437 };
438 return match resolution { 438 return match resolution {
439 TypeNs::AdtId(AdtId::StructId(strukt)) => { 439 TypeNs::AdtId(AdtId::StructId(strukt)) => {
440 let substs = Ty::substs_from_path(&ctx, path, strukt.into(), true); 440 let substs = ctx.substs_from_path(path, strukt.into(), true);
441 let ty = self.db.ty(strukt.into()); 441 let ty = self.db.ty(strukt.into());
442 let ty = self.insert_type_vars(ty.subst(&substs)); 442 let ty = self.insert_type_vars(ty.subst(&substs));
443 forbid_unresolved_segments((ty, Some(strukt.into())), unresolved) 443 forbid_unresolved_segments((ty, Some(strukt.into())), unresolved)
444 } 444 }
445 TypeNs::AdtId(AdtId::UnionId(u)) => { 445 TypeNs::AdtId(AdtId::UnionId(u)) => {
446 let substs = Ty::substs_from_path(&ctx, path, u.into(), true); 446 let substs = ctx.substs_from_path(path, u.into(), true);
447 let ty = self.db.ty(u.into()); 447 let ty = self.db.ty(u.into());
448 let ty = self.insert_type_vars(ty.subst(&substs)); 448 let ty = self.insert_type_vars(ty.subst(&substs));
449 forbid_unresolved_segments((ty, Some(u.into())), unresolved) 449 forbid_unresolved_segments((ty, Some(u.into())), unresolved)
450 } 450 }
451 TypeNs::EnumVariantId(var) => { 451 TypeNs::EnumVariantId(var) => {
452 let substs = Ty::substs_from_path(&ctx, path, var.into(), true); 452 let substs = ctx.substs_from_path(path, var.into(), true);
453 let ty = self.db.ty(var.parent.into()); 453 let ty = self.db.ty(var.parent.into());
454 let ty = self.insert_type_vars(ty.subst(&substs)); 454 let ty = self.insert_type_vars(ty.subst(&substs));
455 forbid_unresolved_segments((ty, Some(var.into())), unresolved) 455 forbid_unresolved_segments((ty, Some(var.into())), unresolved)
@@ -541,7 +541,7 @@ impl<'a> InferenceContext<'a> {
541 let ctx = crate::lower::TyLoweringContext::new(self.db, &self.resolver) 541 let ctx = crate::lower::TyLoweringContext::new(self.db, &self.resolver)
542 .with_impl_trait_mode(ImplTraitLoweringMode::Param); 542 .with_impl_trait_mode(ImplTraitLoweringMode::Param);
543 let param_tys = 543 let param_tys =
544 data.params.iter().map(|type_ref| Ty::from_hir(&ctx, type_ref)).collect::<Vec<_>>(); 544 data.params.iter().map(|type_ref| ctx.lower_ty(type_ref)).collect::<Vec<_>>();
545 for (ty, pat) in param_tys.into_iter().zip(body.params.iter()) { 545 for (ty, pat) in param_tys.into_iter().zip(body.params.iter()) {
546 let ty = self.insert_type_vars(ty); 546 let ty = self.insert_type_vars(ty);
547 let ty = self.normalize_associated_types_in(ty); 547 let ty = self.normalize_associated_types_in(ty);
diff --git a/crates/hir_ty/src/infer/path.rs b/crates/hir_ty/src/infer/path.rs
index c6681834c..af108fb6c 100644
--- a/crates/hir_ty/src/infer/path.rs
+++ b/crates/hir_ty/src/infer/path.rs
@@ -40,7 +40,7 @@ impl<'a> InferenceContext<'a> {
40 let ty = self.make_ty(type_ref); 40 let ty = self.make_ty(type_ref);
41 let remaining_segments_for_ty = path.segments().take(path.segments().len() - 1); 41 let remaining_segments_for_ty = path.segments().take(path.segments().len() - 1);
42 let ctx = crate::lower::TyLoweringContext::new(self.db, &resolver); 42 let ctx = crate::lower::TyLoweringContext::new(self.db, &resolver);
43 let (ty, _) = Ty::from_type_relative_path(&ctx, ty, None, remaining_segments_for_ty); 43 let (ty, _) = ctx.lower_ty_relative_path(ty, None, remaining_segments_for_ty);
44 self.resolve_ty_assoc_item( 44 self.resolve_ty_assoc_item(
45 ty, 45 ty,
46 &path.segments().last().expect("path had at least one segment").name, 46 &path.segments().last().expect("path had at least one segment").name,
@@ -96,7 +96,7 @@ impl<'a> InferenceContext<'a> {
96 // self_subst is just for the parent 96 // self_subst is just for the parent
97 let parent_substs = self_subst.unwrap_or_else(Substs::empty); 97 let parent_substs = self_subst.unwrap_or_else(Substs::empty);
98 let ctx = crate::lower::TyLoweringContext::new(self.db, &self.resolver); 98 let ctx = crate::lower::TyLoweringContext::new(self.db, &self.resolver);
99 let substs = Ty::substs_from_path(&ctx, path, typable, true); 99 let substs = ctx.substs_from_path(path, typable, true);
100 let full_substs = Substs::builder(substs.len()) 100 let full_substs = Substs::builder(substs.len())
101 .use_parent_substs(&parent_substs) 101 .use_parent_substs(&parent_substs)
102 .fill(substs.0[parent_substs.len()..].iter().cloned()) 102 .fill(substs.0[parent_substs.len()..].iter().cloned())
@@ -126,7 +126,8 @@ impl<'a> InferenceContext<'a> {
126 let segment = 126 let segment =
127 remaining_segments.last().expect("there should be at least one segment here"); 127 remaining_segments.last().expect("there should be at least one segment here");
128 let ctx = crate::lower::TyLoweringContext::new(self.db, &self.resolver); 128 let ctx = crate::lower::TyLoweringContext::new(self.db, &self.resolver);
129 let trait_ref = TraitRef::from_resolved_path(&ctx, trait_, resolved_segment, None); 129 let trait_ref =
130 ctx.lower_trait_ref_from_resolved_path(trait_, resolved_segment, None);
130 self.resolve_trait_assoc_item(trait_ref, segment, id) 131 self.resolve_trait_assoc_item(trait_ref, segment, id)
131 } 132 }
132 (def, _) => { 133 (def, _) => {
@@ -137,8 +138,7 @@ impl<'a> InferenceContext<'a> {
137 let remaining_segments_for_ty = 138 let remaining_segments_for_ty =
138 remaining_segments.take(remaining_segments.len() - 1); 139 remaining_segments.take(remaining_segments.len() - 1);
139 let ctx = crate::lower::TyLoweringContext::new(self.db, &self.resolver); 140 let ctx = crate::lower::TyLoweringContext::new(self.db, &self.resolver);
140 let (ty, _) = Ty::from_partly_resolved_hir_path( 141 let (ty, _) = ctx.lower_partly_resolved_path(
141 &ctx,
142 def, 142 def,
143 resolved_segment, 143 resolved_segment,
144 remaining_segments_for_ty, 144 remaining_segments_for_ty,
diff --git a/crates/hir_ty/src/lower.rs b/crates/hir_ty/src/lower.rs
index 3b0706530..c32dca9d7 100644
--- a/crates/hir_ty/src/lower.rs
+++ b/crates/hir_ty/src/lower.rs
@@ -140,44 +140,45 @@ pub enum TypeParamLoweringMode {
140 Variable, 140 Variable,
141} 141}
142 142
143impl Ty { 143impl<'a> TyLoweringContext<'a> {
144 pub fn from_hir(ctx: &TyLoweringContext<'_>, type_ref: &TypeRef) -> Self { 144 pub fn lower_ty(&self, type_ref: &TypeRef) -> Ty {
145 Ty::from_hir_ext(ctx, type_ref).0 145 self.lower_ty_ext(type_ref).0
146 } 146 }
147 pub fn from_hir_ext(ctx: &TyLoweringContext<'_>, type_ref: &TypeRef) -> (Self, Option<TypeNs>) { 147
148 fn lower_ty_ext(&self, type_ref: &TypeRef) -> (Ty, Option<TypeNs>) {
148 let mut res = None; 149 let mut res = None;
149 let ty = match type_ref { 150 let ty = match type_ref {
150 TypeRef::Never => TyKind::Never.intern(&Interner), 151 TypeRef::Never => TyKind::Never.intern(&Interner),
151 TypeRef::Tuple(inner) => { 152 TypeRef::Tuple(inner) => {
152 let inner_tys: Arc<[Ty]> = inner.iter().map(|tr| Ty::from_hir(ctx, tr)).collect(); 153 let inner_tys: Arc<[Ty]> = inner.iter().map(|tr| self.lower_ty(tr)).collect();
153 TyKind::Tuple(inner_tys.len(), Substs(inner_tys)).intern(&Interner) 154 TyKind::Tuple(inner_tys.len(), Substs(inner_tys)).intern(&Interner)
154 } 155 }
155 TypeRef::Path(path) => { 156 TypeRef::Path(path) => {
156 let (ty, res_) = Ty::from_hir_path(ctx, path); 157 let (ty, res_) = self.lower_path(path);
157 res = res_; 158 res = res_;
158 ty 159 ty
159 } 160 }
160 TypeRef::RawPtr(inner, mutability) => { 161 TypeRef::RawPtr(inner, mutability) => {
161 let inner_ty = Ty::from_hir(ctx, inner); 162 let inner_ty = self.lower_ty(inner);
162 TyKind::Raw(lower_to_chalk_mutability(*mutability), Substs::single(inner_ty)) 163 TyKind::Raw(lower_to_chalk_mutability(*mutability), Substs::single(inner_ty))
163 .intern(&Interner) 164 .intern(&Interner)
164 } 165 }
165 TypeRef::Array(inner) => { 166 TypeRef::Array(inner) => {
166 let inner_ty = Ty::from_hir(ctx, inner); 167 let inner_ty = self.lower_ty(inner);
167 TyKind::Array(Substs::single(inner_ty)).intern(&Interner) 168 TyKind::Array(Substs::single(inner_ty)).intern(&Interner)
168 } 169 }
169 TypeRef::Slice(inner) => { 170 TypeRef::Slice(inner) => {
170 let inner_ty = Ty::from_hir(ctx, inner); 171 let inner_ty = self.lower_ty(inner);
171 TyKind::Slice(Substs::single(inner_ty)).intern(&Interner) 172 TyKind::Slice(Substs::single(inner_ty)).intern(&Interner)
172 } 173 }
173 TypeRef::Reference(inner, _, mutability) => { 174 TypeRef::Reference(inner, _, mutability) => {
174 let inner_ty = Ty::from_hir(ctx, inner); 175 let inner_ty = self.lower_ty(inner);
175 TyKind::Ref(lower_to_chalk_mutability(*mutability), Substs::single(inner_ty)) 176 TyKind::Ref(lower_to_chalk_mutability(*mutability), Substs::single(inner_ty))
176 .intern(&Interner) 177 .intern(&Interner)
177 } 178 }
178 TypeRef::Placeholder => TyKind::Unknown.intern(&Interner), 179 TypeRef::Placeholder => TyKind::Unknown.intern(&Interner),
179 TypeRef::Fn(params, is_varargs) => { 180 TypeRef::Fn(params, is_varargs) => {
180 let substs = Substs(params.iter().map(|tr| Ty::from_hir(ctx, tr)).collect()); 181 let substs = Substs(params.iter().map(|tr| self.lower_ty(tr)).collect());
181 TyKind::Function(FnPointer { 182 TyKind::Function(FnPointer {
182 num_args: substs.len() - 1, 183 num_args: substs.len() - 1,
183 sig: FnSig { variadic: *is_varargs }, 184 sig: FnSig { variadic: *is_varargs },
@@ -188,25 +189,22 @@ impl Ty {
188 TypeRef::DynTrait(bounds) => { 189 TypeRef::DynTrait(bounds) => {
189 let self_ty = 190 let self_ty =
190 TyKind::BoundVar(BoundVar::new(DebruijnIndex::INNERMOST, 0)).intern(&Interner); 191 TyKind::BoundVar(BoundVar::new(DebruijnIndex::INNERMOST, 0)).intern(&Interner);
191 let predicates = ctx.with_shifted_in(DebruijnIndex::ONE, |ctx| { 192 let predicates = self.with_shifted_in(DebruijnIndex::ONE, |ctx| {
192 bounds 193 bounds.iter().flat_map(|b| ctx.lower_type_bound(b, self_ty.clone())).collect()
193 .iter()
194 .flat_map(|b| GenericPredicate::from_type_bound(ctx, b, self_ty.clone()))
195 .collect()
196 }); 194 });
197 TyKind::Dyn(predicates).intern(&Interner) 195 TyKind::Dyn(predicates).intern(&Interner)
198 } 196 }
199 TypeRef::ImplTrait(bounds) => { 197 TypeRef::ImplTrait(bounds) => {
200 match ctx.impl_trait_mode { 198 match self.impl_trait_mode {
201 ImplTraitLoweringMode::Opaque => { 199 ImplTraitLoweringMode::Opaque => {
202 let idx = ctx.impl_trait_counter.get(); 200 let idx = self.impl_trait_counter.get();
203 ctx.impl_trait_counter.set(idx + 1); 201 self.impl_trait_counter.set(idx + 1);
204 202
205 assert!(idx as usize == ctx.opaque_type_data.borrow().len()); 203 assert!(idx as usize == self.opaque_type_data.borrow().len());
206 // this dance is to make sure the data is in the right 204 // this dance is to make sure the data is in the right
207 // place even if we encounter more opaque types while 205 // place even if we encounter more opaque types while
208 // lowering the bounds 206 // lowering the bounds
209 ctx.opaque_type_data 207 self.opaque_type_data
210 .borrow_mut() 208 .borrow_mut()
211 .push(ReturnTypeImplTrait { bounds: Binders::new(1, Vec::new()) }); 209 .push(ReturnTypeImplTrait { bounds: Binders::new(1, Vec::new()) });
212 // We don't want to lower the bounds inside the binders 210 // We don't want to lower the bounds inside the binders
@@ -218,29 +216,29 @@ impl Ty {
218 // other, but separately. So if the `T` refers to a type 216 // other, but separately. So if the `T` refers to a type
219 // parameter of the outer function, it's just one binder 217 // parameter of the outer function, it's just one binder
220 // away instead of two. 218 // away instead of two.
221 let actual_opaque_type_data = ctx 219 let actual_opaque_type_data = self
222 .with_debruijn(DebruijnIndex::INNERMOST, |ctx| { 220 .with_debruijn(DebruijnIndex::INNERMOST, |ctx| {
223 ReturnTypeImplTrait::from_hir(ctx, &bounds) 221 ctx.lower_impl_trait(&bounds)
224 }); 222 });
225 ctx.opaque_type_data.borrow_mut()[idx as usize] = actual_opaque_type_data; 223 self.opaque_type_data.borrow_mut()[idx as usize] = actual_opaque_type_data;
226 224
227 let func = match ctx.resolver.generic_def() { 225 let func = match self.resolver.generic_def() {
228 Some(GenericDefId::FunctionId(f)) => f, 226 Some(GenericDefId::FunctionId(f)) => f,
229 _ => panic!("opaque impl trait lowering in non-function"), 227 _ => panic!("opaque impl trait lowering in non-function"),
230 }; 228 };
231 let impl_trait_id = ImplTraitId::ReturnTypeImplTrait(func, idx); 229 let impl_trait_id = ImplTraitId::ReturnTypeImplTrait(func, idx);
232 let opaque_ty_id = ctx.db.intern_impl_trait_id(impl_trait_id).into(); 230 let opaque_ty_id = self.db.intern_impl_trait_id(impl_trait_id).into();
233 let generics = generics(ctx.db.upcast(), func.into()); 231 let generics = generics(self.db.upcast(), func.into());
234 let parameters = Substs::bound_vars(&generics, ctx.in_binders); 232 let parameters = Substs::bound_vars(&generics, self.in_binders);
235 TyKind::Alias(AliasTy::Opaque(OpaqueTy { opaque_ty_id, parameters })) 233 TyKind::Alias(AliasTy::Opaque(OpaqueTy { opaque_ty_id, parameters }))
236 .intern(&Interner) 234 .intern(&Interner)
237 } 235 }
238 ImplTraitLoweringMode::Param => { 236 ImplTraitLoweringMode::Param => {
239 let idx = ctx.impl_trait_counter.get(); 237 let idx = self.impl_trait_counter.get();
240 // FIXME we're probably doing something wrong here 238 // FIXME we're probably doing something wrong here
241 ctx.impl_trait_counter.set(idx + count_impl_traits(type_ref) as u16); 239 self.impl_trait_counter.set(idx + count_impl_traits(type_ref) as u16);
242 if let Some(def) = ctx.resolver.generic_def() { 240 if let Some(def) = self.resolver.generic_def() {
243 let generics = generics(ctx.db.upcast(), def); 241 let generics = generics(self.db.upcast(), def);
244 let param = generics 242 let param = generics
245 .iter() 243 .iter()
246 .filter(|(_, data)| { 244 .filter(|(_, data)| {
@@ -248,7 +246,7 @@ impl Ty {
248 }) 246 })
249 .nth(idx as usize) 247 .nth(idx as usize)
250 .map_or(TyKind::Unknown, |(id, _)| { 248 .map_or(TyKind::Unknown, |(id, _)| {
251 TyKind::Placeholder(to_placeholder_idx(ctx.db, id)) 249 TyKind::Placeholder(to_placeholder_idx(self.db, id))
252 }); 250 });
253 param.intern(&Interner) 251 param.intern(&Interner)
254 } else { 252 } else {
@@ -256,18 +254,18 @@ impl Ty {
256 } 254 }
257 } 255 }
258 ImplTraitLoweringMode::Variable => { 256 ImplTraitLoweringMode::Variable => {
259 let idx = ctx.impl_trait_counter.get(); 257 let idx = self.impl_trait_counter.get();
260 // FIXME we're probably doing something wrong here 258 // FIXME we're probably doing something wrong here
261 ctx.impl_trait_counter.set(idx + count_impl_traits(type_ref) as u16); 259 self.impl_trait_counter.set(idx + count_impl_traits(type_ref) as u16);
262 let (parent_params, self_params, list_params, _impl_trait_params) = 260 let (parent_params, self_params, list_params, _impl_trait_params) =
263 if let Some(def) = ctx.resolver.generic_def() { 261 if let Some(def) = self.resolver.generic_def() {
264 let generics = generics(ctx.db.upcast(), def); 262 let generics = generics(self.db.upcast(), def);
265 generics.provenance_split() 263 generics.provenance_split()
266 } else { 264 } else {
267 (0, 0, 0, 0) 265 (0, 0, 0, 0)
268 }; 266 };
269 TyKind::BoundVar(BoundVar::new( 267 TyKind::BoundVar(BoundVar::new(
270 ctx.in_binders, 268 self.in_binders,
271 idx as usize + parent_params + self_params + list_params, 269 idx as usize + parent_params + self_params + list_params,
272 )) 270 ))
273 .intern(&Interner) 271 .intern(&Interner)
@@ -286,7 +284,7 @@ impl Ty {
286 /// This is only for `generic_predicates_for_param`, where we can't just 284 /// This is only for `generic_predicates_for_param`, where we can't just
287 /// lower the self types of the predicates since that could lead to cycles. 285 /// lower the self types of the predicates since that could lead to cycles.
288 /// So we just check here if the `type_ref` resolves to a generic param, and which. 286 /// So we just check here if the `type_ref` resolves to a generic param, and which.
289 fn from_hir_only_param(ctx: &TyLoweringContext<'_>, type_ref: &TypeRef) -> Option<TypeParamId> { 287 fn lower_ty_only_param(&self, type_ref: &TypeRef) -> Option<TypeParamId> {
290 let path = match type_ref { 288 let path = match type_ref {
291 TypeRef::Path(path) => path, 289 TypeRef::Path(path) => path,
292 _ => return None, 290 _ => return None,
@@ -298,7 +296,7 @@ impl Ty {
298 return None; 296 return None;
299 } 297 }
300 let resolution = 298 let resolution =
301 match ctx.resolver.resolve_path_in_type_ns(ctx.db.upcast(), path.mod_path()) { 299 match self.resolver.resolve_path_in_type_ns(self.db.upcast(), path.mod_path()) {
302 Some((it, None)) => it, 300 Some((it, None)) => it,
303 _ => return None, 301 _ => return None,
304 }; 302 };
@@ -309,8 +307,8 @@ impl Ty {
309 } 307 }
310 } 308 }
311 309
312 pub(crate) fn from_type_relative_path( 310 pub(crate) fn lower_ty_relative_path(
313 ctx: &TyLoweringContext<'_>, 311 &self,
314 ty: Ty, 312 ty: Ty,
315 // We need the original resolution to lower `Self::AssocTy` correctly 313 // We need the original resolution to lower `Self::AssocTy` correctly
316 res: Option<TypeNs>, 314 res: Option<TypeNs>,
@@ -319,7 +317,7 @@ impl Ty {
319 if remaining_segments.len() == 1 { 317 if remaining_segments.len() == 1 {
320 // resolve unselected assoc types 318 // resolve unselected assoc types
321 let segment = remaining_segments.first().unwrap(); 319 let segment = remaining_segments.first().unwrap();
322 (Ty::select_associated_type(ctx, res, segment), None) 320 (self.select_associated_type(res, segment), None)
323 } else if remaining_segments.len() > 1 { 321 } else if remaining_segments.len() > 1 {
324 // FIXME report error (ambiguous associated type) 322 // FIXME report error (ambiguous associated type)
325 (TyKind::Unknown.intern(&Interner), None) 323 (TyKind::Unknown.intern(&Interner), None)
@@ -328,8 +326,8 @@ impl Ty {
328 } 326 }
329 } 327 }
330 328
331 pub(crate) fn from_partly_resolved_hir_path( 329 pub(crate) fn lower_partly_resolved_path(
332 ctx: &TyLoweringContext<'_>, 330 &self,
333 resolution: TypeNs, 331 resolution: TypeNs,
334 resolved_segment: PathSegment<'_>, 332 resolved_segment: PathSegment<'_>,
335 remaining_segments: PathSegments<'_>, 333 remaining_segments: PathSegments<'_>,
@@ -347,11 +345,11 @@ impl Ty {
347 None 345 None
348 }; 346 };
349 let trait_ref = 347 let trait_ref =
350 TraitRef::from_resolved_path(ctx, trait_, resolved_segment, self_ty); 348 self.lower_trait_ref_from_resolved_path(trait_, resolved_segment, self_ty);
351 let ty = if remaining_segments.len() == 1 { 349 let ty = if remaining_segments.len() == 1 {
352 let segment = remaining_segments.first().unwrap(); 350 let segment = remaining_segments.first().unwrap();
353 let found = associated_type_by_name_including_super_traits( 351 let found = associated_type_by_name_including_super_traits(
354 ctx.db, 352 self.db,
355 trait_ref, 353 trait_ref,
356 &segment.name, 354 &segment.name,
357 ); 355 );
@@ -380,68 +378,66 @@ impl Ty {
380 } 378 }
381 TypeNs::GenericParam(param_id) => { 379 TypeNs::GenericParam(param_id) => {
382 let generics = generics( 380 let generics = generics(
383 ctx.db.upcast(), 381 self.db.upcast(),
384 ctx.resolver.generic_def().expect("generics in scope"), 382 self.resolver.generic_def().expect("generics in scope"),
385 ); 383 );
386 match ctx.type_param_mode { 384 match self.type_param_mode {
387 TypeParamLoweringMode::Placeholder => { 385 TypeParamLoweringMode::Placeholder => {
388 TyKind::Placeholder(to_placeholder_idx(ctx.db, param_id)) 386 TyKind::Placeholder(to_placeholder_idx(self.db, param_id))
389 } 387 }
390 TypeParamLoweringMode::Variable => { 388 TypeParamLoweringMode::Variable => {
391 let idx = generics.param_idx(param_id).expect("matching generics"); 389 let idx = generics.param_idx(param_id).expect("matching generics");
392 TyKind::BoundVar(BoundVar::new(ctx.in_binders, idx)) 390 TyKind::BoundVar(BoundVar::new(self.in_binders, idx))
393 } 391 }
394 } 392 }
395 .intern(&Interner) 393 .intern(&Interner)
396 } 394 }
397 TypeNs::SelfType(impl_id) => { 395 TypeNs::SelfType(impl_id) => {
398 let generics = generics(ctx.db.upcast(), impl_id.into()); 396 let generics = generics(self.db.upcast(), impl_id.into());
399 let substs = match ctx.type_param_mode { 397 let substs = match self.type_param_mode {
400 TypeParamLoweringMode::Placeholder => { 398 TypeParamLoweringMode::Placeholder => {
401 Substs::type_params_for_generics(ctx.db, &generics) 399 Substs::type_params_for_generics(self.db, &generics)
402 } 400 }
403 TypeParamLoweringMode::Variable => { 401 TypeParamLoweringMode::Variable => {
404 Substs::bound_vars(&generics, ctx.in_binders) 402 Substs::bound_vars(&generics, self.in_binders)
405 } 403 }
406 }; 404 };
407 ctx.db.impl_self_ty(impl_id).subst(&substs) 405 self.db.impl_self_ty(impl_id).subst(&substs)
408 } 406 }
409 TypeNs::AdtSelfType(adt) => { 407 TypeNs::AdtSelfType(adt) => {
410 let generics = generics(ctx.db.upcast(), adt.into()); 408 let generics = generics(self.db.upcast(), adt.into());
411 let substs = match ctx.type_param_mode { 409 let substs = match self.type_param_mode {
412 TypeParamLoweringMode::Placeholder => { 410 TypeParamLoweringMode::Placeholder => {
413 Substs::type_params_for_generics(ctx.db, &generics) 411 Substs::type_params_for_generics(self.db, &generics)
414 } 412 }
415 TypeParamLoweringMode::Variable => { 413 TypeParamLoweringMode::Variable => {
416 Substs::bound_vars(&generics, ctx.in_binders) 414 Substs::bound_vars(&generics, self.in_binders)
417 } 415 }
418 }; 416 };
419 ctx.db.ty(adt.into()).subst(&substs) 417 self.db.ty(adt.into()).subst(&substs)
420 } 418 }
421 419
422 TypeNs::AdtId(it) => { 420 TypeNs::AdtId(it) => self.lower_path_inner(resolved_segment, it.into(), infer_args),
423 Ty::from_hir_path_inner(ctx, resolved_segment, it.into(), infer_args)
424 }
425 TypeNs::BuiltinType(it) => { 421 TypeNs::BuiltinType(it) => {
426 Ty::from_hir_path_inner(ctx, resolved_segment, it.into(), infer_args) 422 self.lower_path_inner(resolved_segment, it.into(), infer_args)
427 } 423 }
428 TypeNs::TypeAliasId(it) => { 424 TypeNs::TypeAliasId(it) => {
429 Ty::from_hir_path_inner(ctx, resolved_segment, it.into(), infer_args) 425 self.lower_path_inner(resolved_segment, it.into(), infer_args)
430 } 426 }
431 // FIXME: report error 427 // FIXME: report error
432 TypeNs::EnumVariantId(_) => return (TyKind::Unknown.intern(&Interner), None), 428 TypeNs::EnumVariantId(_) => return (TyKind::Unknown.intern(&Interner), None),
433 }; 429 };
434 Ty::from_type_relative_path(ctx, ty, Some(resolution), remaining_segments) 430 self.lower_ty_relative_path(ty, Some(resolution), remaining_segments)
435 } 431 }
436 432
437 pub(crate) fn from_hir_path(ctx: &TyLoweringContext<'_>, path: &Path) -> (Ty, Option<TypeNs>) { 433 pub(crate) fn lower_path(&self, path: &Path) -> (Ty, Option<TypeNs>) {
438 // Resolve the path (in type namespace) 434 // Resolve the path (in type namespace)
439 if let Some(type_ref) = path.type_anchor() { 435 if let Some(type_ref) = path.type_anchor() {
440 let (ty, res) = Ty::from_hir_ext(ctx, &type_ref); 436 let (ty, res) = self.lower_ty_ext(&type_ref);
441 return Ty::from_type_relative_path(ctx, ty, res, path.segments()); 437 return self.lower_ty_relative_path(ty, res, path.segments());
442 } 438 }
443 let (resolution, remaining_index) = 439 let (resolution, remaining_index) =
444 match ctx.resolver.resolve_path_in_type_ns(ctx.db.upcast(), path.mod_path()) { 440 match self.resolver.resolve_path_in_type_ns(self.db.upcast(), path.mod_path()) {
445 Some(it) => it, 441 Some(it) => it,
446 None => return (TyKind::Unknown.intern(&Interner), None), 442 None => return (TyKind::Unknown.intern(&Interner), None),
447 }; 443 };
@@ -452,31 +448,23 @@ impl Ty {
452 ), 448 ),
453 Some(i) => (path.segments().get(i - 1).unwrap(), path.segments().skip(i)), 449 Some(i) => (path.segments().get(i - 1).unwrap(), path.segments().skip(i)),
454 }; 450 };
455 Ty::from_partly_resolved_hir_path( 451 self.lower_partly_resolved_path(resolution, resolved_segment, remaining_segments, false)
456 ctx,
457 resolution,
458 resolved_segment,
459 remaining_segments,
460 false,
461 )
462 } 452 }
463 453
464 fn select_associated_type( 454 fn select_associated_type(&self, res: Option<TypeNs>, segment: PathSegment<'_>) -> Ty {
465 ctx: &TyLoweringContext<'_>,
466 res: Option<TypeNs>,
467 segment: PathSegment<'_>,
468 ) -> Ty {
469 if let Some(res) = res { 455 if let Some(res) = res {
470 let ty = 456 let ty = associated_type_shorthand_candidates(
471 associated_type_shorthand_candidates(ctx.db, res, move |name, t, associated_ty| { 457 self.db,
458 res,
459 move |name, t, associated_ty| {
472 if name == segment.name { 460 if name == segment.name {
473 let substs = match ctx.type_param_mode { 461 let substs = match self.type_param_mode {
474 TypeParamLoweringMode::Placeholder => { 462 TypeParamLoweringMode::Placeholder => {
475 // if we're lowering to placeholders, we have to put 463 // if we're lowering to placeholders, we have to put
476 // them in now 464 // them in now
477 let s = Substs::type_params( 465 let s = Substs::type_params(
478 ctx.db, 466 self.db,
479 ctx.resolver.generic_def().expect( 467 self.resolver.generic_def().expect(
480 "there should be generics if there's a generic param", 468 "there should be generics if there's a generic param",
481 ), 469 ),
482 ); 470 );
@@ -486,7 +474,7 @@ impl Ty {
486 }; 474 };
487 // We need to shift in the bound vars, since 475 // We need to shift in the bound vars, since
488 // associated_type_shorthand_candidates does not do that 476 // associated_type_shorthand_candidates does not do that
489 let substs = substs.shift_bound_vars(ctx.in_binders); 477 let substs = substs.shift_bound_vars(self.in_binders);
490 // FIXME handle type parameters on the segment 478 // FIXME handle type parameters on the segment
491 return Some( 479 return Some(
492 TyKind::Alias(AliasTy::Projection(ProjectionTy { 480 TyKind::Alias(AliasTy::Projection(ProjectionTy {
@@ -498,7 +486,8 @@ impl Ty {
498 } 486 }
499 487
500 None 488 None
501 }); 489 },
490 );
502 491
503 ty.unwrap_or(TyKind::Unknown.intern(&Interner)) 492 ty.unwrap_or(TyKind::Unknown.intern(&Interner))
504 } else { 493 } else {
@@ -506,8 +495,8 @@ impl Ty {
506 } 495 }
507 } 496 }
508 497
509 fn from_hir_path_inner( 498 fn lower_path_inner(
510 ctx: &TyLoweringContext<'_>, 499 &self,
511 segment: PathSegment<'_>, 500 segment: PathSegment<'_>,
512 typeable: TyDefId, 501 typeable: TyDefId,
513 infer_args: bool, 502 infer_args: bool,
@@ -517,14 +506,14 @@ impl Ty {
517 TyDefId::AdtId(it) => Some(it.into()), 506 TyDefId::AdtId(it) => Some(it.into()),
518 TyDefId::TypeAliasId(it) => Some(it.into()), 507 TyDefId::TypeAliasId(it) => Some(it.into()),
519 }; 508 };
520 let substs = substs_from_path_segment(ctx, segment, generic_def, infer_args); 509 let substs = self.substs_from_path_segment(segment, generic_def, infer_args);
521 ctx.db.ty(typeable).subst(&substs) 510 self.db.ty(typeable).subst(&substs)
522 } 511 }
523 512
524 /// Collect generic arguments from a path into a `Substs`. See also 513 /// Collect generic arguments from a path into a `Substs`. See also
525 /// `create_substs_for_ast_path` and `def_to_ty` in rustc. 514 /// `create_substs_for_ast_path` and `def_to_ty` in rustc.
526 pub(super) fn substs_from_path( 515 pub(super) fn substs_from_path(
527 ctx: &TyLoweringContext<'_>, 516 &self,
528 path: &Path, 517 path: &Path,
529 // Note that we don't call `db.value_type(resolved)` here, 518 // Note that we don't call `db.value_type(resolved)` here,
530 // `ValueTyDefId` is just a convenient way to pass generics and 519 // `ValueTyDefId` is just a convenient way to pass generics and
@@ -554,145 +543,137 @@ impl Ty {
554 (segment, Some(var.parent.into())) 543 (segment, Some(var.parent.into()))
555 } 544 }
556 }; 545 };
557 substs_from_path_segment(ctx, segment, generic_def, infer_args) 546 self.substs_from_path_segment(segment, generic_def, infer_args)
558 } 547 }
559}
560 548
561fn substs_from_path_segment( 549 fn substs_from_path_segment(
562 ctx: &TyLoweringContext<'_>, 550 &self,
563 segment: PathSegment<'_>, 551 segment: PathSegment<'_>,
564 def_generic: Option<GenericDefId>, 552 def_generic: Option<GenericDefId>,
565 infer_args: bool, 553 infer_args: bool,
566) -> Substs { 554 ) -> Substs {
567 let mut substs = Vec::new(); 555 let mut substs = Vec::new();
568 let def_generics = def_generic.map(|def| generics(ctx.db.upcast(), def)); 556 let def_generics = def_generic.map(|def| generics(self.db.upcast(), def));
569 557
570 let (parent_params, self_params, type_params, impl_trait_params) = 558 let (parent_params, self_params, type_params, impl_trait_params) =
571 def_generics.map_or((0, 0, 0, 0), |g| g.provenance_split()); 559 def_generics.map_or((0, 0, 0, 0), |g| g.provenance_split());
572 let total_len = parent_params + self_params + type_params + impl_trait_params; 560 let total_len = parent_params + self_params + type_params + impl_trait_params;
573 561
574 substs.extend(iter::repeat(TyKind::Unknown.intern(&Interner)).take(parent_params)); 562 substs.extend(iter::repeat(TyKind::Unknown.intern(&Interner)).take(parent_params));
575 563
576 let mut had_explicit_type_args = false; 564 let mut had_explicit_type_args = false;
577 565
578 if let Some(generic_args) = &segment.args_and_bindings { 566 if let Some(generic_args) = &segment.args_and_bindings {
579 if !generic_args.has_self_type { 567 if !generic_args.has_self_type {
580 substs.extend(iter::repeat(TyKind::Unknown.intern(&Interner)).take(self_params)); 568 substs.extend(iter::repeat(TyKind::Unknown.intern(&Interner)).take(self_params));
581 } 569 }
582 let expected_num = 570 let expected_num =
583 if generic_args.has_self_type { self_params + type_params } else { type_params }; 571 if generic_args.has_self_type { self_params + type_params } else { type_params };
584 let skip = if generic_args.has_self_type && self_params == 0 { 1 } else { 0 }; 572 let skip = if generic_args.has_self_type && self_params == 0 { 1 } else { 0 };
585 // if args are provided, it should be all of them, but we can't rely on that 573 // if args are provided, it should be all of them, but we can't rely on that
586 for arg in generic_args 574 for arg in generic_args
587 .args 575 .args
588 .iter() 576 .iter()
589 .filter(|arg| matches!(arg, GenericArg::Type(_))) 577 .filter(|arg| matches!(arg, GenericArg::Type(_)))
590 .skip(skip) 578 .skip(skip)
591 .take(expected_num) 579 .take(expected_num)
592 { 580 {
593 match arg { 581 match arg {
594 GenericArg::Type(type_ref) => { 582 GenericArg::Type(type_ref) => {
595 had_explicit_type_args = true; 583 had_explicit_type_args = true;
596 let ty = Ty::from_hir(ctx, type_ref); 584 let ty = self.lower_ty(type_ref);
597 substs.push(ty); 585 substs.push(ty);
586 }
587 GenericArg::Lifetime(_) => {}
598 } 588 }
599 GenericArg::Lifetime(_) => {}
600 } 589 }
601 } 590 }
602 }
603 591
604 // handle defaults. In expression or pattern path segments without 592 // handle defaults. In expression or pattern path segments without
605 // explicitly specified type arguments, missing type arguments are inferred 593 // explicitly specified type arguments, missing type arguments are inferred
606 // (i.e. defaults aren't used). 594 // (i.e. defaults aren't used).
607 if !infer_args || had_explicit_type_args { 595 if !infer_args || had_explicit_type_args {
608 if let Some(def_generic) = def_generic { 596 if let Some(def_generic) = def_generic {
609 let defaults = ctx.db.generic_defaults(def_generic); 597 let defaults = self.db.generic_defaults(def_generic);
610 assert_eq!(total_len, defaults.len()); 598 assert_eq!(total_len, defaults.len());
611 599
612 for default_ty in defaults.iter().skip(substs.len()) { 600 for default_ty in defaults.iter().skip(substs.len()) {
613 // each default can depend on the previous parameters 601 // each default can depend on the previous parameters
614 let substs_so_far = Substs(substs.clone().into()); 602 let substs_so_far = Substs(substs.clone().into());
615 substs.push(default_ty.clone().subst(&substs_so_far)); 603 substs.push(default_ty.clone().subst(&substs_so_far));
604 }
616 } 605 }
617 } 606 }
618 }
619 607
620 // add placeholders for args that were not provided 608 // add placeholders for args that were not provided
621 // FIXME: emit diagnostics in contexts where this is not allowed 609 // FIXME: emit diagnostics in contexts where this is not allowed
622 for _ in substs.len()..total_len { 610 for _ in substs.len()..total_len {
623 substs.push(TyKind::Unknown.intern(&Interner)); 611 substs.push(TyKind::Unknown.intern(&Interner));
624 } 612 }
625 assert_eq!(substs.len(), total_len); 613 assert_eq!(substs.len(), total_len);
626 614
627 Substs(substs.into()) 615 Substs(substs.into())
628} 616 }
629 617
630impl TraitRef { 618 fn lower_trait_ref_from_path(
631 fn from_path( 619 &self,
632 ctx: &TyLoweringContext<'_>,
633 path: &Path, 620 path: &Path,
634 explicit_self_ty: Option<Ty>, 621 explicit_self_ty: Option<Ty>,
635 ) -> Option<Self> { 622 ) -> Option<TraitRef> {
636 let resolved = 623 let resolved =
637 match ctx.resolver.resolve_path_in_type_ns_fully(ctx.db.upcast(), path.mod_path())? { 624 match self.resolver.resolve_path_in_type_ns_fully(self.db.upcast(), path.mod_path())? {
638 TypeNs::TraitId(tr) => tr, 625 TypeNs::TraitId(tr) => tr,
639 _ => return None, 626 _ => return None,
640 }; 627 };
641 let segment = path.segments().last().expect("path should have at least one segment"); 628 let segment = path.segments().last().expect("path should have at least one segment");
642 Some(TraitRef::from_resolved_path(ctx, resolved, segment, explicit_self_ty)) 629 Some(self.lower_trait_ref_from_resolved_path(resolved, segment, explicit_self_ty))
643 } 630 }
644 631
645 pub(crate) fn from_resolved_path( 632 pub(crate) fn lower_trait_ref_from_resolved_path(
646 ctx: &TyLoweringContext<'_>, 633 &self,
647 resolved: TraitId, 634 resolved: TraitId,
648 segment: PathSegment<'_>, 635 segment: PathSegment<'_>,
649 explicit_self_ty: Option<Ty>, 636 explicit_self_ty: Option<Ty>,
650 ) -> Self { 637 ) -> TraitRef {
651 let mut substs = TraitRef::substs_from_path(ctx, segment, resolved); 638 let mut substs = self.trait_ref_substs_from_path(segment, resolved);
652 if let Some(self_ty) = explicit_self_ty { 639 if let Some(self_ty) = explicit_self_ty {
653 make_mut_slice(&mut substs.0)[0] = self_ty; 640 make_mut_slice(&mut substs.0)[0] = self_ty;
654 } 641 }
655 TraitRef { trait_: resolved, substs } 642 TraitRef { trait_: resolved, substs }
656 } 643 }
657 644
658 fn from_hir( 645 fn lower_trait_ref(
659 ctx: &TyLoweringContext<'_>, 646 &self,
660 type_ref: &TypeRef, 647 type_ref: &TypeRef,
661 explicit_self_ty: Option<Ty>, 648 explicit_self_ty: Option<Ty>,
662 ) -> Option<Self> { 649 ) -> Option<TraitRef> {
663 let path = match type_ref { 650 let path = match type_ref {
664 TypeRef::Path(path) => path, 651 TypeRef::Path(path) => path,
665 _ => return None, 652 _ => return None,
666 }; 653 };
667 TraitRef::from_path(ctx, path, explicit_self_ty) 654 self.lower_trait_ref_from_path(path, explicit_self_ty)
668 } 655 }
669 656
670 fn substs_from_path( 657 fn trait_ref_substs_from_path(&self, segment: PathSegment<'_>, resolved: TraitId) -> Substs {
671 ctx: &TyLoweringContext<'_>, 658 self.substs_from_path_segment(segment, Some(resolved.into()), false)
672 segment: PathSegment<'_>,
673 resolved: TraitId,
674 ) -> Substs {
675 substs_from_path_segment(ctx, segment, Some(resolved.into()), false)
676 } 659 }
677}
678 660
679impl GenericPredicate { 661 pub(crate) fn lower_where_predicate(
680 pub(crate) fn from_where_predicate<'a>( 662 &'a self,
681 ctx: &'a TyLoweringContext<'a>,
682 where_predicate: &'a WherePredicate, 663 where_predicate: &'a WherePredicate,
683 ) -> impl Iterator<Item = GenericPredicate> + 'a { 664 ) -> impl Iterator<Item = GenericPredicate> + 'a {
684 match where_predicate { 665 match where_predicate {
685 WherePredicate::ForLifetime { target, bound, .. } 666 WherePredicate::ForLifetime { target, bound, .. }
686 | WherePredicate::TypeBound { target, bound } => { 667 | WherePredicate::TypeBound { target, bound } => {
687 let self_ty = match target { 668 let self_ty = match target {
688 WherePredicateTypeTarget::TypeRef(type_ref) => Ty::from_hir(ctx, type_ref), 669 WherePredicateTypeTarget::TypeRef(type_ref) => self.lower_ty(type_ref),
689 WherePredicateTypeTarget::TypeParam(param_id) => { 670 WherePredicateTypeTarget::TypeParam(param_id) => {
690 let generic_def = ctx.resolver.generic_def().expect("generics in scope"); 671 let generic_def = self.resolver.generic_def().expect("generics in scope");
691 let generics = generics(ctx.db.upcast(), generic_def); 672 let generics = generics(self.db.upcast(), generic_def);
692 let param_id = 673 let param_id =
693 hir_def::TypeParamId { parent: generic_def, local_id: *param_id }; 674 hir_def::TypeParamId { parent: generic_def, local_id: *param_id };
694 let placeholder = to_placeholder_idx(ctx.db, param_id); 675 let placeholder = to_placeholder_idx(self.db, param_id);
695 match ctx.type_param_mode { 676 match self.type_param_mode {
696 TypeParamLoweringMode::Placeholder => TyKind::Placeholder(placeholder), 677 TypeParamLoweringMode::Placeholder => TyKind::Placeholder(placeholder),
697 TypeParamLoweringMode::Variable => { 678 TypeParamLoweringMode::Variable => {
698 let idx = generics.param_idx(param_id).expect("matching generics"); 679 let idx = generics.param_idx(param_id).expect("matching generics");
@@ -702,23 +683,21 @@ impl GenericPredicate {
702 .intern(&Interner) 683 .intern(&Interner)
703 } 684 }
704 }; 685 };
705 GenericPredicate::from_type_bound(ctx, bound, self_ty) 686 self.lower_type_bound(bound, self_ty).collect::<Vec<_>>().into_iter()
706 .collect::<Vec<_>>()
707 .into_iter()
708 } 687 }
709 WherePredicate::Lifetime { .. } => vec![].into_iter(), 688 WherePredicate::Lifetime { .. } => vec![].into_iter(),
710 } 689 }
711 } 690 }
712 691
713 pub(crate) fn from_type_bound<'a>( 692 pub(crate) fn lower_type_bound(
714 ctx: &'a TyLoweringContext<'a>, 693 &'a self,
715 bound: &'a TypeBound, 694 bound: &'a TypeBound,
716 self_ty: Ty, 695 self_ty: Ty,
717 ) -> impl Iterator<Item = GenericPredicate> + 'a { 696 ) -> impl Iterator<Item = GenericPredicate> + 'a {
718 let mut bindings = None; 697 let mut bindings = None;
719 let trait_ref = match bound { 698 let trait_ref = match bound {
720 TypeBound::Path(path) => { 699 TypeBound::Path(path) => {
721 bindings = TraitRef::from_path(ctx, path, Some(self_ty)); 700 bindings = self.lower_trait_ref_from_path(path, Some(self_ty));
722 Some( 701 Some(
723 bindings.clone().map_or(GenericPredicate::Error, GenericPredicate::Implemented), 702 bindings.clone().map_or(GenericPredicate::Error, GenericPredicate::Implemented),
724 ) 703 )
@@ -729,68 +708,62 @@ impl GenericPredicate {
729 trait_ref.into_iter().chain( 708 trait_ref.into_iter().chain(
730 bindings 709 bindings
731 .into_iter() 710 .into_iter()
732 .flat_map(move |tr| assoc_type_bindings_from_type_bound(ctx, bound, tr)), 711 .flat_map(move |tr| self.assoc_type_bindings_from_type_bound(bound, tr)),
733 ) 712 )
734 } 713 }
735}
736 714
737fn assoc_type_bindings_from_type_bound<'a>( 715 fn assoc_type_bindings_from_type_bound(
738 ctx: &'a TyLoweringContext<'a>, 716 &'a self,
739 bound: &'a TypeBound, 717 bound: &'a TypeBound,
740 trait_ref: TraitRef, 718 trait_ref: TraitRef,
741) -> impl Iterator<Item = GenericPredicate> + 'a { 719 ) -> impl Iterator<Item = GenericPredicate> + 'a {
742 let last_segment = match bound { 720 let last_segment = match bound {
743 TypeBound::Path(path) => path.segments().last(), 721 TypeBound::Path(path) => path.segments().last(),
744 TypeBound::Error | TypeBound::Lifetime(_) => None, 722 TypeBound::Error | TypeBound::Lifetime(_) => None,
745 }; 723 };
746 last_segment 724 last_segment
747 .into_iter() 725 .into_iter()
748 .flat_map(|segment| segment.args_and_bindings.into_iter()) 726 .flat_map(|segment| segment.args_and_bindings.into_iter())
749 .flat_map(|args_and_bindings| args_and_bindings.bindings.iter()) 727 .flat_map(|args_and_bindings| args_and_bindings.bindings.iter())
750 .flat_map(move |binding| { 728 .flat_map(move |binding| {
751 let found = associated_type_by_name_including_super_traits( 729 let found = associated_type_by_name_including_super_traits(
752 ctx.db, 730 self.db,
753 trait_ref.clone(), 731 trait_ref.clone(),
754 &binding.name, 732 &binding.name,
755 ); 733 );
756 let (super_trait_ref, associated_ty) = match found { 734 let (super_trait_ref, associated_ty) = match found {
757 None => return SmallVec::<[GenericPredicate; 1]>::new(), 735 None => return SmallVec::<[GenericPredicate; 1]>::new(),
758 Some(t) => t, 736 Some(t) => t,
759 }; 737 };
760 let projection_ty = ProjectionTy { 738 let projection_ty = ProjectionTy {
761 associated_ty: to_assoc_type_id(associated_ty), 739 associated_ty: to_assoc_type_id(associated_ty),
762 parameters: super_trait_ref.substs, 740 parameters: super_trait_ref.substs,
763 }; 741 };
764 let mut preds = SmallVec::with_capacity( 742 let mut preds = SmallVec::with_capacity(
765 binding.type_ref.as_ref().map_or(0, |_| 1) + binding.bounds.len(), 743 binding.type_ref.as_ref().map_or(0, |_| 1) + binding.bounds.len(),
766 ); 744 );
767 if let Some(type_ref) = &binding.type_ref { 745 if let Some(type_ref) = &binding.type_ref {
768 let ty = Ty::from_hir(ctx, type_ref); 746 let ty = self.lower_ty(type_ref);
769 let projection_predicate = 747 let projection_predicate =
770 ProjectionPredicate { projection_ty: projection_ty.clone(), ty }; 748 ProjectionPredicate { projection_ty: projection_ty.clone(), ty };
771 preds.push(GenericPredicate::Projection(projection_predicate)); 749 preds.push(GenericPredicate::Projection(projection_predicate));
772 } 750 }
773 for bound in &binding.bounds { 751 for bound in &binding.bounds {
774 preds.extend(GenericPredicate::from_type_bound( 752 preds.extend(self.lower_type_bound(
775 ctx, 753 bound,
776 bound, 754 TyKind::Alias(AliasTy::Projection(projection_ty.clone())).intern(&Interner),
777 TyKind::Alias(AliasTy::Projection(projection_ty.clone())).intern(&Interner), 755 ));
778 )); 756 }
779 } 757 preds
780 preds 758 })
781 }) 759 }
782}
783 760
784impl ReturnTypeImplTrait { 761 fn lower_impl_trait(&self, bounds: &[TypeBound]) -> ReturnTypeImplTrait {
785 fn from_hir(ctx: &TyLoweringContext, bounds: &[TypeBound]) -> Self {
786 cov_mark::hit!(lower_rpit); 762 cov_mark::hit!(lower_rpit);
787 let self_ty = 763 let self_ty =
788 TyKind::BoundVar(BoundVar::new(DebruijnIndex::INNERMOST, 0)).intern(&Interner); 764 TyKind::BoundVar(BoundVar::new(DebruijnIndex::INNERMOST, 0)).intern(&Interner);
789 let predicates = ctx.with_shifted_in(DebruijnIndex::ONE, |ctx| { 765 let predicates = self.with_shifted_in(DebruijnIndex::ONE, |ctx| {
790 bounds 766 bounds.iter().flat_map(|b| ctx.lower_type_bound(b, self_ty.clone())).collect()
791 .iter()
792 .flat_map(|b| GenericPredicate::from_type_bound(ctx, b, self_ty.clone()))
793 .collect()
794 }); 767 });
795 ReturnTypeImplTrait { bounds: Binders::new(1, predicates) } 768 ReturnTypeImplTrait { bounds: Binders::new(1, predicates) }
796 } 769 }
@@ -886,7 +859,7 @@ pub(crate) fn field_types_query(
886 let ctx = 859 let ctx =
887 TyLoweringContext::new(db, &resolver).with_type_param_mode(TypeParamLoweringMode::Variable); 860 TyLoweringContext::new(db, &resolver).with_type_param_mode(TypeParamLoweringMode::Variable);
888 for (field_id, field_data) in var_data.fields().iter() { 861 for (field_id, field_data) in var_data.fields().iter() {
889 res.insert(field_id, Binders::new(generics.len(), Ty::from_hir(&ctx, &field_data.type_ref))) 862 res.insert(field_id, Binders::new(generics.len(), ctx.lower_ty(&field_data.type_ref)))
890 } 863 }
891 Arc::new(res) 864 Arc::new(res)
892} 865}
@@ -914,16 +887,13 @@ pub(crate) fn generic_predicates_for_param_query(
914 WherePredicate::ForLifetime { target, .. } 887 WherePredicate::ForLifetime { target, .. }
915 | WherePredicate::TypeBound { target, .. } => match target { 888 | WherePredicate::TypeBound { target, .. } => match target {
916 WherePredicateTypeTarget::TypeRef(type_ref) => { 889 WherePredicateTypeTarget::TypeRef(type_ref) => {
917 Ty::from_hir_only_param(&ctx, type_ref) == Some(param_id) 890 ctx.lower_ty_only_param(type_ref) == Some(param_id)
918 } 891 }
919 WherePredicateTypeTarget::TypeParam(local_id) => *local_id == param_id.local_id, 892 WherePredicateTypeTarget::TypeParam(local_id) => *local_id == param_id.local_id,
920 }, 893 },
921 WherePredicate::Lifetime { .. } => false, 894 WherePredicate::Lifetime { .. } => false,
922 }) 895 })
923 .flat_map(|pred| { 896 .flat_map(|pred| ctx.lower_where_predicate(pred).map(|p| Binders::new(generics.len(), p)))
924 GenericPredicate::from_where_predicate(&ctx, pred)
925 .map(|p| Binders::new(generics.len(), p))
926 })
927 .collect() 897 .collect()
928} 898}
929 899
@@ -945,7 +915,7 @@ pub(crate) fn trait_environment_query(
945 let mut traits_in_scope = Vec::new(); 915 let mut traits_in_scope = Vec::new();
946 let mut clauses = Vec::new(); 916 let mut clauses = Vec::new();
947 for pred in resolver.where_predicates_in_scope() { 917 for pred in resolver.where_predicates_in_scope() {
948 for pred in GenericPredicate::from_where_predicate(&ctx, pred) { 918 for pred in ctx.lower_where_predicate(pred) {
949 if pred.is_error() { 919 if pred.is_error() {
950 continue; 920 continue;
951 } 921 }
@@ -997,10 +967,7 @@ pub(crate) fn generic_predicates_query(
997 let generics = generics(db.upcast(), def); 967 let generics = generics(db.upcast(), def);
998 resolver 968 resolver
999 .where_predicates_in_scope() 969 .where_predicates_in_scope()
1000 .flat_map(|pred| { 970 .flat_map(|pred| ctx.lower_where_predicate(pred).map(|p| Binders::new(generics.len(), p)))
1001 GenericPredicate::from_where_predicate(&ctx, pred)
1002 .map(|p| Binders::new(generics.len(), p))
1003 })
1004 .collect() 971 .collect()
1005} 972}
1006 973
@@ -1018,10 +985,8 @@ pub(crate) fn generic_defaults_query(
1018 .iter() 985 .iter()
1019 .enumerate() 986 .enumerate()
1020 .map(|(idx, (_, p))| { 987 .map(|(idx, (_, p))| {
1021 let mut ty = p 988 let mut ty =
1022 .default 989 p.default.as_ref().map_or(TyKind::Unknown.intern(&Interner), |t| ctx.lower_ty(t));
1023 .as_ref()
1024 .map_or(TyKind::Unknown.intern(&Interner), |t| Ty::from_hir(&ctx, t));
1025 990
1026 // Each default can only refer to previous parameters. 991 // Each default can only refer to previous parameters.
1027 ty.walk_mut_binders( 992 ty.walk_mut_binders(
@@ -1052,11 +1017,11 @@ fn fn_sig_for_fn(db: &dyn HirDatabase, def: FunctionId) -> PolyFnSig {
1052 let ctx_params = TyLoweringContext::new(db, &resolver) 1017 let ctx_params = TyLoweringContext::new(db, &resolver)
1053 .with_impl_trait_mode(ImplTraitLoweringMode::Variable) 1018 .with_impl_trait_mode(ImplTraitLoweringMode::Variable)
1054 .with_type_param_mode(TypeParamLoweringMode::Variable); 1019 .with_type_param_mode(TypeParamLoweringMode::Variable);
1055 let params = data.params.iter().map(|tr| Ty::from_hir(&ctx_params, tr)).collect::<Vec<_>>(); 1020 let params = data.params.iter().map(|tr| (&ctx_params).lower_ty(tr)).collect::<Vec<_>>();
1056 let ctx_ret = TyLoweringContext::new(db, &resolver) 1021 let ctx_ret = TyLoweringContext::new(db, &resolver)
1057 .with_impl_trait_mode(ImplTraitLoweringMode::Opaque) 1022 .with_impl_trait_mode(ImplTraitLoweringMode::Opaque)
1058 .with_type_param_mode(TypeParamLoweringMode::Variable); 1023 .with_type_param_mode(TypeParamLoweringMode::Variable);
1059 let ret = Ty::from_hir(&ctx_ret, &data.ret_type); 1024 let ret = (&ctx_ret).lower_ty(&data.ret_type);
1060 let generics = generics(db.upcast(), def.into()); 1025 let generics = generics(db.upcast(), def.into());
1061 let num_binders = generics.len(); 1026 let num_binders = generics.len();
1062 Binders::new(num_binders, CallableSig::from_params_and_return(params, ret, data.is_varargs)) 1027 Binders::new(num_binders, CallableSig::from_params_and_return(params, ret, data.is_varargs))
@@ -1081,7 +1046,7 @@ fn type_for_const(db: &dyn HirDatabase, def: ConstId) -> Binders<Ty> {
1081 let ctx = 1046 let ctx =
1082 TyLoweringContext::new(db, &resolver).with_type_param_mode(TypeParamLoweringMode::Variable); 1047 TyLoweringContext::new(db, &resolver).with_type_param_mode(TypeParamLoweringMode::Variable);
1083 1048
1084 Binders::new(generics.len(), Ty::from_hir(&ctx, &data.type_ref)) 1049 Binders::new(generics.len(), ctx.lower_ty(&data.type_ref))
1085} 1050}
1086 1051
1087/// Build the declared type of a static. 1052/// Build the declared type of a static.
@@ -1090,7 +1055,7 @@ fn type_for_static(db: &dyn HirDatabase, def: StaticId) -> Binders<Ty> {
1090 let resolver = def.resolver(db.upcast()); 1055 let resolver = def.resolver(db.upcast());
1091 let ctx = TyLoweringContext::new(db, &resolver); 1056 let ctx = TyLoweringContext::new(db, &resolver);
1092 1057
1093 Binders::new(0, Ty::from_hir(&ctx, &data.type_ref)) 1058 Binders::new(0, ctx.lower_ty(&data.type_ref))
1094} 1059}
1095 1060
1096fn fn_sig_for_struct_constructor(db: &dyn HirDatabase, def: StructId) -> PolyFnSig { 1061fn fn_sig_for_struct_constructor(db: &dyn HirDatabase, def: StructId) -> PolyFnSig {
@@ -1099,8 +1064,7 @@ fn fn_sig_for_struct_constructor(db: &dyn HirDatabase, def: StructId) -> PolyFnS
1099 let resolver = def.resolver(db.upcast()); 1064 let resolver = def.resolver(db.upcast());
1100 let ctx = 1065 let ctx =
1101 TyLoweringContext::new(db, &resolver).with_type_param_mode(TypeParamLoweringMode::Variable); 1066 TyLoweringContext::new(db, &resolver).with_type_param_mode(TypeParamLoweringMode::Variable);
1102 let params = 1067 let params = fields.iter().map(|(_, field)| ctx.lower_ty(&field.type_ref)).collect::<Vec<_>>();
1103 fields.iter().map(|(_, field)| Ty::from_hir(&ctx, &field.type_ref)).collect::<Vec<_>>();
1104 let ret = type_for_adt(db, def.into()); 1068 let ret = type_for_adt(db, def.into());
1105 Binders::new(ret.num_binders, CallableSig::from_params_and_return(params, ret.value, false)) 1069 Binders::new(ret.num_binders, CallableSig::from_params_and_return(params, ret.value, false))
1106} 1070}
@@ -1126,8 +1090,7 @@ fn fn_sig_for_enum_variant_constructor(db: &dyn HirDatabase, def: EnumVariantId)
1126 let resolver = def.parent.resolver(db.upcast()); 1090 let resolver = def.parent.resolver(db.upcast());
1127 let ctx = 1091 let ctx =
1128 TyLoweringContext::new(db, &resolver).with_type_param_mode(TypeParamLoweringMode::Variable); 1092 TyLoweringContext::new(db, &resolver).with_type_param_mode(TypeParamLoweringMode::Variable);
1129 let params = 1093 let params = fields.iter().map(|(_, field)| ctx.lower_ty(&field.type_ref)).collect::<Vec<_>>();
1130 fields.iter().map(|(_, field)| Ty::from_hir(&ctx, &field.type_ref)).collect::<Vec<_>>();
1131 let ret = type_for_adt(db, def.parent.into()); 1094 let ret = type_for_adt(db, def.parent.into());
1132 Binders::new(ret.num_binders, CallableSig::from_params_and_return(params, ret.value, false)) 1095 Binders::new(ret.num_binders, CallableSig::from_params_and_return(params, ret.value, false))
1133} 1096}
@@ -1163,7 +1126,7 @@ fn type_for_type_alias(db: &dyn HirDatabase, t: TypeAliasId) -> Binders<Ty> {
1163 } else { 1126 } else {
1164 let substs = Substs::bound_vars(&generics, DebruijnIndex::INNERMOST); 1127 let substs = Substs::bound_vars(&generics, DebruijnIndex::INNERMOST);
1165 let type_ref = &db.type_alias_data(t).type_ref; 1128 let type_ref = &db.type_alias_data(t).type_ref;
1166 let inner = Ty::from_hir(&ctx, type_ref.as_ref().unwrap_or(&TypeRef::Error)); 1129 let inner = ctx.lower_ty(type_ref.as_ref().unwrap_or(&TypeRef::Error));
1167 Binders::new(substs.len(), inner) 1130 Binders::new(substs.len(), inner)
1168 } 1131 }
1169} 1132}
@@ -1255,7 +1218,7 @@ pub(crate) fn impl_self_ty_query(db: &dyn HirDatabase, impl_id: ImplId) -> Binde
1255 let generics = generics(db.upcast(), impl_id.into()); 1218 let generics = generics(db.upcast(), impl_id.into());
1256 let ctx = 1219 let ctx =
1257 TyLoweringContext::new(db, &resolver).with_type_param_mode(TypeParamLoweringMode::Variable); 1220 TyLoweringContext::new(db, &resolver).with_type_param_mode(TypeParamLoweringMode::Variable);
1258 Binders::new(generics.len(), Ty::from_hir(&ctx, &impl_data.target_type)) 1221 Binders::new(generics.len(), ctx.lower_ty(&impl_data.target_type))
1259} 1222}
1260 1223
1261pub(crate) fn const_param_ty_query(db: &dyn HirDatabase, def: ConstParamId) -> Ty { 1224pub(crate) fn const_param_ty_query(db: &dyn HirDatabase, def: ConstParamId) -> Ty {
@@ -1264,7 +1227,7 @@ pub(crate) fn const_param_ty_query(db: &dyn HirDatabase, def: ConstParamId) -> T
1264 let resolver = def.parent.resolver(db.upcast()); 1227 let resolver = def.parent.resolver(db.upcast());
1265 let ctx = TyLoweringContext::new(db, &resolver); 1228 let ctx = TyLoweringContext::new(db, &resolver);
1266 1229
1267 Ty::from_hir(&ctx, &data.ty) 1230 ctx.lower_ty(&data.ty)
1268} 1231}
1269 1232
1270pub(crate) fn impl_self_ty_recover( 1233pub(crate) fn impl_self_ty_recover(
@@ -1283,10 +1246,7 @@ pub(crate) fn impl_trait_query(db: &dyn HirDatabase, impl_id: ImplId) -> Option<
1283 TyLoweringContext::new(db, &resolver).with_type_param_mode(TypeParamLoweringMode::Variable); 1246 TyLoweringContext::new(db, &resolver).with_type_param_mode(TypeParamLoweringMode::Variable);
1284 let self_ty = db.impl_self_ty(impl_id); 1247 let self_ty = db.impl_self_ty(impl_id);
1285 let target_trait = impl_data.target_trait.as_ref()?; 1248 let target_trait = impl_data.target_trait.as_ref()?;
1286 Some(Binders::new( 1249 Some(Binders::new(self_ty.num_binders, ctx.lower_trait_ref(target_trait, Some(self_ty.value))?))
1287 self_ty.num_binders,
1288 TraitRef::from_hir(&ctx, target_trait, Some(self_ty.value))?,
1289 ))
1290} 1250}
1291 1251
1292pub(crate) fn return_type_impl_traits( 1252pub(crate) fn return_type_impl_traits(
@@ -1299,7 +1259,7 @@ pub(crate) fn return_type_impl_traits(
1299 let ctx_ret = TyLoweringContext::new(db, &resolver) 1259 let ctx_ret = TyLoweringContext::new(db, &resolver)
1300 .with_impl_trait_mode(ImplTraitLoweringMode::Opaque) 1260 .with_impl_trait_mode(ImplTraitLoweringMode::Opaque)
1301 .with_type_param_mode(TypeParamLoweringMode::Variable); 1261 .with_type_param_mode(TypeParamLoweringMode::Variable);
1302 let _ret = Ty::from_hir(&ctx_ret, &data.ret_type); 1262 let _ret = (&ctx_ret).lower_ty(&data.ret_type);
1303 let generics = generics(db.upcast(), def.into()); 1263 let generics = generics(db.upcast(), def.into());
1304 let num_binders = generics.len(); 1264 let num_binders = generics.len();
1305 let return_type_impl_traits = 1265 let return_type_impl_traits =
diff --git a/crates/hir_ty/src/traits/chalk.rs b/crates/hir_ty/src/traits/chalk.rs
index 1f3e1c07a..ef1e6b2df 100644
--- a/crates/hir_ty/src/traits/chalk.rs
+++ b/crates/hir_ty/src/traits/chalk.rs
@@ -401,7 +401,7 @@ pub(crate) fn associated_ty_data_query(
401 let bounds = type_alias_data 401 let bounds = type_alias_data
402 .bounds 402 .bounds
403 .iter() 403 .iter()
404 .flat_map(|bound| GenericPredicate::from_type_bound(&ctx, bound, self_ty.clone())) 404 .flat_map(|bound| ctx.lower_type_bound(bound, self_ty.clone()))
405 .filter_map(|pred| generic_predicate_to_inline_bound(db, &pred, &self_ty)) 405 .filter_map(|pred| generic_predicate_to_inline_bound(db, &pred, &self_ty))
406 .map(|bound| make_binders(bound.shifted_in(&Interner), 0)) 406 .map(|bound| make_binders(bound.shifted_in(&Interner), 0))
407 .collect(); 407 .collect();