about summary refs log tree commit diff
diff options
context:
space:
mode:
authordfireBird <me@dfirebird.dev>2024-03-19 10:14:45 +0530
committerdfireBird <me@dfirebird.dev>2024-03-19 10:14:45 +0530
commitb357bcab2beb3533d3059b4c8723e4729a4333e2 (patch)
treec69eed0abbcde25c655bf512b84439adc2a585b6
parent13301e7a1ae26214a038a6c344df9d85b895b540 (diff)
downloadrust-b357bcab2beb3533d3059b4c8723e4729a4333e2.tar.gz
rust-b357bcab2beb3533d3059b4c8723e4729a4333e2.zip
modify `insert_type_vars` for lifetimes
-rw-r--r--crates/hir-ty/src/infer.rs8
-rw-r--r--crates/hir-ty/src/infer/expr.rs3
-rw-r--r--crates/hir-ty/src/infer/unify.rs25
-rw-r--r--crates/hir-ty/src/lib.rs49
-rw-r--r--crates/hir-ty/src/lower.rs2
5 files changed, 73 insertions, 14 deletions
diff --git a/crates/hir-ty/src/infer.rs b/crates/hir-ty/src/infer.rs
index 29e12799451..be3b50e1411 100644
--- a/crates/hir-ty/src/infer.rs
+++ b/crates/hir-ty/src/infer.rs
@@ -42,7 +42,7 @@ use hir_def::{
     layout::Integer,
     path::{ModPath, Path},
     resolver::{HasResolver, ResolveValueResult, Resolver, TypeNs, ValueNs},
-    type_ref::TypeRef,
+    type_ref::{LifetimeRef, TypeRef},
     AdtId, AssocItemId, DefWithBodyId, FieldId, FunctionId, ItemContainerId, Lookup, TraitId,
     TupleFieldId, TupleId, TypeAliasId, VariantId,
 };
@@ -1037,6 +1037,12 @@ impl<'a> InferenceContext<'a> {
         self.result.standard_types.unknown.clone()
     }
 
+    fn make_lifetime(&mut self, lifetime_ref: &LifetimeRef) -> Lifetime {
+        let ctx = crate::lower::TyLoweringContext::new(self.db, &self.resolver, self.owner.into());
+        let lt = ctx.lower_lifetime(lifetime_ref);
+        self.insert_type_vars(lt)
+    }
+
     /// Replaces `Ty::Error` by a new type var, so we can maybe still infer it.
     fn insert_type_vars_shallow(&mut self, ty: Ty) -> Ty {
         self.table.insert_type_vars_shallow(ty)
diff --git a/crates/hir-ty/src/infer/expr.rs b/crates/hir-ty/src/infer/expr.rs
index aab052fdf16..35d59679355 100644
--- a/crates/hir-ty/src/infer/expr.rs
+++ b/crates/hir-ty/src/infer/expr.rs
@@ -1855,8 +1855,7 @@ impl InferenceContext<'_> {
                             DebruijnIndex::INNERMOST,
                         )
                     },
-                    // FIXME: create make_lifetimes and infer lifetimes
-                    |_, _| static_lifetime(),
+                    |this, lt_ref| this.make_lifetime(lt_ref),
                 ) {
                     substs.push(g);
                 }
diff --git a/crates/hir-ty/src/infer/unify.rs b/crates/hir-ty/src/infer/unify.rs
index a6c5666911a..afb89fe1e5b 100644
--- a/crates/hir-ty/src/infer/unify.rs
+++ b/crates/hir-ty/src/infer/unify.rs
@@ -16,12 +16,12 @@ use triomphe::Arc;
 
 use super::{InferOk, InferResult, InferenceContext, TypeError};
 use crate::{
-    consteval::unknown_const, db::HirDatabase, fold_tys_and_consts, static_lifetime,
-    to_chalk_trait_id, traits::FnTrait, AliasEq, AliasTy, BoundVar, Canonical, Const, ConstValue,
-    DebruijnIndex, DomainGoal, GenericArg, GenericArgData, Goal, GoalData, Guidance, InEnvironment,
-    InferenceVar, Interner, Lifetime, OpaqueTyId, ParamKind, ProjectionTy, ProjectionTyExt, Scalar,
-    Solution, Substitution, TraitEnvironment, Ty, TyBuilder, TyExt, TyKind, VariableKind,
-    WhereClause,
+    consteval::unknown_const, db::HirDatabase, fold_generic_args, fold_tys_and_consts,
+    static_lifetime, to_chalk_trait_id, traits::FnTrait, AliasEq, AliasTy, BoundVar, Canonical,
+    Const, ConstValue, DebruijnIndex, DomainGoal, GenericArg, GenericArgData, Goal, GoalData,
+    Guidance, InEnvironment, InferenceVar, Interner, Lifetime, OpaqueTyId, ParamKind, ProjectionTy,
+    ProjectionTyExt, Scalar, Solution, Substitution, TraitEnvironment, Ty, TyBuilder, TyExt,
+    TyKind, VariableKind, WhereClause,
 };
 
 impl InferenceContext<'_> {
