aboutsummaryrefslogtreecommitdiff
path: root/crates/ra_hir_ty/src/infer/unify.rs
diff options
context:
space:
mode:
Diffstat (limited to 'crates/ra_hir_ty/src/infer/unify.rs')
-rw-r--r--crates/ra_hir_ty/src/infer/unify.rs28
1 files changed, 17 insertions, 11 deletions
diff --git a/crates/ra_hir_ty/src/infer/unify.rs b/crates/ra_hir_ty/src/infer/unify.rs
index 0bf8fbd63..ac25f8a80 100644
--- a/crates/ra_hir_ty/src/infer/unify.rs
+++ b/crates/ra_hir_ty/src/infer/unify.rs
@@ -7,7 +7,9 @@ use ena::unify::{InPlaceUnificationTable, NoError, UnifyKey, UnifyValue};
7use test_utils::tested_by; 7use test_utils::tested_by;
8 8
9use super::{InferenceContext, Obligation}; 9use super::{InferenceContext, Obligation};
10use crate::{Canonical, InEnvironment, InferTy, Substs, Ty, TypeCtor, TypeWalk}; 10use crate::{
11 BoundVar, Canonical, DebruijnIndex, InEnvironment, InferTy, Substs, Ty, TypeCtor, TypeWalk,
12};
11 13
12impl<'a> InferenceContext<'a> { 14impl<'a> InferenceContext<'a> {
13 pub(super) fn canonicalizer<'b>(&'b mut self) -> Canonicalizer<'a, 'b> 15 pub(super) fn canonicalizer<'b>(&'b mut self) -> Canonicalizer<'a, 'b>
@@ -47,7 +49,7 @@ where
47 }) 49 })
48 } 50 }
49 51
50 fn do_canonicalize<T: TypeWalk>(&mut self, t: T, binders: usize) -> T { 52 fn do_canonicalize<T: TypeWalk>(&mut self, t: T, binders: DebruijnIndex) -> T {
51 t.fold_binders( 53 t.fold_binders(
52 &mut |ty, binders| match ty { 54 &mut |ty, binders| match ty {
53 Ty::Infer(tv) => { 55 Ty::Infer(tv) => {
@@ -72,7 +74,7 @@ where
72 InferTy::MaybeNeverTypeVar(_) => InferTy::MaybeNeverTypeVar(root), 74 InferTy::MaybeNeverTypeVar(_) => InferTy::MaybeNeverTypeVar(root),
73 }; 75 };
74 let position = self.add(free_var); 76 let position = self.add(free_var);
75 Ty::Bound((position + binders) as u32) 77 Ty::Bound(BoundVar::new(binders, position))
76 } 78 }
77 } 79 }
78 _ => ty, 80 _ => ty,
@@ -89,7 +91,7 @@ where
89 } 91 }
90 92
91 pub(crate) fn canonicalize_ty(mut self, ty: Ty) -> Canonicalized<Ty> { 93 pub(crate) fn canonicalize_ty(mut self, ty: Ty) -> Canonicalized<Ty> {
92 let result = self.do_canonicalize(ty, 0); 94 let result = self.do_canonicalize(ty, DebruijnIndex::INNERMOST);
93 self.into_canonicalized(result) 95 self.into_canonicalized(result)
94 } 96 }
95 97
@@ -98,8 +100,12 @@ where
98 obligation: InEnvironment<Obligation>, 100 obligation: InEnvironment<Obligation>,
99 ) -> Canonicalized<InEnvironment<Obligation>> { 101 ) -> Canonicalized<InEnvironment<Obligation>> {
100 let result = match obligation.value { 102 let result = match obligation.value {
101 Obligation::Trait(tr) => Obligation::Trait(self.do_canonicalize(tr, 0)), 103 Obligation::Trait(tr) => {
102 Obligation::Projection(pr) => Obligation::Projection(self.do_canonicalize(pr, 0)), 104 Obligation::Trait(self.do_canonicalize(tr, DebruijnIndex::INNERMOST))
105 }
106 Obligation::Projection(pr) => {
107 Obligation::Projection(self.do_canonicalize(pr, DebruijnIndex::INNERMOST))
108 }
103 }; 109 };
104 self.into_canonicalized(InEnvironment { 110 self.into_canonicalized(InEnvironment {
105 value: result, 111 value: result,
@@ -112,13 +118,13 @@ impl<T> Canonicalized<T> {
112 pub fn decanonicalize_ty(&self, mut ty: Ty) -> Ty { 118 pub fn decanonicalize_ty(&self, mut ty: Ty) -> Ty {
113 ty.walk_mut_binders( 119 ty.walk_mut_binders(
114 &mut |ty, binders| { 120 &mut |ty, binders| {
115 if let &mut Ty::Bound(idx) = ty { 121 if let &mut Ty::Bound(bound) = ty {
116 if idx as usize >= binders && (idx as usize - binders) < self.free_vars.len() { 122 if bound.debruijn >= binders {
117 *ty = Ty::Infer(self.free_vars[idx as usize - binders]); 123 *ty = Ty::Infer(self.free_vars[bound.index]);
118 } 124 }
119 } 125 }
120 }, 126 },
121 0, 127 DebruijnIndex::INNERMOST,
122 ); 128 );
123 ty 129 ty
124 } 130 }
@@ -150,7 +156,7 @@ pub fn unify(ty1: &Canonical<Ty>, ty2: &Canonical<Ty>) -> Option<Substs> {
150 // (kind of hacky) 156 // (kind of hacky)
151 for (i, var) in vars.iter().enumerate() { 157 for (i, var) in vars.iter().enumerate() {
152 if &*table.resolve_ty_shallow(var) == var { 158 if &*table.resolve_ty_shallow(var) == var {
153 table.unify(var, &Ty::Bound(i as u32)); 159 table.unify(var, &Ty::Bound(BoundVar::new(DebruijnIndex::INNERMOST, i)));
154 } 160 }
155 } 161 }
156 Some( 162 Some(