diff options
| author | bors <bors@rust-lang.org> | 2024-05-19 00:03:48 +0000 |
|---|---|---|
| committer | bors <bors@rust-lang.org> | 2024-05-19 00:03:48 +0000 |
| commit | 7690f29bdb6460ab525a8e8919420a4675a93386 (patch) | |
| tree | 61f44e5244dec6a18f1e700239b8b2b92c0ae3ae /compiler/rustc_trait_selection/src | |
| parent | b1ec1bd65f89c1375d2cf2fb733a87ef390276d3 (diff) | |
| parent | 8e1dba46176c936344adf9130fbee628f7461a8f (diff) | |
| download | rust-7690f29bdb6460ab525a8e8919420a4675a93386.tar.gz rust-7690f29bdb6460ab525a8e8919420a4675a93386.zip | |
Auto merge of #125230 - compiler-errors:uplift-query-stuff, r=lcnr
Uplift more query stuff - Uplift various query input/response internals - Uplift the `ProofTree` structures and make the `ProofTreeBuilder` stuff (mostly) generic over `Interner` - Stop using `TyCtxt::def_kind` in favor of `AliasTerm::kind` r? lcnr
Diffstat (limited to 'compiler/rustc_trait_selection/src')
12 files changed, 207 insertions, 181 deletions
diff --git a/compiler/rustc_trait_selection/src/solve/assembly/mod.rs b/compiler/rustc_trait_selection/src/solve/assembly/mod.rs index 4074ecdd74e..b1dd6ae6611 100644 --- a/compiler/rustc_trait_selection/src/solve/assembly/mod.rs +++ b/compiler/rustc_trait_selection/src/solve/assembly/mod.rs @@ -25,7 +25,7 @@ pub(super) mod structural_traits; /// and the `result` when using the given `source`. #[derive(Debug, Clone)] pub(super) struct Candidate<'tcx> { - pub(super) source: CandidateSource, + pub(super) source: CandidateSource<'tcx>, pub(super) result: CanonicalResponse<'tcx>, } @@ -47,7 +47,7 @@ pub(super) trait GoalKind<'tcx>: /// [`EvalCtxt::evaluate_added_goals_and_make_canonical_response`]). fn probe_and_match_goal_against_assumption( ecx: &mut EvalCtxt<'_, 'tcx>, - source: CandidateSource, + source: CandidateSource<'tcx>, goal: Goal<'tcx, Self>, assumption: ty::Clause<'tcx>, then: impl FnOnce(&mut EvalCtxt<'_, 'tcx>) -> QueryResult<'tcx>, @@ -58,7 +58,7 @@ pub(super) trait GoalKind<'tcx>: /// goal by equating it with the assumption. fn probe_and_consider_implied_clause( ecx: &mut EvalCtxt<'_, 'tcx>, - parent_source: CandidateSource, + parent_source: CandidateSource<'tcx>, goal: Goal<'tcx, Self>, assumption: ty::Clause<'tcx>, requirements: impl IntoIterator<Item = (GoalSource, Goal<'tcx, ty::Predicate<'tcx>>)>, @@ -76,7 +76,7 @@ pub(super) trait GoalKind<'tcx>: /// since they're not implied by the well-formedness of the object type. fn probe_and_consider_object_bound_candidate( ecx: &mut EvalCtxt<'_, 'tcx>, - source: CandidateSource, + source: CandidateSource<'tcx>, goal: Goal<'tcx, Self>, assumption: ty::Clause<'tcx>, ) -> Result<Candidate<'tcx>, NoSolution> { diff --git a/compiler/rustc_trait_selection/src/solve/assembly/structural_traits.rs b/compiler/rustc_trait_selection/src/solve/assembly/structural_traits.rs index 90cc33e0275..cf826596392 100644 --- a/compiler/rustc_trait_selection/src/solve/assembly/structural_traits.rs +++ b/compiler/rustc_trait_selection/src/solve/assembly/structural_traits.rs @@ -6,9 +6,8 @@ use rustc_hir::{def_id::DefId, Movability, Mutability}; use rustc_infer::traits::query::NoSolution; use rustc_macros::{TypeFoldable, TypeVisitable}; use rustc_middle::bug; -use rustc_middle::ty::{ - self, Goal, Ty, TyCtxt, TypeFoldable, TypeFolder, TypeSuperFoldable, Upcast, -}; +use rustc_middle::traits::solve::Goal; +use rustc_middle::ty::{self, Ty, TyCtxt, TypeFoldable, TypeFolder, TypeSuperFoldable, Upcast}; use rustc_span::sym; use crate::solve::EvalCtxt; diff --git a/compiler/rustc_trait_selection/src/solve/eval_ctxt/canonical.rs b/compiler/rustc_trait_selection/src/solve/eval_ctxt/canonical.rs index 2058650f288..52deb22098f 100644 --- a/compiler/rustc_trait_selection/src/solve/eval_ctxt/canonical.rs +++ b/compiler/rustc_trait_selection/src/solve/eval_ctxt/canonical.rs @@ -40,13 +40,13 @@ trait ResponseT<'tcx> { fn var_values(&self) -> CanonicalVarValues<'tcx>; } -impl<'tcx> ResponseT<'tcx> for Response<'tcx> { +impl<'tcx> ResponseT<'tcx> for Response<TyCtxt<'tcx>> { fn var_values(&self) -> CanonicalVarValues<'tcx> { self.var_values } } -impl<'tcx, T> ResponseT<'tcx> for inspect::State<'tcx, T> { +impl<'tcx, T> ResponseT<'tcx> for inspect::State<TyCtxt<'tcx>, T> { fn var_values(&self) -> CanonicalVarValues<'tcx> { self.var_values } @@ -384,7 +384,7 @@ pub(in crate::solve) fn make_canonical_state<'tcx, T: TypeFoldable<TyCtxt<'tcx>> var_values: &[ty::GenericArg<'tcx>], max_input_universe: ty::UniverseIndex, data: T, -) -> inspect::CanonicalState<'tcx, T> { +) -> inspect::CanonicalState<TyCtxt<'tcx>, T> { let var_values = CanonicalVarValues { var_values: infcx.tcx.mk_args(var_values) }; let state = inspect::State { var_values, data }; let state = state.fold_with(&mut EagerResolver::new(infcx)); @@ -414,7 +414,7 @@ pub(in crate::solve) fn instantiate_canonical_state<'tcx, T: TypeFoldable<TyCtxt span: Span, param_env: ty::ParamEnv<'tcx>, orig_values: &mut Vec<ty::GenericArg<'tcx>>, - state: inspect::CanonicalState<'tcx, T>, + state: inspect::CanonicalState<TyCtxt<'tcx>, T>, ) -> T { // In case any fresh inference variables have been created between `state` // and the previous instantiation, extend `orig_values` for it. diff --git a/compiler/rustc_trait_selection/src/solve/eval_ctxt/mod.rs b/compiler/rustc_trait_selection/src/solve/eval_ctxt/mod.rs index e5d26e530ee..70308d4359d 100644 --- a/compiler/rustc_trait_selection/src/solve/eval_ctxt/mod.rs +++ b/compiler/rustc_trait_selection/src/solve/eval_ctxt/mod.rs @@ -1,3 +1,6 @@ +use std::io::Write; +use std::ops::ControlFlow; + use rustc_data_structures::stack::ensure_sufficient_stack; use rustc_hir::def_id::DefId; use rustc_infer::infer::at::ToTrace; @@ -8,13 +11,12 @@ use rustc_infer::infer::{ use rustc_infer::traits::query::NoSolution; use rustc_infer::traits::solve::{MaybeCause, NestedNormalizationGoals}; use rustc_infer::traits::ObligationCause; -use rustc_macros::{extension, HashStable}; +use rustc_macros::{extension, HashStable, HashStable_NoContext, TyDecodable, TyEncodable}; use rustc_middle::bug; use rustc_middle::infer::canonical::CanonicalVarInfos; -use rustc_middle::traits::solve::inspect; use rustc_middle::traits::solve::{ - CanonicalInput, CanonicalResponse, Certainty, PredefinedOpaques, PredefinedOpaquesData, - QueryResult, + inspect, CanonicalInput, CanonicalResponse, Certainty, PredefinedOpaques, + PredefinedOpaquesData, QueryResult, }; use rustc_middle::traits::specialization_graph; use rustc_middle::ty::{ @@ -23,8 +25,8 @@ use rustc_middle::ty::{ }; use rustc_session::config::DumpSolverProofTree; use rustc_span::DUMMY_SP; -use std::io::Write; -use std::ops::ControlFlow; +use rustc_type_ir::{self as ir, Interner}; +use rustc_type_ir_macros::{Lift_Generic, TypeFoldable_Generic, TypeVisitable_Generic}; use crate::traits::coherence; use crate::traits::vtable::{count_own_vtable_entries, prepare_vtable_segments, VtblSegment}; @@ -85,7 +87,7 @@ pub struct EvalCtxt<'a, 'tcx> { pub(super) search_graph: &'a mut SearchGraph<'tcx>, - nested_goals: NestedGoals<'tcx>, + nested_goals: NestedGoals<TyCtxt<'tcx>>, // Has this `EvalCtxt` errored out with `NoSolution` in `try_evaluate_added_goals`? // @@ -95,11 +97,15 @@ pub struct EvalCtxt<'a, 'tcx> { // evaluation code. tainted: Result<(), NoSolution>, - pub(super) inspect: ProofTreeBuilder<'tcx>, + pub(super) inspect: ProofTreeBuilder<TyCtxt<'tcx>>, } -#[derive(Default, Debug, Clone)] -pub(super) struct NestedGoals<'tcx> { +#[derive(derivative::Derivative)] +#[derivative(Clone(bound = ""), Debug(bound = ""), Default(bound = ""))] +#[derive(TypeVisitable_Generic, TypeFoldable_Generic, Lift_Generic)] +#[derive(TyDecodable, TyEncodable, HashStable_NoContext)] +// FIXME: This can be made crate-private once `EvalCtxt` also lives in this crate. +pub struct NestedGoals<I: Interner> { /// These normalizes-to goals are treated specially during the evaluation /// loop. In each iteration we take the RHS of the projection, replace it with /// a fresh inference variable, and only after evaluating that goal do we @@ -110,17 +116,17 @@ pub(super) struct NestedGoals<'tcx> { /// /// Forgetting to replace the RHS with a fresh inference variable when we evaluate /// this goal results in an ICE.. - pub(super) normalizes_to_goals: Vec<Goal<'tcx, ty::NormalizesTo<'tcx>>>, + pub normalizes_to_goals: Vec<ir::solve::Goal<I, ir::NormalizesTo<I>>>, /// The rest of the goals which have not yet processed or remain ambiguous. - pub(super) goals: Vec<(GoalSource, Goal<'tcx, ty::Predicate<'tcx>>)>, + pub goals: Vec<(GoalSource, ir::solve::Goal<I, I::Predicate>)>, } -impl<'tcx> NestedGoals<'tcx> { - pub(super) fn new() -> Self { +impl<I: Interner> NestedGoals<I> { + pub fn new() -> Self { Self { normalizes_to_goals: Vec::new(), goals: Vec::new() } } - pub(super) fn is_empty(&self) -> bool { + pub fn is_empty(&self) -> bool { self.normalizes_to_goals.is_empty() && self.goals.is_empty() } } @@ -143,7 +149,8 @@ impl<'tcx> InferCtxt<'tcx> { &self, goal: Goal<'tcx, ty::Predicate<'tcx>>, generate_proof_tree: GenerateProofTree, - ) -> (Result<(bool, Certainty), NoSolution>, Option<inspect::GoalEvaluation<'tcx>>) { + ) -> (Result<(bool, Certainty), NoSolution>, Option<inspect::GoalEvaluation<TyCtxt<'tcx>>>) + { EvalCtxt::enter_root(self, generate_proof_tree, |ecx| { ecx.evaluate_goal(GoalEvaluationKind::Root, GoalSource::Misc, goal) }) @@ -166,7 +173,7 @@ impl<'a, 'tcx> EvalCtxt<'a, 'tcx> { infcx: &InferCtxt<'tcx>, generate_proof_tree: GenerateProofTree, f: impl FnOnce(&mut EvalCtxt<'_, 'tcx>) -> R, - ) -> (R, Option<inspect::GoalEvaluation<'tcx>>) { + ) -> (R, Option<inspect::GoalEvaluation<TyCtxt<'tcx>>>) { let mode = if infcx.intercrate { SolverMode::Coherence } else { SolverMode::Normal }; let mut search_graph = search_graph::SearchGraph::new(mode); @@ -220,7 +227,7 @@ impl<'a, 'tcx> EvalCtxt<'a, 'tcx> { tcx: TyCtxt<'tcx>, search_graph: &'a mut search_graph::SearchGraph<'tcx>, canonical_input: CanonicalInput<'tcx>, - canonical_goal_evaluation: &mut ProofTreeBuilder<'tcx>, + canonical_goal_evaluation: &mut ProofTreeBuilder<TyCtxt<'tcx>>, f: impl FnOnce(&mut EvalCtxt<'_, 'tcx>, Goal<'tcx, ty::Predicate<'tcx>>) -> R, ) -> R { let intercrate = match search_graph.solver_mode() { @@ -282,7 +289,7 @@ impl<'a, 'tcx> EvalCtxt<'a, 'tcx> { tcx: TyCtxt<'tcx>, search_graph: &'a mut search_graph::SearchGraph<'tcx>, canonical_input: CanonicalInput<'tcx>, - goal_evaluation: &mut ProofTreeBuilder<'tcx>, + goal_evaluation: &mut ProofTreeBuilder<TyCtxt<'tcx>>, ) -> QueryResult<'tcx> { let mut canonical_goal_evaluation = goal_evaluation.new_canonical_goal_evaluation(canonical_input); diff --git a/compiler/rustc_trait_selection/src/solve/eval_ctxt/probe.rs b/compiler/rustc_trait_selection/src/solve/eval_ctxt/probe.rs index 47109c8ad5d..9edc489754c 100644 --- a/compiler/rustc_trait_selection/src/solve/eval_ctxt/probe.rs +++ b/compiler/rustc_trait_selection/src/solve/eval_ctxt/probe.rs @@ -2,10 +2,9 @@ use crate::solve::assembly::Candidate; use super::EvalCtxt; use rustc_infer::traits::BuiltinImplSource; -use rustc_middle::traits::{ - query::NoSolution, - solve::{inspect, CandidateSource, QueryResult}, -}; +use rustc_middle::traits::query::NoSolution; +use rustc_middle::traits::solve::{inspect, CandidateSource, QueryResult}; +use rustc_middle::ty::TyCtxt; use std::marker::PhantomData; pub(in crate::solve) struct ProbeCtxt<'me, 'a, 'tcx, F, T> { @@ -16,7 +15,7 @@ pub(in crate::solve) struct ProbeCtxt<'me, 'a, 'tcx, F, T> { impl<'tcx, F, T> ProbeCtxt<'_, '_, 'tcx, F, T> where - F: FnOnce(&T) -> inspect::ProbeKind<'tcx>, + F: FnOnce(&T) -> inspect::ProbeKind<TyCtxt<'tcx>>, { pub(in crate::solve) fn enter(self, f: impl FnOnce(&mut EvalCtxt<'_, 'tcx>) -> T) -> T { let ProbeCtxt { ecx: outer_ecx, probe_kind, _result } = self; @@ -51,12 +50,12 @@ where pub(in crate::solve) struct TraitProbeCtxt<'me, 'a, 'tcx, F> { cx: ProbeCtxt<'me, 'a, 'tcx, F, QueryResult<'tcx>>, - source: CandidateSource, + source: CandidateSource<'tcx>, } impl<'tcx, F> TraitProbeCtxt<'_, '_, 'tcx, F> where - F: FnOnce(&QueryResult<'tcx>) -> inspect::ProbeKind<'tcx>, + F: FnOnce(&QueryResult<'tcx>) -> inspect::ProbeKind<TyCtxt<'tcx>>, { #[instrument(level = "debug", skip_all, fields(source = ?self.source))] pub(in crate::solve) fn enter( @@ -72,7 +71,7 @@ impl<'a, 'tcx> EvalCtxt<'a, 'tcx> { /// as expensive as necessary to output the desired information. pub(in crate::solve) fn probe<F, T>(&mut self, probe_kind: F) -> ProbeCtxt<'_, 'a, 'tcx, F, T> where - F: FnOnce(&T) -> inspect::ProbeKind<'tcx>, + F: FnOnce(&T) -> inspect::ProbeKind<TyCtxt<'tcx>>, { ProbeCtxt { ecx: self, probe_kind, _result: PhantomData } } @@ -80,16 +79,24 @@ impl<'a, 'tcx> EvalCtxt<'a, 'tcx> { pub(in crate::solve) fn probe_builtin_trait_candidate( &mut self, source: BuiltinImplSource, - ) -> TraitProbeCtxt<'_, 'a, 'tcx, impl FnOnce(&QueryResult<'tcx>) -> inspect::ProbeKind<'tcx>> - { + ) -> TraitProbeCtxt< + '_, + 'a, + 'tcx, + impl FnOnce(&QueryResult<'tcx>) -> inspect::ProbeKind<TyCtxt<'tcx>>, + > { self.probe_trait_candidate(CandidateSource::BuiltinImpl(source)) } pub(in crate::solve) fn probe_trait_candidate( &mut self, - source: CandidateSource, - ) -> TraitProbeCtxt<'_, 'a, 'tcx, impl FnOnce(&QueryResult<'tcx>) -> inspect::ProbeKind<'tcx>> - { + source: CandidateSource<'tcx>, + ) -> TraitProbeCtxt< + '_, + 'a, + 'tcx, + impl FnOnce(&QueryResult<'tcx>) -> inspect::ProbeKind<TyCtxt<'tcx>>, + > { TraitProbeCtxt { cx: ProbeCtxt { ecx: self, diff --git a/compiler/rustc_trait_selection/src/solve/fulfill.rs b/compiler/rustc_trait_selection/src/solve/fulfill.rs index 625bcf33a16..4933080451d 100644 --- a/compiler/rustc_trait_selection/src/solve/fulfill.rs +++ b/compiler/rustc_trait_selection/src/solve/fulfill.rs @@ -3,7 +3,6 @@ use std::ops::ControlFlow; use rustc_infer::infer::InferCtxt; use rustc_infer::traits::query::NoSolution; -use rustc_infer::traits::solve::inspect::ProbeKind; use rustc_infer::traits::solve::{CandidateSource, GoalSource, MaybeCause}; use rustc_infer::traits::{ self, FulfillmentError, FulfillmentErrorCode, MismatchedProjectionTypes, Obligation, @@ -15,7 +14,7 @@ use rustc_middle::ty::{self, TyCtxt}; use rustc_span::symbol::sym; use super::eval_ctxt::GenerateProofTree; -use super::inspect::{InspectCandidate, InspectGoal, ProofTreeInferCtxtExt, ProofTreeVisitor}; +use super::inspect::{self, ProofTreeInferCtxtExt, ProofTreeVisitor}; use super::{Certainty, InferCtxtEvalExt}; /// A trait engine using the new trait solver. @@ -319,8 +318,8 @@ impl<'tcx> BestObligation<'tcx> { /// *don't* hold and which have impl-where clauses that also don't hold. fn non_trivial_candidates<'a>( &self, - goal: &'a InspectGoal<'a, 'tcx>, - ) -> Vec<InspectCandidate<'a, 'tcx>> { + goal: &'a inspect::InspectGoal<'a, 'tcx>, + ) -> Vec<inspect::InspectCandidate<'a, 'tcx>> { let mut candidates = goal.candidates(); match self.consider_ambiguities { true => { @@ -370,15 +369,17 @@ impl<'tcx> ProofTreeVisitor<'tcx> for BestObligation<'tcx> { self.obligation.cause.span } - fn visit_goal(&mut self, goal: &super::inspect::InspectGoal<'_, 'tcx>) -> Self::Result { + fn visit_goal(&mut self, goal: &inspect::InspectGoal<'_, 'tcx>) -> Self::Result { let candidates = self.non_trivial_candidates(goal); let [candidate] = candidates.as_slice() else { return ControlFlow::Break(self.obligation.clone()); }; // Don't walk into impls that have `do_not_recommend`. - if let ProbeKind::TraitCandidate { source: CandidateSource::Impl(impl_def_id), result: _ } = - candidate.kind() + if let inspect::ProbeKind::TraitCandidate { + source: CandidateSource::Impl(impl_def_id), + result: _, + } = candidate.kind() && goal.infcx().tcx.has_attr(impl_def_id, sym::do_not_recommend) { return ControlFlow::Break(self.obligation.clone()); @@ -475,13 +476,16 @@ enum ChildMode<'tcx> { fn derive_cause<'tcx>( tcx: TyCtxt<'tcx>, - candidate_kind: ProbeKind<'tcx>, + candidate_kind: inspect::ProbeKind<TyCtxt<'tcx>>, mut cause: ObligationCause<'tcx>, idx: usize, parent_trait_pred: ty::PolyTraitPredicate<'tcx>, ) -> ObligationCause<'tcx> { match candidate_kind { - ProbeKind::TraitCandidate { source: CandidateSource::Impl(impl_def_id), result: _ } => { + inspect::ProbeKind::TraitCandidate { + source: CandidateSource::Impl(impl_def_id), + result: _, + } => { if let Some((_, span)) = tcx.predicates_of(impl_def_id).instantiate_identity(tcx).iter().nth(idx) { @@ -495,7 +499,10 @@ fn derive_cause<'tcx>( }) } } - ProbeKind::TraitCandidate { source: CandidateSource::BuiltinImpl(..), result: _ } => { + inspect::ProbeKind::TraitCandidate { + source: CandidateSource::BuiltinImpl(..), + result: _, + } => { cause = cause.derived_cause(parent_trait_pred, ObligationCauseCode::BuiltinDerived); } _ => {} diff --git a/compiler/rustc_trait_selection/src/solve/inspect/analyse.rs b/compiler/rustc_trait_selection/src/solve/inspect/analyse.rs index b71a1b339cb..e12c66b6928 100644 --- a/compiler/rustc_trait_selection/src/solve/inspect/analyse.rs +++ b/compiler/rustc_trait_selection/src/solve/inspect/analyse.rs @@ -18,7 +18,7 @@ use rustc_middle::traits::query::NoSolution; use rustc_middle::traits::solve::{inspect, QueryResult}; use rustc_middle::traits::solve::{Certainty, Goal}; use rustc_middle::traits::ObligationCause; -use rustc_middle::ty::TypeFoldable; +use rustc_middle::ty::{TyCtxt, TypeFoldable}; use rustc_middle::{bug, ty}; use rustc_span::{Span, DUMMY_SP}; @@ -37,7 +37,7 @@ pub struct InspectGoal<'a, 'tcx> { orig_values: Vec<ty::GenericArg<'tcx>>, goal: Goal<'tcx, ty::Predicate<'tcx>>, result: Result<Certainty, NoSolution>, - evaluation_kind: inspect::CanonicalGoalEvaluationKind<'tcx>, + evaluation_kind: inspect::CanonicalGoalEvaluationKind<TyCtxt<'tcx>>, normalizes_to_term_hack: Option<NormalizesToTermHack<'tcx>>, source: GoalSource, } @@ -88,16 +88,17 @@ impl<'tcx> NormalizesToTermHack<'tcx> { pub struct InspectCandidate<'a, 'tcx> { goal: &'a InspectGoal<'a, 'tcx>, - kind: inspect::ProbeKind<'tcx>, - nested_goals: Vec<(GoalSource, inspect::CanonicalState<'tcx, Goal<'tcx, ty::Predicate<'tcx>>>)>, - final_state: inspect::CanonicalState<'tcx, ()>, - impl_args: Option<inspect::CanonicalState<'tcx, ty::GenericArgsRef<'tcx>>>, + kind: inspect::ProbeKind<TyCtxt<'tcx>>, + nested_goals: + Vec<(GoalSource, inspect::CanonicalState<TyCtxt<'tcx>, Goal<'tcx, ty::Predicate<'tcx>>>)>, + final_state: inspect::CanonicalState<TyCtxt<'tcx>, ()>, + impl_args: Option<inspect::CanonicalState<TyCtxt<'tcx>, ty::GenericArgsRef<'tcx>>>, result: QueryResult<'tcx>, shallow_certainty: Certainty, } impl<'a, 'tcx> InspectCandidate<'a, 'tcx> { - pub fn kind(&self) -> inspect::ProbeKind<'tcx> { + pub fn kind(&self) -> inspect::ProbeKind<TyCtxt<'tcx>> { self.kind } @@ -280,9 +281,9 @@ impl<'a, 'tcx> InspectGoal<'a, 'tcx> { candidates: &mut Vec<InspectCandidate<'a, 'tcx>>, nested_goals: &mut Vec<( GoalSource, - inspect::CanonicalState<'tcx, Goal<'tcx, ty::Predicate<'tcx>>>, + inspect::CanonicalState<TyCtxt<'tcx>, Goal<'tcx, ty::Predicate<'tcx>>>, )>, - probe: &inspect::Probe<'tcx>, + probe: &inspect::Probe<TyCtxt<'tcx>>, ) { let mut shallow_certainty = None; let mut impl_args = None; @@ -387,7 +388,7 @@ impl<'a, 'tcx> InspectGoal<'a, 'tcx> { fn new( infcx: &'a InferCtxt<'tcx>, depth: usize, - root: inspect::GoalEvaluation<'tcx>, + root: inspect::GoalEvaluation<TyCtxt<'tcx>>, normalizes_to_term_hack: Option<NormalizesToTermHack<'tcx>>, source: GoalSource, ) -> Self { diff --git a/compiler/rustc_trait_selection/src/solve/inspect/build.rs b/compiler/rustc_trait_selection/src/solve/inspect/build.rs index 9dd681f09e7..803300c5196 100644 --- a/compiler/rustc_trait_selection/src/solve/inspect/build.rs +++ b/compiler/rustc_trait_selection/src/solve/inspect/build.rs @@ -9,11 +9,12 @@ use rustc_infer::infer::InferCtxt; use rustc_middle::bug; use rustc_middle::infer::canonical::CanonicalVarValues; use rustc_middle::traits::query::NoSolution; -use rustc_middle::traits::solve::{ +use rustc_middle::ty::{self, TyCtxt}; +use rustc_next_trait_solver::solve::{ CanonicalInput, Certainty, Goal, GoalSource, QueryInput, QueryResult, }; -use rustc_middle::ty::{self, TyCtxt}; use rustc_session::config::DumpSolverProofTree; +use rustc_type_ir::Interner; use crate::solve::eval_ctxt::canonical; use crate::solve::{self, inspect, GenerateProofTree}; @@ -38,49 +39,51 @@ use crate::solve::{self, inspect, GenerateProofTree}; /// trees. At the end of trait solving `ProofTreeBuilder::finalize` /// is called to recursively convert the whole structure to a /// finished proof tree. -pub(in crate::solve) struct ProofTreeBuilder<'tcx> { - state: Option<Box<DebugSolver<'tcx>>>, +pub(in crate::solve) struct ProofTreeBuilder<I: Interner> { + state: Option<Box<DebugSolver<I>>>, } /// The current state of the proof tree builder, at most places /// in the code, only one or two variants are actually possible. /// /// We simply ICE in case that assumption is broken. -#[derive(Debug)] -enum DebugSolver<'tcx> { +#[derive(derivative::Derivative)] +#[derivative(Debug(bound = ""))] +enum DebugSolver<I: Interner> { Root, - GoalEvaluation(WipGoalEvaluation<'tcx>), - CanonicalGoalEvaluation(WipCanonicalGoalEvaluation<'tcx>), - GoalEvaluationStep(WipGoalEvaluationStep<'tcx>), + GoalEvaluation(WipGoalEvaluation<I>), + CanonicalGoalEvaluation(WipCanonicalGoalEvaluation<I>), + GoalEvaluationStep(WipGoalEvaluationStep<I>), } -impl<'tcx> From<WipGoalEvaluation<'tcx>> for DebugSolver<'tcx> { - fn from(g: WipGoalEvaluation<'tcx>) -> DebugSolver<'tcx> { +impl<I: Interner> From<WipGoalEvaluation<I>> for DebugSolver<I> { + fn from(g: WipGoalEvaluation<I>) -> DebugSolver<I> { DebugSolver::GoalEvaluation(g) } } -impl<'tcx> From<WipCanonicalGoalEvaluation<'tcx>> for DebugSolver<'tcx> { - fn from(g: WipCanonicalGoalEvaluation<'tcx>) -> DebugSolver<'tcx> { +impl<I: Interner> From<WipCanonicalGoalEvaluation<I>> for DebugSolver<I> { + fn from(g: WipCanonicalGoalEvaluation<I>) -> DebugSolver<I> { DebugSolver::CanonicalGoalEvaluation(g) } } -impl<'tcx> From<WipGoalEvaluationStep<'tcx>> for DebugSolver<'tcx> { - fn from(g: WipGoalEvaluationStep<'tcx>) -> DebugSolver<'tcx> { +impl<I: Interner> From<WipGoalEvaluationStep<I>> for DebugSolver<I> { + fn from(g: WipGoalEvaluationStep<I>) -> DebugSolver<I> { DebugSolver::GoalEvaluationStep(g) } } -#[derive(Eq, PartialEq, Debug)] -struct WipGoalEvaluation<'tcx> { - pub uncanonicalized_goal: Goal<'tcx, ty::Predicate<'tcx>>, - pub kind: WipGoalEvaluationKind<'tcx>, - pub evaluation: Option<WipCanonicalGoalEvaluation<'tcx>>, +#[derive(derivative::Derivative)] +#[derivative(PartialEq(bound = ""), Eq(bound = ""), Debug(bound = ""))] +struct WipGoalEvaluation<I: Interner> { + pub uncanonicalized_goal: Goal<I, I::Predicate>, + pub kind: WipGoalEvaluationKind<I>, + pub evaluation: Option<WipCanonicalGoalEvaluation<I>>, } -impl<'tcx> WipGoalEvaluation<'tcx> { - fn finalize(self) -> inspect::GoalEvaluation<'tcx> { +impl<I: Interner> WipGoalEvaluation<I> { + fn finalize(self) -> inspect::GoalEvaluation<I> { inspect::GoalEvaluation { uncanonicalized_goal: self.uncanonicalized_goal, kind: match self.kind { @@ -94,21 +97,23 @@ impl<'tcx> WipGoalEvaluation<'tcx> { } } -#[derive(Eq, PartialEq, Debug)] -pub(in crate::solve) enum WipGoalEvaluationKind<'tcx> { - Root { orig_values: Vec<ty::GenericArg<'tcx>> }, +#[derive(derivative::Derivative)] +#[derivative(PartialEq(bound = ""), Eq(bound = ""), Debug(bound = ""))] +pub(in crate::solve) enum WipGoalEvaluationKind<I: Interner> { + Root { orig_values: Vec<I::GenericArg> }, Nested, } -#[derive(Eq, PartialEq)] -pub(in crate::solve) enum WipCanonicalGoalEvaluationKind<'tcx> { +#[derive(derivative::Derivative)] +#[derivative(PartialEq(bound = ""), Eq(bound = ""))] +pub(in crate::solve) enum WipCanonicalGoalEvaluationKind<I: Interner> { Overflow, CycleInStack, ProvisionalCacheHit, - Interned { revisions: &'tcx [inspect::GoalEvaluationStep<'tcx>] }, + Interned { revisions: I::GoalEvaluationSteps }, } -impl std::fmt::Debug for WipCanonicalGoalEvaluationKind<'_> { +impl<I: Interner> std::fmt::Debug for WipCanonicalGoalEvaluationKind<I> { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { match self { Self::Overflow => write!(f, "Overflow"), @@ -119,18 +124,19 @@ impl std::fmt::Debug for WipCanonicalGoalEvaluationKind<'_> { } } -#[derive(Eq, PartialEq, Debug)] -struct WipCanonicalGoalEvaluation<'tcx> { - goal: CanonicalInput<'tcx>, - kind: Option<WipCanonicalGoalEvaluationKind<'tcx>>, +#[derive(derivative::Derivative)] +#[derivative(PartialEq(bound = ""), Eq(bound = ""), Debug(bound = ""))] +struct WipCanonicalGoalEvaluation<I: Interner> { + goal: CanonicalInput<I>, + kind: Option<WipCanonicalGoalEvaluationKind<I>>, /// Only used for uncached goals. After we finished evaluating /// the goal, this is interned and moved into `kind`. - revisions: Vec<WipGoalEvaluationStep<'tcx>>, - result: Option<QueryResult<'tcx>>, + revisions: Vec<WipGoalEvaluationStep<I>>, + result: Option<QueryResult<I>>, } -impl<'tcx> WipCanonicalGoalEvaluation<'tcx> { - fn finalize(self) -> inspect::CanonicalGoalEvaluation<'tcx> { +impl<I: Interner> WipCanonicalGoalEvaluation<I> { + fn finalize(self) -> inspect::CanonicalGoalEvaluation<I> { assert!(self.revisions.is_empty()); let kind = match self.kind.unwrap() { WipCanonicalGoalEvaluationKind::Overflow => { @@ -151,14 +157,15 @@ impl<'tcx> WipCanonicalGoalEvaluation<'tcx> { } } -#[derive(Eq, PartialEq, Debug)] -struct WipAddedGoalsEvaluation<'tcx> { - evaluations: Vec<Vec<WipGoalEvaluation<'tcx>>>, +#[derive(derivative::Derivative)] +#[derivative(PartialEq(bound = ""), Eq(bound = ""), Debug(bound = ""))] +struct WipAddedGoalsEvaluation<I: Interner> { + evaluations: Vec<Vec<WipGoalEvaluation<I>>>, result: Option<Result<Certainty, NoSolution>>, } -impl<'tcx> WipAddedGoalsEvaluation<'tcx> { - fn finalize(self) -> inspect::AddedGoalsEvaluation<'tcx> { +impl<I: Interner> WipAddedGoalsEvaluation<I> { + fn finalize(self) -> inspect::AddedGoalsEvaluation<I> { inspect::AddedGoalsEvaluation { evaluations: self .evaluations @@ -172,22 +179,23 @@ impl<'tcx> WipAddedGoalsEvaluation<'tcx> { } } -#[derive(Eq, PartialEq, Debug)] -struct WipGoalEvaluationStep<'tcx> { +#[derive(derivative::Derivative)] +#[derivative(PartialEq(bound = ""), Eq(bound = ""), Debug(bound = ""))] +struct WipGoalEvaluationStep<I: Interner> { /// Unlike `EvalCtxt::var_values`, we append a new /// generic arg here whenever we create a new inference /// variable. /// /// This is necessary as we otherwise don't unify these /// vars when instantiating multiple `CanonicalState`. - var_values: Vec<ty::GenericArg<'tcx>>, - instantiated_goal: QueryInput<'tcx, ty::Predicate<'tcx>>, + var_values: Vec<I::GenericArg>, + instantiated_goal: QueryInput<I, I::Predicate>, probe_depth: usize, - evaluation: WipProbe<'tcx>, + evaluation: WipProbe<I>, } -impl<'tcx> WipGoalEvaluationStep<'tcx> { - fn current_evaluation_scope(&mut self) -> &mut WipProbe<'tcx> { +impl<I: Interner> WipGoalEvaluationStep<I> { + fn current_evaluation_scope(&mut self) -> &mut WipProbe<I> { let mut current = &mut self.evaluation; for _ in 0..self.probe_depth { match current.steps.last_mut() { @@ -198,7 +206,7 @@ impl<'tcx> WipGoalEvaluationStep<'tcx> { current } - fn added_goals_evaluation(&mut self) -> &mut WipAddedGoalsEvaluation<'tcx> { + fn added_goals_evaluation(&mut self) -> &mut WipAddedGoalsEvaluation<I> { let mut current = &mut self.evaluation; loop { match current.steps.last_mut() { @@ -209,7 +217,7 @@ impl<'tcx> WipGoalEvaluationStep<'tcx> { } } - fn finalize(self) -> inspect::GoalEvaluationStep<'tcx> { + fn finalize(self) -> inspect::GoalEvaluationStep<I> { let evaluation = self.evaluation.finalize(); match evaluation.kind { inspect::ProbeKind::Root { .. } => (), @@ -219,16 +227,17 @@ impl<'tcx> WipGoalEvaluationStep<'tcx> { } } -#[derive(Eq, PartialEq, Debug)] -struct WipProbe<'tcx> { +#[derive(derivative::Derivative)] +#[derivative(PartialEq(bound = ""), Eq(bound = ""), Debug(bound = ""))] +struct WipProbe<I: Interner> { initial_num_var_values: usize, - steps: Vec<WipProbeStep<'tcx>>, - kind: Option<inspect::ProbeKind<'tcx>>, - final_state: Option<inspect::CanonicalState<'tcx, ()>>, + steps: Vec<WipProbeStep<I>>, + kind: Option<inspect::ProbeKind<I>>, + final_state: Option<inspect::CanonicalState<I, ()>>, } -impl<'tcx> WipProbe<'tcx> { - fn finalize(self) -> inspect::Probe<'tcx> { +impl<I: Interner> WipProbe<I> { + fn finalize(self) -> inspect::Probe<I> { inspect::Probe { steps: self.steps.into_iter().map(WipProbeStep::finalize).collect(), kind: self.kind.unwrap(), @@ -237,17 +246,18 @@ impl<'tcx> WipProbe<'tcx> { } } -#[derive(Eq, PartialEq, Debug)] -enum WipProbeStep<'tcx> { - AddGoal(GoalSource, inspect::CanonicalState<'tcx, Goal<'tcx, ty::Predicate<'tcx>>>), - EvaluateGoals(WipAddedGoalsEvaluation<'tcx>), - NestedProbe(WipProbe<'tcx>), +#[derive(derivative::Derivative)] +#[derivative(PartialEq(bound = ""), Eq(bound = ""), Debug(bound = ""))] +enum WipProbeStep<I: Interner> { + AddGoal(GoalSource, inspect::CanonicalState<I, Goal<I, I::Predicate>>), + EvaluateGoals(WipAddedGoalsEvaluation<I>), + NestedProbe(WipProbe<I>), MakeCanonicalResponse { shallow_certainty: Certainty }, - RecordImplArgs { impl_args: inspect::CanonicalState<'tcx, ty::GenericArgsRef<'tcx>> }, + RecordImplArgs { impl_args: inspect::CanonicalState<I, I::GenericArgs> }, } -impl<'tcx> WipProbeStep<'tcx> { - fn finalize(self) -> inspect::ProbeStep<'tcx> { +impl<I: Interner> WipProbeStep<I> { + fn finalize(self) -> inspect::ProbeStep<I> { match self { WipProbeStep::AddGoal(source, goal) => inspect::ProbeStep::AddGoal(source, goal), WipProbeStep::EvaluateGoals(eval) => inspect::ProbeStep::EvaluateGoals(eval.finalize()), @@ -262,26 +272,27 @@ impl<'tcx> WipProbeStep<'tcx> { } } -impl<'tcx> ProofTreeBuilder<'tcx> { - fn new(state: impl Into<DebugSolver<'tcx>>) -> ProofTreeBuilder<'tcx> { +// FIXME: Genericize this impl. +impl<'tcx> ProofTreeBuilder<TyCtxt<'tcx>> { + fn new(state: impl Into<DebugSolver<TyCtxt<'tcx>>>) -> ProofTreeBuilder<TyCtxt<'tcx>> { ProofTreeBuilder { state: Some(Box::new(state.into())) } } - fn nested<T: Into<DebugSolver<'tcx>>>(&self, state: impl FnOnce() -> T) -> Self { + fn nested<T: Into<DebugSolver<TyCtxt<'tcx>>>>(&self, state: impl FnOnce() -> T) -> Self { ProofTreeBuilder { state: self.state.as_ref().map(|_| Box::new(state().into())) } } - fn as_mut(&mut self) -> Option<&mut DebugSolver<'tcx>> { + fn as_mut(&mut self) -> Option<&mut DebugSolver<TyCtxt<'tcx>>> { self.state.as_deref_mut() } - pub fn take_and_enter_probe(&mut self) -> ProofTreeBuilder<'tcx> { + pub fn take_and_enter_probe(&mut self) -> ProofTreeBuilder<TyCtxt<'tcx>> { let mut nested = ProofTreeBuilder { state: self.state.take() }; nested.enter_probe(); nested } - pub fn finalize(self) -> Option<inspect::GoalEvaluation<'tcx>> { + pub fn finalize(self) -> Option<inspect::GoalEvaluation<TyCtxt<'tcx>>> { match *self.state? { DebugSolver::GoalEvaluation(wip_goal_evaluation) => { Some(wip_goal_evaluation.finalize()) @@ -293,7 +304,7 @@ impl<'tcx> ProofTreeBuilder<'tcx> { pub fn new_maybe_root( tcx: TyCtxt<'tcx>, generate_proof_tree: GenerateProofTree, - ) -> ProofTreeBuilder<'tcx> { + ) -> ProofTreeBuilder<TyCtxt<'tcx>> { match generate_proof_tree { GenerateProofTree::Never => ProofTreeBuilder::new_noop(), GenerateProofTree::IfEnabled => { @@ -311,11 +322,11 @@ impl<'tcx> ProofTreeBuilder<'tcx> { } } - pub fn new_root() -> ProofTreeBuilder<'tcx> { + pub fn new_root() -> ProofTreeBuilder<TyCtxt<'tcx>> { ProofTreeBuilder::new(DebugSolver::Root) } - pub fn new_noop() -> ProofTreeBuilder<'tcx> { + pub fn new_noop() -> ProofTreeBuilder<TyCtxt<'tcx>> { ProofTreeBuilder { state: None } } @@ -325,10 +336,10 @@ impl<'tcx> ProofTreeBuilder<'tcx> { pub(in crate::solve) fn new_goal_evaluation( &mut self, - goal: Goal<'tcx, ty::Predicate<'tcx>>, + goal: Goal<TyCtxt<'tcx>, ty::Predicate<'tcx>>, orig_values: &[ty::GenericArg<'tcx>], kind: solve::GoalEvaluationKind, - ) -> ProofTreeBuilder<'tcx> { + ) -> ProofTreeBuilder<TyCtxt<'tcx>> { self.nested(|| WipGoalEvaluation { uncanonicalized_goal: goal, kind: match kind { @@ -343,8 +354,8 @@ impl<'tcx> ProofTreeBuilder<'tcx> { pub fn new_canonical_goal_evaluation( &mut self, - goal: CanonicalInput<'tcx>, - ) -> ProofTreeBuilder<'tcx> { + goal: CanonicalInput<TyCtxt<'tcx>>, + ) -> ProofTreeBuilder<TyCtxt<'tcx>> { self.nested(|| WipCanonicalGoalEvaluation { goal, kind: None, @@ -356,7 +367,7 @@ impl<'tcx> ProofTreeBuilder<'tcx> { pub fn finalize_evaluation( &mut self, tcx: TyCtxt<'tcx>, - ) -> Option<&'tcx [inspect::GoalEvaluationStep<'tcx>]> { + ) -> Option<&'tcx [inspect::GoalEvaluationStep<TyCtxt<'tcx>>]> { self.as_mut().map(|this| match this { DebugSolver::CanonicalGoalEvaluation(evaluation) => { let revisions = mem::take(&mut evaluation.revisions) @@ -371,7 +382,10 @@ impl<'tcx> ProofTreeBuilder<'tcx> { }) } - pub fn canonical_goal_evaluation(&mut self, canonical_goal_evaluation: ProofTreeBuilder<'tcx>) { + pub fn canonical_goal_evaluation( + &mut self, + canonical_goal_evaluation: ProofTreeBuilder<TyCtxt<'tcx>>, + ) { if let Some(this) = self.as_mut() { match (this, *canonical_goal_evaluation.state.unwrap()) { ( @@ -386,7 +400,7 @@ impl<'tcx> ProofTreeBuilder<'tcx> { } } - pub fn goal_evaluation_kind(&mut self, kind: WipCanonicalGoalEvaluationKind<'tcx>) { + pub fn goal_evaluation_kind(&mut self, kind: WipCanonicalGoalEvaluationKind<TyCtxt<'tcx>>) { if let Some(this) = self.as_mut() { match this { DebugSolver::CanonicalGoalEvaluation(canonical_goal_evaluation) => { @@ -397,7 +411,7 @@ impl<'tcx> ProofTreeBuilder<'tcx> { } } - pub fn goal_evaluation(&mut self, goal_evaluation: ProofTreeBuilder<'tcx>) { + pub fn goal_evaluation(&mut self, goal_evaluation: ProofTreeBuilder<TyCtxt<'tcx>>) { if let Some(this) = self.as_mut() { match (this, *goal_evaluation.state.unwrap()) { ( @@ -418,8 +432,8 @@ impl<'tcx> ProofTreeBuilder<'tcx> { pub fn new_goal_evaluation_step( &mut self, var_values: CanonicalVarValues<'tcx>, - instantiated_goal: QueryInput<'tcx, ty::Predicate<'tcx>>, - ) -> ProofTreeBuilder<'tcx> { + instantiated_goal: QueryInput<TyCtxt<'tcx>, ty::Predicate<'tcx>>, + ) -> ProofTreeBuilder<TyCtxt<'tcx>> { self.nested(|| WipGoalEvaluationStep { var_values: var_values.var_values.to_vec(), instantiated_goal, @@ -433,7 +447,7 @@ impl<'tcx> ProofTreeBuilder<'tcx> { }) } - pub fn goal_evaluation_step(&mut self, goal_evaluation_step: ProofTreeBuilder<'tcx>) { + pub fn goal_evaluation_step(&mut self, goal_evaluation_step: ProofTreeBuilder<TyCtxt<'tcx>>) { if let Some(this) = self.as_mut() { match (this, *goal_evaluation_step.state.unwrap()) { ( @@ -474,7 +488,7 @@ impl<'tcx> ProofTreeBuilder<'tcx> { } } - pub fn probe_kind(&mut self, probe_kind: inspect::ProbeKind<'tcx>) { + pub fn probe_kind(&mut self, probe_kind: inspect::ProbeKind<TyCtxt<'tcx>>) { match self.as_mut() { None => {} Some(DebugSolver::GoalEvaluationStep(state)) => { @@ -510,7 +524,7 @@ impl<'tcx> ProofTreeBuilder<'tcx> { &mut self, infcx: &InferCtxt<'tcx>, max_input_universe: ty::UniverseIndex, - goal: Goal<'tcx, ty::NormalizesTo<'tcx>>, + goal: Goal<TyCtxt<'tcx>, ty::NormalizesTo<'tcx>>, ) { self.add_goal( infcx, @@ -525,7 +539,7 @@ impl<'tcx> ProofTreeBuilder<'tcx> { infcx: &InferCtxt<'tcx>, max_input_universe: ty::UniverseIndex, source: GoalSource, - goal: Goal<'tcx, ty::Predicate<'tcx>>, + goal: Goal<TyCtxt<'tcx>, ty::Predicate<'tcx>>, ) { match self.as_mut() { None => {} @@ -579,7 +593,7 @@ impl<'tcx> ProofTreeBuilder<'tcx> { } } - pub fn finish_probe(mut self) -> ProofTreeBuilder<'tcx> { + pub fn finish_probe(mut self) -> ProofTreeBuilder<TyCtxt<'tcx>> { match self.as_mut() { None => {} Some(DebugSolver::GoalEvaluationStep(state)) => { @@ -627,7 +641,7 @@ impl<'tcx> ProofTreeBuilder<'tcx> { } } - pub fn query_result(&mut self, result: QueryResult<'tcx>) { + pub fn query_result(&mut self, result: QueryResult<TyCtxt<'tcx>>) { if let Some(this) = self.as_mut() { match this { DebugSolver::CanonicalGoalEvaluation(canonical_goal_evaluation) => { diff --git a/compiler/rustc_trait_selection/src/solve/mod.rs b/compiler/rustc_trait_selection/src/solve/mod.rs index 540ab738a22..b085d009d75 100644 --- a/compiler/rustc_trait_selection/src/solve/mod.rs +++ b/compiler/rustc_trait_selection/src/solve/mod.rs @@ -20,11 +20,11 @@ use rustc_macros::extension; use rustc_middle::bug; use rustc_middle::infer::canonical::CanonicalVarInfos; use rustc_middle::traits::solve::{ - CanonicalResponse, Certainty, ExternalConstraintsData, GoalSource, QueryResult, Response, + CanonicalResponse, Certainty, ExternalConstraintsData, Goal, GoalSource, QueryResult, Response, }; use rustc_middle::ty::{ - self, AliasRelationDirection, CoercePredicate, Goal, RegionOutlivesPredicate, SubtypePredicate, - Ty, TyCtxt, TypeOutlivesPredicate, UniverseIndex, + self, AliasRelationDirection, CoercePredicate, RegionOutlivesPredicate, SubtypePredicate, Ty, + TyCtxt, TypeOutlivesPredicate, UniverseIndex, }; mod alias_relate; @@ -74,7 +74,7 @@ enum GoalEvaluationKind { } #[extension(trait CanonicalResponseExt)] -impl<'tcx> Canonical<'tcx, Response<'tcx>> { +impl<'tcx> Canonical<'tcx, Response<TyCtxt<'tcx>>> { fn has_no_inference_or_external_constraints(&self) -> bool { self.value.external_constraints.region_constraints.is_empty() && self.value.var_values.is_identity() diff --git a/compiler/rustc_trait_selection/src/solve/normalizes_to/mod.rs b/compiler/rustc_trait_selection/src/solve/normalizes_to/mod.rs index 7ab27374e7a..8c492b62c1a 100644 --- a/compiler/rustc_trait_selection/src/solve/normalizes_to/mod.rs +++ b/compiler/rustc_trait_selection/src/solve/normalizes_to/mod.rs @@ -3,7 +3,6 @@ use crate::traits::specialization_graph; use super::assembly::structural_traits::AsyncCallableRelevantTypes; use super::assembly::{self, structural_traits, Candidate}; use super::{EvalCtxt, GoalSource}; -use rustc_hir::def::DefKind; use rustc_hir::def_id::DefId; use rustc_hir::LangItem; use rustc_infer::traits::query::NoSolution; @@ -54,23 +53,15 @@ impl<'tcx> EvalCtxt<'_, 'tcx> { &mut self, goal: Goal<'tcx, NormalizesTo<'tcx>>, ) -> QueryResult<'tcx> { - let def_id = goal.predicate.def_id(); - match self.tcx().def_kind(def_id) { - DefKind::AssocTy | DefKind::AssocConst => { - match self.tcx().associated_item(def_id).container { - ty::AssocItemContainer::TraitContainer => { - let candidates = self.assemble_and_evaluate_candidates(goal); - self.merge_candidates(candidates) - } - ty::AssocItemContainer::ImplContainer => { - self.normalize_inherent_associated_type(goal) - } - } + match goal.predicate.alias.kind(self.tcx()) { + ty::AliasTermKind::ProjectionTy | ty::AliasTermKind::ProjectionConst => { + let candidates = self.assemble_and_evaluate_candidates(goal); + self.merge_candidates(candidates) } - DefKind::AnonConst => self.normalize_anon_const(goal), - DefKind::TyAlias => self.normalize_weak_type(goal), - DefKind::OpaqueTy => self.normalize_opaque_type(goal), - kind => bug!("unknown DefKind {} in normalizes-to goal: {goal:#?}", kind.descr(def_id)), + ty::AliasTermKind::InherentTy => self.normalize_inherent_associated_type(goal), + ty::AliasTermKind::OpaqueTy => self.normalize_opaque_type(goal), + ty::AliasTermKind::WeakTy => self.normalize_weak_type(goal), + ty::AliasTermKind::UnevaluatedConst => self.normalize_anon_const(goal), } } @@ -108,7 +99,7 @@ impl<'tcx> assembly::GoalKind<'tcx> for NormalizesTo<'tcx> { fn probe_and_match_goal_against_assumption( ecx: &mut EvalCtxt<'_, 'tcx>, - source: CandidateSource, + source: CandidateSource<'tcx>, goal: Goal<'tcx, Self>, assumption: ty::Clause<'tcx>, then: impl FnOnce(&mut EvalCtxt<'_, 'tcx>) -> QueryResult<'tcx>, diff --git a/compiler/rustc_trait_selection/src/solve/search_graph.rs b/compiler/rustc_trait_selection/src/solve/search_graph.rs index 60362aa01da..0164d44667c 100644 --- a/compiler/rustc_trait_selection/src/solve/search_graph.rs +++ b/compiler/rustc_trait_selection/src/solve/search_graph.rs @@ -253,8 +253,8 @@ impl<'tcx> SearchGraph<'tcx> { &mut self, tcx: TyCtxt<'tcx>, input: CanonicalInput<'tcx>, - inspect: &mut ProofTreeBuilder<'tcx>, - mut prove_goal: impl FnMut(&mut Self, &mut ProofTreeBuilder<'tcx>) -> QueryResult<'tcx>, + inspect: &mut ProofTreeBuilder<TyCtxt<'tcx>>, + mut prove_goal: impl FnMut(&mut Self, &mut ProofTreeBuilder<TyCtxt<'tcx>>) -> QueryResult<'tcx>, ) -> QueryResult<'tcx> { // Check for overflow. let Some(available_depth) = Self::allowed_depth_for_nested(tcx, &self.stack) else { diff --git a/compiler/rustc_trait_selection/src/solve/trait_goals.rs b/compiler/rustc_trait_selection/src/solve/trait_goals.rs index b46edb32f72..9139c75d399 100644 --- a/compiler/rustc_trait_selection/src/solve/trait_goals.rs +++ b/compiler/rustc_trait_selection/src/solve/trait_goals.rs @@ -103,7 +103,7 @@ impl<'tcx> assembly::GoalKind<'tcx> for TraitPredicate<'tcx> { fn probe_and_match_goal_against_assumption( ecx: &mut EvalCtxt<'_, 'tcx>, - source: CandidateSource, + source: CandidateSource<'tcx>, goal: Goal<'tcx, Self>, assumption: ty::Clause<'tcx>, then: impl FnOnce(&mut EvalCtxt<'_, 'tcx>) -> QueryResult<'tcx>, @@ -821,7 +821,7 @@ impl<'tcx> EvalCtxt<'_, 'tcx> { fn consider_builtin_upcast_to_principal( &mut self, goal: Goal<'tcx, (Ty<'tcx>, Ty<'tcx>)>, - source: CandidateSource, + source: CandidateSource<'tcx>, a_data: &'tcx ty::List<ty::PolyExistentialPredicate<'tcx>>, a_region: ty::Region<'tcx>, b_data: &'tcx ty::List<ty::PolyExistentialPredicate<'tcx>>, @@ -1149,7 +1149,7 @@ impl<'tcx> EvalCtxt<'_, 'tcx> { /// wrapped in one. fn probe_and_evaluate_goal_for_constituent_tys( &mut self, - source: CandidateSource, + source: CandidateSource<'tcx>, goal: Goal<'tcx, TraitPredicate<'tcx>>, constituent_tys: impl Fn( &EvalCtxt<'_, 'tcx>, |
