Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 7 additions & 7 deletions crates/hir-ty/src/autoderef.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ use triomphe::Arc;

use crate::{
Canonical, Goal, Interner, ProjectionTyExt, TraitEnvironment, Ty, TyBuilder, TyKind,
db::HirDatabase, infer::unify::InferenceTable,
db::HirDatabase, infer::unify::InferenceTable, next_solver::mapping::ChalkToNextSolver,
};

const AUTODEREF_RECURSION_LIMIT: usize = 20;
Expand Down Expand Up @@ -98,7 +98,7 @@ impl<'table, 'db> Autoderef<'table, 'db> {
explicit: bool,
use_receiver_trait: bool,
) -> Self {
let ty = table.resolve_ty_shallow(&ty);
let ty = table.structurally_resolve_type(&ty);
Autoderef { table, ty, at_start: true, steps: Vec::new(), explicit, use_receiver_trait }
}

Expand All @@ -114,7 +114,7 @@ impl<'table, 'db> Autoderef<'table, 'db, usize> {
explicit: bool,
use_receiver_trait: bool,
) -> Self {
let ty = table.resolve_ty_shallow(&ty);
let ty = table.structurally_resolve_type(&ty);
Autoderef { table, ty, at_start: true, steps: 0, explicit, use_receiver_trait }
}
}
Expand Down Expand Up @@ -160,7 +160,7 @@ pub(crate) fn autoderef_step(
use_receiver_trait: bool,
) -> Option<(AutoderefKind, Ty)> {
if let Some(derefed) = builtin_deref(table.db, &ty, explicit) {
Some((AutoderefKind::Builtin, table.resolve_ty_shallow(derefed)))
Some((AutoderefKind::Builtin, table.structurally_resolve_type(derefed)))
} else {
Some((AutoderefKind::Overloaded, deref_by_trait(table, ty, use_receiver_trait)?))
}
Expand All @@ -187,7 +187,7 @@ pub(crate) fn deref_by_trait(
use_receiver_trait: bool,
) -> Option<Ty> {
let _p = tracing::info_span!("deref_by_trait").entered();
if table.resolve_ty_shallow(&ty).inference_var(Interner).is_some() {
if table.structurally_resolve_type(&ty).inference_var(Interner).is_some() {
// don't try to deref unknown variables
return None;
}
Expand Down Expand Up @@ -229,8 +229,8 @@ pub(crate) fn deref_by_trait(
return None;
}

table.register_obligation(implements_goal);
table.register_obligation(implements_goal.to_nextsolver(table.interner));

let result = table.normalize_projection_ty(projection);
Some(table.resolve_ty_shallow(&result))
Some(table.structurally_resolve_type(&result))
}
41 changes: 23 additions & 18 deletions crates/hir-ty/src/chalk_ext.rs
Original file line number Diff line number Diff line change
Expand Up @@ -245,26 +245,30 @@ impl TyExt for Ty {
}

fn impl_trait_bounds(&self, db: &dyn HirDatabase) -> Option<Vec<QuantifiedWhereClause>> {
let handle_async_block_type_impl_trait = |def: DefWithBodyId| {
let krate = def.module(db).krate();
if let Some(future_trait) = LangItem::Future.resolve_trait(db, krate) {
// This is only used by type walking.
// Parameters will be walked outside, and projection predicate is not used.
// So just provide the Future trait.
let impl_bound = Binders::empty(
Interner,
WhereClause::Implemented(TraitRef {
trait_id: to_chalk_trait_id(future_trait),
substitution: Substitution::empty(Interner),
}),
);
Some(vec![impl_bound])
} else {
None
}
};

match self.kind(Interner) {
TyKind::OpaqueType(opaque_ty_id, subst) => {
match db.lookup_intern_impl_trait_id((*opaque_ty_id).into()) {
ImplTraitId::AsyncBlockTypeImplTrait(def, _expr) => {
let krate = def.module(db).krate();
if let Some(future_trait) = LangItem::Future.resolve_trait(db, krate) {
// This is only used by type walking.
// Parameters will be walked outside, and projection predicate is not used.
// So just provide the Future trait.
let impl_bound = Binders::empty(
Interner,
WhereClause::Implemented(TraitRef {
trait_id: to_chalk_trait_id(future_trait),
substitution: Substitution::empty(Interner),
}),
);
Some(vec![impl_bound])
} else {
None
}
handle_async_block_type_impl_trait(def)
}
ImplTraitId::ReturnTypeImplTrait(func, idx) => {
db.return_type_impl_traits(func).map(|it| {
Expand Down Expand Up @@ -299,8 +303,9 @@ impl TyExt for Ty {
data.substitute(Interner, &opaque_ty.substitution)
})
}
// It always has an parameter for Future::Output type.
ImplTraitId::AsyncBlockTypeImplTrait(..) => unreachable!(),
ImplTraitId::AsyncBlockTypeImplTrait(def, _) => {
return handle_async_block_type_impl_trait(def);
}
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

};

predicates.map(|it| it.into_value_and_skipped_binders().0)
Expand Down
6 changes: 3 additions & 3 deletions crates/hir-ty/src/consteval_nextsolver.rs
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ use crate::{
next_solver::{
Const, ConstBytes, ConstKind, DbInterner, ErrorGuaranteed, GenericArg, GenericArgs,
ParamConst, SolverDefId, Ty, ValueConst,
mapping::{ChalkToNextSolver, convert_args_for_result, convert_binder_to_early_binder},
mapping::{ChalkToNextSolver, NextSolverToChalk, convert_binder_to_early_binder},
},
};

Expand Down Expand Up @@ -145,7 +145,7 @@ pub fn try_const_usize<'db>(db: &'db dyn HirDatabase, c: Const<'db>) -> Option<u
SolverDefId::StaticId(id) => GeneralConstId::StaticId(id),
_ => unreachable!(),
};
let subst = convert_args_for_result(interner, unevaluated_const.args.as_slice());
let subst = unevaluated_const.args.to_chalk(interner);
let ec = db.const_eval(c, subst, None).ok()?.to_nextsolver(interner);
try_const_usize(db, ec)
}
Expand All @@ -168,7 +168,7 @@ pub fn try_const_isize<'db>(db: &'db dyn HirDatabase, c: &Const<'db>) -> Option<
SolverDefId::StaticId(id) => GeneralConstId::StaticId(id),
_ => unreachable!(),
};
let subst = convert_args_for_result(interner, unevaluated_const.args.as_slice());
let subst = unevaluated_const.args.to_chalk(interner);
let ec = db.const_eval(c, subst, None).ok()?.to_nextsolver(interner);
try_const_isize(db, &ec)
}
Expand Down
28 changes: 15 additions & 13 deletions crates/hir-ty/src/infer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -55,10 +55,9 @@ use stdx::{always, never};
use triomphe::Arc;

use crate::{
AliasEq, AliasTy, Binders, ClosureId, Const, DomainGoal, GenericArg, Goal, ImplTraitId,
ImplTraitIdx, InEnvironment, IncorrectGenericsLenKind, Interner, Lifetime, OpaqueTyId,
ParamLoweringMode, PathLoweringDiagnostic, ProjectionTy, Substitution, TraitEnvironment, Ty,
TyBuilder, TyExt,
AliasEq, AliasTy, Binders, ClosureId, Const, DomainGoal, GenericArg, ImplTraitId, ImplTraitIdx,
IncorrectGenericsLenKind, Interner, Lifetime, OpaqueTyId, ParamLoweringMode,
PathLoweringDiagnostic, ProjectionTy, Substitution, TraitEnvironment, Ty, TyBuilder, TyExt,
db::HirDatabase,
fold_tys,
generics::Generics,
Expand All @@ -70,6 +69,7 @@ use crate::{
},
lower::{ImplTraitLoweringMode, LifetimeElisionKind, diagnostics::TyLoweringDiagnostic},
mir::MirSpan,
next_solver::{self, mapping::ChalkToNextSolver},
static_lifetime, to_assoc_type_id,
traits::FnTrait,
utils::UnevaluatedConstEvaluatorFolder,
Expand Down Expand Up @@ -182,13 +182,13 @@ impl BindingMode {
}

#[derive(Debug)]
pub(crate) struct InferOk<T> {
pub(crate) struct InferOk<'db, T> {
value: T,
goals: Vec<InEnvironment<Goal>>,
goals: Vec<next_solver::Goal<'db, next_solver::Predicate<'db>>>,
}

impl<T> InferOk<T> {
fn map<U>(self, f: impl FnOnce(T) -> U) -> InferOk<U> {
impl<'db, T> InferOk<'db, T> {
fn map<U>(self, f: impl FnOnce(T) -> U) -> InferOk<'db, U> {
InferOk { value: f(self.value), goals: self.goals }
}
}
Expand All @@ -203,7 +203,7 @@ pub enum InferenceTyDiagnosticSource {

#[derive(Debug)]
pub(crate) struct TypeError;
pub(crate) type InferResult<T> = Result<InferOk<T>, TypeError>;
pub(crate) type InferResult<'db, T> = Result<InferOk<'db, T>, TypeError>;

#[derive(Debug, PartialEq, Eq, Clone)]
pub enum InferenceDiagnostic {
Expand Down Expand Up @@ -832,6 +832,7 @@ impl<'db> InferenceContext<'db> {
coercion_casts,
diagnostics: _,
} = &mut result;
table.resolve_obligations_as_possible();
table.fallback_if_possible();

// Comment from rustc:
Expand Down Expand Up @@ -1480,7 +1481,8 @@ impl<'db> InferenceContext<'db> {
}

fn push_obligation(&mut self, o: DomainGoal) {
self.table.register_obligation(o.cast(Interner));
let goal: crate::Goal = o.cast(Interner);
self.table.register_obligation(goal.to_nextsolver(self.table.interner));
}

fn unify(&mut self, ty1: &Ty, ty2: &Ty) -> bool {
Expand Down Expand Up @@ -1746,7 +1748,7 @@ impl<'db> InferenceContext<'db> {

ty = self.table.insert_type_vars(ty);
ty = self.table.normalize_associated_types_in(ty);
ty = self.table.resolve_ty_shallow(&ty);
ty = self.table.structurally_resolve_type(&ty);
if ty.is_unknown() {
return (self.err_ty(), None);
}
Expand Down Expand Up @@ -1817,7 +1819,7 @@ impl<'db> InferenceContext<'db> {
let ty = match ty.kind(Interner) {
TyKind::Alias(AliasTy::Projection(proj_ty)) => {
let ty = self.table.normalize_projection_ty(proj_ty.clone());
self.table.resolve_ty_shallow(&ty)
self.table.structurally_resolve_type(&ty)
}
_ => ty,
};
Expand Down Expand Up @@ -2047,7 +2049,7 @@ impl Expectation {
fn adjust_for_branches(&self, table: &mut unify::InferenceTable<'_>) -> Expectation {
match self {
Expectation::HasType(ety) => {
let ety = table.resolve_ty_shallow(ety);
let ety = table.structurally_resolve_type(ety);
if ety.is_ty_var() { Expectation::None } else { Expectation::HasType(ety) }
}
Expectation::RValueLikeUnsized(ety) => Expectation::RValueLikeUnsized(ety.clone()),
Expand Down
12 changes: 8 additions & 4 deletions crates/hir-ty/src/infer/closure.rs
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ use crate::{
infer::{BreakableKind, CoerceMany, Diverges, coerce::CoerceNever},
make_binders,
mir::{BorrowKind, MirSpan, MutBorrowKind, ProjectionElem},
next_solver::mapping::ChalkToNextSolver,
to_assoc_type_id,
traits::FnTrait,
utils::{self, elaborate_clause_supertraits},
Expand Down Expand Up @@ -437,10 +438,10 @@ impl InferenceContext<'_> {
associated_ty_id: to_assoc_type_id(future_output),
substitution: Substitution::from1(Interner, ret_param_future.clone()),
});
self.table.register_obligation(
let goal: crate::Goal =
crate::AliasEq { alias: future_projection, ty: ret_param_future_output.clone() }
.cast(Interner),
);
.cast(Interner);
self.table.register_obligation(goal.to_nextsolver(self.table.interner));

Some(FnSubst(Substitution::from_iter(
Interner,
Expand Down Expand Up @@ -568,7 +569,10 @@ impl InferenceContext<'_> {
let supplied_sig = self.supplied_sig_of_closure(body, ret_type, arg_types, closure_kind);

let snapshot = self.table.snapshot();
if !self.table.unify(&expected_sig.substitution, &supplied_sig.expected_sig.substitution) {
if !self.table.unify::<_, crate::next_solver::GenericArgs<'_>>(
&expected_sig.substitution.0,
&supplied_sig.expected_sig.substitution.0,
) {
self.table.rollback_to(snapshot);
}

Expand Down
Loading
Loading