aboutsummaryrefslogtreecommitdiff
path: root/crates/hir_ty/src/infer/unify.rs
diff options
context:
space:
mode:
Diffstat (limited to 'crates/hir_ty/src/infer/unify.rs')
-rw-r--r--crates/hir_ty/src/infer/unify.rs39
1 files changed, 3 insertions, 36 deletions
diff --git a/crates/hir_ty/src/infer/unify.rs b/crates/hir_ty/src/infer/unify.rs
index 278127c69..539e12420 100644
--- a/crates/hir_ty/src/infer/unify.rs
+++ b/crates/hir_ty/src/infer/unify.rs
@@ -24,6 +24,9 @@ impl<'a> InferenceContext<'a> {
24 where 24 where
25 T::Result: HasInterner<Interner = Interner>, 25 T::Result: HasInterner<Interner = Interner>,
26 { 26 {
27 // try to resolve obligations before canonicalizing, since this might
28 // result in new knowledge about variables
29 self.resolve_obligations_as_possible();
27 self.table.canonicalize(t) 30 self.table.canonicalize(t)
28 } 31 }
29} 32}
@@ -216,7 +219,6 @@ impl<'a> InferenceTable<'a> {
216 /// call). `make_ty` handles this already, but e.g. for field types we need 219 /// call). `make_ty` handles this already, but e.g. for field types we need
217 /// to do it as well. 220 /// to do it as well.
218 pub(super) fn normalize_associated_types_in(&mut self, ty: Ty) -> Ty { 221 pub(super) fn normalize_associated_types_in(&mut self, ty: Ty) -> Ty {
219 let ty = self.resolve_ty_as_possible(ty);
220 fold_tys( 222 fold_tys(
221 ty, 223 ty,
222 |ty, _| match ty.kind(&Interner) { 224 |ty, _| match ty.kind(&Interner) {
@@ -302,11 +304,6 @@ impl<'a> InferenceTable<'a> {
302 self.resolve_with_fallback(ty, |_, _, d, _| d) 304 self.resolve_with_fallback(ty, |_, _, d, _| d)
303 } 305 }
304 306
305 // FIXME get rid of this, instead resolve shallowly where necessary
306 pub(crate) fn resolve_ty_as_possible(&mut self, ty: Ty) -> Ty {
307 self.resolve_ty_as_possible_inner(&mut Vec::new(), ty)
308 }
309
310 /// Unify two types and register new trait goals that arise from that. 307 /// Unify two types and register new trait goals that arise from that.
311 // TODO give these two functions better names 308 // TODO give these two functions better names
312 pub(crate) fn unify(&mut self, ty1: &Ty, ty2: &Ty) -> bool { 309 pub(crate) fn unify(&mut self, ty1: &Ty, ty2: &Ty) -> bool {
@@ -344,36 +341,6 @@ impl<'a> InferenceTable<'a> {
344 self.var_unification_table.normalize_ty_shallow(&Interner, ty).unwrap_or_else(|| ty.clone()) 341 self.var_unification_table.normalize_ty_shallow(&Interner, ty).unwrap_or_else(|| ty.clone())
345 } 342 }
346 343
347 /// Resolves the type as far as currently possible, replacing type variables
348 /// by their known types.
349 fn resolve_ty_as_possible_inner(&mut self, tv_stack: &mut Vec<InferenceVar>, ty: Ty) -> Ty {
350 fold_tys(
351 ty,
352 |ty, _| match ty.kind(&Interner) {
353 &TyKind::InferenceVar(tv, kind) => {
354 if tv_stack.contains(&tv) {
355 // recursive type
356 return self.type_variable_table.fallback_value(tv, kind);
357 }
358 if let Some(known_ty) = self.var_unification_table.probe_var(tv) {
359 // known_ty may contain other variables that are known by now
360 tv_stack.push(tv);
361 let result = self.resolve_ty_as_possible_inner(
362 tv_stack,
363 known_ty.assert_ty_ref(&Interner).clone(),
364 );
365 tv_stack.pop();
366 result
367 } else {
368 ty
369 }
370 }
371 _ => ty,
372 },
373 DebruijnIndex::INNERMOST,
374 )
375 }
376
377 pub fn register_obligation(&mut self, goal: Goal) { 344 pub fn register_obligation(&mut self, goal: Goal) {
378 let in_env = InEnvironment::new(&self.trait_env.env, goal); 345 let in_env = InEnvironment::new(&self.trait_env.env, goal);
379 self.register_obligation_in_env(in_env) 346 self.register_obligation_in_env(in_env)