Add support for inherent projections
This commit is contained in:
@@ -0,0 +1,42 @@
|
||||
use rustc_middle::traits::solve::{Certainty, Goal, QueryResult};
|
||||
use rustc_middle::ty;
|
||||
|
||||
use super::EvalCtxt;
|
||||
|
||||
impl<'tcx> EvalCtxt<'_, 'tcx> {
|
||||
pub(super) fn normalize_inherent_associated_type(
|
||||
&mut self,
|
||||
goal: Goal<'tcx, ty::ProjectionPredicate<'tcx>>,
|
||||
) -> QueryResult<'tcx> {
|
||||
let tcx = self.tcx();
|
||||
let inherent = goal.predicate.projection_ty;
|
||||
let expected = goal.predicate.term.ty().expect("inherent consts are treated separately");
|
||||
|
||||
let impl_def_id = tcx.parent(inherent.def_id);
|
||||
let impl_substs = self.fresh_args_for_item(impl_def_id);
|
||||
|
||||
// Equate impl header and add impl where clauses
|
||||
self.eq(
|
||||
goal.param_env,
|
||||
inherent.self_ty(),
|
||||
tcx.type_of(impl_def_id).instantiate(tcx, impl_substs),
|
||||
)?;
|
||||
self.add_goals(
|
||||
tcx.predicates_of(impl_def_id)
|
||||
.instantiate(tcx, impl_substs)
|
||||
.into_iter()
|
||||
.map(|(pred, _)| goal.with(tcx, pred)),
|
||||
);
|
||||
|
||||
// Equate IAT with the RHS of the project goal
|
||||
let inherent_substs = inherent.rebase_inherent_args_onto_impl(impl_substs, tcx);
|
||||
self.eq(
|
||||
goal.param_env,
|
||||
expected,
|
||||
tcx.type_of(inherent.def_id).instantiate(tcx, inherent_substs),
|
||||
)
|
||||
.expect("expected goal term to be fully unconstrained");
|
||||
|
||||
self.evaluate_added_goals_and_make_canonical_response(Certainty::Yes)
|
||||
}
|
||||
}
|
||||
@@ -25,6 +25,7 @@ mod assembly;
|
||||
mod canonicalize;
|
||||
mod eval_ctxt;
|
||||
mod fulfill;
|
||||
mod inherent_projection;
|
||||
pub mod inspect;
|
||||
mod normalize;
|
||||
mod opaques;
|
||||
|
||||
@@ -48,7 +48,7 @@ impl<'tcx> EvalCtxt<'_, 'tcx> {
|
||||
self.merge_candidates(candidates)
|
||||
}
|
||||
ty::AssocItemContainer::ImplContainer => {
|
||||
bug!("IATs not supported here yet")
|
||||
self.normalize_inherent_associated_type(goal)
|
||||
}
|
||||
}
|
||||
} else {
|
||||
|
||||
Reference in New Issue
Block a user