@@ -862,11 +862,16 @@ impl<'a> InferenceTable<'a> {
     where
         T: HasInterner<Interner = Interner> + TypeFoldable<Interner>,
     {
-        fold_tys_and_consts(
+        fold_generic_args(
             ty,
-            |it, _| match it {
-                Either::Left(ty) => Either::Left(self.insert_type_vars_shallow(ty)),
-                Either::Right(c) => Either::Right(self.insert_const_vars_shallow(c)),
+            |arg, _| match arg {
+                GenericArgData::Ty(ty) => GenericArgData::Ty(self.insert_type_vars_shallow(ty)),
+                // FIXME: insert lifetime vars once LifetimeData::InferenceVar
+                // and specific error variant for lifetimes start being constructed
+                GenericArgData::Lifetime(lt) => GenericArgData::Lifetime(lt),
+                GenericArgData::Const(c) => {
+                    GenericArgData::Const(self.insert_const_vars_shallow(c))
+                }
             },
             DebruijnIndex::INNERMOST,
         )
diff --git a/crates/hir-ty/src/lib.rs b/crates/hir-ty/src/lib.rs
index fc7ed79f5cf..e217cf3d09d 100644
--- a/crates/hir-ty/src/lib.rs
+++ b/crates/hir-ty/src/lib.rs
@@ -716,6 +716,55 @@ pub(crate) fn fold_tys_and_consts<T: HasInterner<Interner = Interner> + TypeFold
     t.fold_with(&mut TyFolder(f), binders)
 }
 
+pub(crate) fn fold_generic_args<T: HasInterner<Interner = Interner> + TypeFoldable<Interner>>(
+    t: T,
+    f: impl FnMut(GenericArgData, DebruijnIndex) -> GenericArgData,
+    binders: DebruijnIndex,
+) -> T {
+    use chalk_ir::fold::{TypeFolder, TypeSuperFoldable};
+    #[derive(chalk_derive::FallibleTypeFolder)]
+    #[has_interner(Interner)]
+    struct TyFolder<F: FnMut(GenericArgData, DebruijnIndex) -> GenericArgData>(F);
+    impl<F: FnMut(GenericArgData, DebruijnIndex) -> GenericArgData> TypeFolder<Interner>
+        for TyFolder<F>
+    {
+        fn as_dyn(&mut self) -> &mut dyn TypeFolder<Interner> {
+            self
+        }
+
+        fn interner(&self) -> Interner {
+            Interner
+        }
+
+        fn fold_ty(&mut self, ty: Ty, outer_binder: DebruijnIndex) -> Ty {
+            let ty = ty.super_fold_with(self.as_dyn(), outer_binder);
+            self.0(GenericArgData::Ty(ty), outer_binder)
+                .intern(Interner)
+                .ty(Interner)
+                .unwrap()
+                .clone()
+        }
+
+        fn fold_const(&mut self, c: Const, outer_binder: DebruijnIndex) -> Const {
+            self.0(GenericArgData::Const(c), outer_binder)
+                .intern(Interner)
+                .constant(Interner)
+                .unwrap()
+                .clone()
+        }
+
+        fn fold_lifetime(&mut self, lt: Lifetime, outer_binder: DebruijnIndex) -> Lifetime {
+            let lt = lt.super_fold_with(self.as_dyn(), outer_binder);
+            self.0(GenericArgData::Lifetime(lt), outer_binder)
+                .intern(Interner)
+                .lifetime(Interner)
+                .unwrap()
+                .clone()
+        }
+    }
+    t.fold_with(&mut TyFolder(f), binders)
+}
+
 /// 'Canonicalizes' the `t` by replacing any errors with new variables. Also
 /// ensures there are no unbound variables or inference variables anywhere in
 /// the `t`.
diff --git a/crates/hir-ty/src/lower.rs b/crates/hir-ty/src/lower.rs
index b4ff98a63c6..d0d30fd570c 100644
--- a/crates/hir-ty/src/lower.rs
+++ b/crates/hir-ty/src/lower.rs
@@ -1362,7 +1362,7 @@ impl<'a> TyLoweringContext<'a> {
         ImplTrait { bounds: crate::make_single_type_binders(predicates) }
     }
 
-    fn lower_lifetime(&self, lifetime: &LifetimeRef) -> Lifetime {
+    pub fn lower_lifetime(&self, lifetime: &LifetimeRef) -> Lifetime {
         match self.resolver.resolve_lifetime(lifetime) {
             Some(resolution) => match resolution {
                 LifetimeNs::Static => static_lifetime(),