1
Fork 0

DropckOutlives to rustc_middle

This commit is contained in:
lcnr 2024-10-15 18:23:32 +02:00
parent 9334d85e69
commit f3ce557fcd
6 changed files with 27 additions and 37 deletions

View file

@ -11,8 +11,7 @@ use rustc_mir_dataflow::impls::MaybeInitializedPlaces;
use rustc_mir_dataflow::move_paths::{HasMoveData, MoveData, MovePathIndex}; use rustc_mir_dataflow::move_paths::{HasMoveData, MoveData, MovePathIndex};
use rustc_mir_dataflow::points::{DenseLocationMap, PointIndex}; use rustc_mir_dataflow::points::{DenseLocationMap, PointIndex};
use rustc_span::DUMMY_SP; use rustc_span::DUMMY_SP;
use rustc_trait_selection::traits::query::type_op::outlives::DropckOutlives; use rustc_trait_selection::traits::query::type_op::{DropckOutlives, TypeOp, TypeOpOutput};
use rustc_trait_selection::traits::query::type_op::{TypeOp, TypeOpOutput};
use tracing::debug; use tracing::debug;
use crate::location::RichLocation; use crate::location::RichLocation;
@ -632,7 +631,7 @@ impl<'tcx> LivenessContext<'_, '_, '_, 'tcx> {
match typeck match typeck
.param_env .param_env
.and(DropckOutlives::new(dropped_ty)) .and(DropckOutlives { dropped_ty })
.fully_perform(typeck.infcx, DUMMY_SP) .fully_perform(typeck.infcx, DUMMY_SP)
{ {
Ok(TypeOpOutput { output, constraints, .. }) => { Ok(TypeOpOutput { output, constraints, .. }) => {

View file

@ -65,10 +65,11 @@ use crate::query::plumbing::{
CyclePlaceholder, DynamicQuery, query_ensure, query_ensure_error_guaranteed, query_get_at, CyclePlaceholder, DynamicQuery, query_ensure, query_ensure_error_guaranteed, query_get_at,
}; };
use crate::traits::query::{ use crate::traits::query::{
CanonicalAliasGoal, CanonicalImpliedOutlivesBoundsGoal, CanonicalPredicateGoal, CanonicalAliasGoal, CanonicalDropckOutlivesGoal, CanonicalImpliedOutlivesBoundsGoal,
CanonicalTyGoal, CanonicalTypeOpAscribeUserTypeGoal, CanonicalTypeOpNormalizeGoal, CanonicalPredicateGoal, CanonicalTyGoal, CanonicalTypeOpAscribeUserTypeGoal,
CanonicalTypeOpProvePredicateGoal, DropckConstraint, DropckOutlivesResult, CanonicalTypeOpNormalizeGoal, CanonicalTypeOpProvePredicateGoal, DropckConstraint,
MethodAutoderefStepsResult, NoSolution, NormalizationResult, OutlivesBound, DropckOutlivesResult, MethodAutoderefStepsResult, NoSolution, NormalizationResult,
OutlivesBound,
}; };
use crate::traits::{ use crate::traits::{
CodegenObligationError, DynCompatibilityViolation, EvaluationResult, ImplSource, CodegenObligationError, DynCompatibilityViolation, EvaluationResult, ImplSource,
@ -2069,12 +2070,12 @@ rustc_queries! {
/// Do not call this query directly: /// Do not call this query directly:
/// invoke `DropckOutlives::new(dropped_ty)).fully_perform(typeck.infcx)` instead. /// invoke `DropckOutlives::new(dropped_ty)).fully_perform(typeck.infcx)` instead.
query dropck_outlives( query dropck_outlives(
goal: CanonicalTyGoal<'tcx> goal: CanonicalDropckOutlivesGoal<'tcx>
) -> Result< ) -> Result<
&'tcx Canonical<'tcx, canonical::QueryResponse<'tcx, DropckOutlivesResult<'tcx>>>, &'tcx Canonical<'tcx, canonical::QueryResponse<'tcx, DropckOutlivesResult<'tcx>>>,
NoSolution, NoSolution,
> { > {
desc { "computing dropck types for `{}`", goal.value.value } desc { "computing dropck types for `{}`", goal.value.value.dropped_ty }
} }
/// Do not call this query directly: invoke `infcx.predicate_may_hold()` or /// Do not call this query directly: invoke `infcx.predicate_may_hold()` or

View file

@ -51,6 +51,11 @@ pub mod type_op {
pub struct ImpliedOutlivesBounds<'tcx> { pub struct ImpliedOutlivesBounds<'tcx> {
pub ty: Ty<'tcx>, pub ty: Ty<'tcx>,
} }
#[derive(Copy, Clone, Debug, Hash, PartialEq, Eq, HashStable, TypeFoldable, TypeVisitable)]
pub struct DropckOutlives<'tcx> {
pub dropped_ty: Ty<'tcx>,
}
} }
pub type CanonicalAliasGoal<'tcx> = Canonical<'tcx, ty::ParamEnvAnd<'tcx, ty::AliasTy<'tcx>>>; pub type CanonicalAliasGoal<'tcx> = Canonical<'tcx, ty::ParamEnvAnd<'tcx, ty::AliasTy<'tcx>>>;
@ -76,6 +81,9 @@ pub type CanonicalTypeOpNormalizeGoal<'tcx, T> =
pub type CanonicalImpliedOutlivesBoundsGoal<'tcx> = pub type CanonicalImpliedOutlivesBoundsGoal<'tcx> =
Canonical<'tcx, ty::ParamEnvAnd<'tcx, type_op::ImpliedOutlivesBounds<'tcx>>>; Canonical<'tcx, ty::ParamEnvAnd<'tcx, type_op::ImpliedOutlivesBounds<'tcx>>>;
pub type CanonicalDropckOutlivesGoal<'tcx> =
Canonical<'tcx, ty::ParamEnvAnd<'tcx, type_op::DropckOutlives<'tcx>>>;
#[derive(Clone, Debug, Default, HashStable, TypeFoldable, TypeVisitable)] #[derive(Clone, Debug, Default, HashStable, TypeFoldable, TypeVisitable)]
pub struct DropckOutlivesResult<'tcx> { pub struct DropckOutlivesResult<'tcx> {
pub kinds: Vec<GenericArg<'tcx>>, pub kinds: Vec<GenericArg<'tcx>>,

View file

@ -1,4 +1,5 @@
use rustc_data_structures::fx::FxHashSet; use rustc_data_structures::fx::FxHashSet;
use rustc_infer::traits::query::type_op::DropckOutlives;
use rustc_middle::traits::query::{DropckConstraint, DropckOutlivesResult}; use rustc_middle::traits::query::{DropckConstraint, DropckOutlivesResult};
use rustc_middle::ty::{self, EarlyBinder, ParamEnvAnd, Ty, TyCtxt}; use rustc_middle::ty::{self, EarlyBinder, ParamEnvAnd, Ty, TyCtxt};
use rustc_span::{DUMMY_SP, Span}; use rustc_span::{DUMMY_SP, Span};
@ -88,10 +89,10 @@ pub fn trivial_dropck_outlives<'tcx>(tcx: TyCtxt<'tcx>, ty: Ty<'tcx>) -> bool {
pub fn compute_dropck_outlives_inner<'tcx>( pub fn compute_dropck_outlives_inner<'tcx>(
ocx: &ObligationCtxt<'_, 'tcx>, ocx: &ObligationCtxt<'_, 'tcx>,
goal: ParamEnvAnd<'tcx, Ty<'tcx>>, goal: ParamEnvAnd<'tcx, DropckOutlives<'tcx>>,
) -> Result<DropckOutlivesResult<'tcx>, NoSolution> { ) -> Result<DropckOutlivesResult<'tcx>, NoSolution> {
let tcx = ocx.infcx.tcx; let tcx = ocx.infcx.tcx;
let ParamEnvAnd { param_env, value: for_ty } = goal; let ParamEnvAnd { param_env, value: DropckOutlives { dropped_ty } } = goal;
let mut result = DropckOutlivesResult { kinds: vec![], overflows: vec![] }; let mut result = DropckOutlivesResult { kinds: vec![], overflows: vec![] };
@ -99,7 +100,7 @@ pub fn compute_dropck_outlives_inner<'tcx>(
// something from the stack and invoke // something from the stack and invoke
// `dtorck_constraint_for_ty_inner`. This may produce new types that // `dtorck_constraint_for_ty_inner`. This may produce new types that
// have to be pushed on the stack. This continues until we have explored // have to be pushed on the stack. This continues until we have explored
// all the reachable types from the type `for_ty`. // all the reachable types from the type `dropped_ty`.
// //
// Example: Imagine that we have the following code: // Example: Imagine that we have the following code:
// //
@ -129,7 +130,7 @@ pub fn compute_dropck_outlives_inner<'tcx>(
// lead to us trying to push `A` a second time -- to prevent // lead to us trying to push `A` a second time -- to prevent
// infinite recursion, we notice that `A` was already pushed // infinite recursion, we notice that `A` was already pushed
// once and stop. // once and stop.
let mut ty_stack = vec![(for_ty, 0)]; let mut ty_stack = vec![(dropped_ty, 0)];
// Set used to detect infinite recursion. // Set used to detect infinite recursion.
let mut ty_set = FxHashSet::default(); let mut ty_set = FxHashSet::default();

View file

@ -1,23 +1,12 @@
use rustc_macros::{HashStable, TypeFoldable, TypeVisitable};
use rustc_middle::traits::query::{DropckOutlivesResult, NoSolution}; use rustc_middle::traits::query::{DropckOutlivesResult, NoSolution};
use rustc_middle::ty::{ParamEnvAnd, Ty, TyCtxt}; use rustc_middle::ty::{ParamEnvAnd, TyCtxt};
use crate::infer::canonical::{Canonical, CanonicalQueryResponse}; use crate::infer::canonical::{Canonical, CanonicalQueryResponse};
use crate::traits::ObligationCtxt; use crate::traits::ObligationCtxt;
use crate::traits::query::dropck_outlives::{ use crate::traits::query::dropck_outlives::{
compute_dropck_outlives_inner, trivial_dropck_outlives, compute_dropck_outlives_inner, trivial_dropck_outlives,
}; };
use crate::traits::query::type_op::DropckOutlives;
#[derive(Copy, Clone, Debug, HashStable, TypeFoldable, TypeVisitable)]
pub struct DropckOutlives<'tcx> {
dropped_ty: Ty<'tcx>,
}
impl<'tcx> DropckOutlives<'tcx> {
pub fn new(dropped_ty: Ty<'tcx>) -> Self {
DropckOutlives { dropped_ty }
}
}
impl<'tcx> super::QueryTypeOp<'tcx> for DropckOutlives<'tcx> { impl<'tcx> super::QueryTypeOp<'tcx> for DropckOutlives<'tcx> {
type QueryResponse = DropckOutlivesResult<'tcx>; type QueryResponse = DropckOutlivesResult<'tcx>;
@ -33,14 +22,6 @@ impl<'tcx> super::QueryTypeOp<'tcx> for DropckOutlives<'tcx> {
tcx: TyCtxt<'tcx>, tcx: TyCtxt<'tcx>,
canonicalized: Canonical<'tcx, ParamEnvAnd<'tcx, Self>>, canonicalized: Canonical<'tcx, ParamEnvAnd<'tcx, Self>>,
) -> Result<CanonicalQueryResponse<'tcx, Self::QueryResponse>, NoSolution> { ) -> Result<CanonicalQueryResponse<'tcx, Self::QueryResponse>, NoSolution> {
// FIXME convert to the type expected by the `dropck_outlives`
// query. This should eventually be fixed by changing the
// *underlying query*.
let canonicalized = canonicalized.unchecked_map(|ParamEnvAnd { param_env, value }| {
let DropckOutlives { dropped_ty } = value;
param_env.and(dropped_ty)
});
tcx.dropck_outlives(canonicalized) tcx.dropck_outlives(canonicalized)
} }
@ -48,6 +29,6 @@ impl<'tcx> super::QueryTypeOp<'tcx> for DropckOutlives<'tcx> {
ocx: &ObligationCtxt<'_, 'tcx>, ocx: &ObligationCtxt<'_, 'tcx>,
key: ParamEnvAnd<'tcx, Self>, key: ParamEnvAnd<'tcx, Self>,
) -> Result<Self::QueryResponse, NoSolution> { ) -> Result<Self::QueryResponse, NoSolution> {
compute_dropck_outlives_inner(ocx, key.param_env.and(key.value.dropped_ty)) compute_dropck_outlives_inner(ocx, key.param_env.and(key.value))
} }
} }

View file

@ -10,7 +10,7 @@ use rustc_trait_selection::infer::InferCtxtBuilderExt;
use rustc_trait_selection::traits::query::dropck_outlives::{ use rustc_trait_selection::traits::query::dropck_outlives::{
compute_dropck_outlives_inner, dtorck_constraint_for_ty_inner, compute_dropck_outlives_inner, dtorck_constraint_for_ty_inner,
}; };
use rustc_trait_selection::traits::query::{CanonicalTyGoal, NoSolution}; use rustc_trait_selection::traits::query::{CanonicalDropckOutlivesGoal, NoSolution};
use tracing::debug; use tracing::debug;
pub(crate) fn provide(p: &mut Providers) { pub(crate) fn provide(p: &mut Providers) {
@ -19,7 +19,7 @@ pub(crate) fn provide(p: &mut Providers) {
fn dropck_outlives<'tcx>( fn dropck_outlives<'tcx>(
tcx: TyCtxt<'tcx>, tcx: TyCtxt<'tcx>,
canonical_goal: CanonicalTyGoal<'tcx>, canonical_goal: CanonicalDropckOutlivesGoal<'tcx>,
) -> Result<&'tcx Canonical<'tcx, QueryResponse<'tcx, DropckOutlivesResult<'tcx>>>, NoSolution> { ) -> Result<&'tcx Canonical<'tcx, QueryResponse<'tcx, DropckOutlivesResult<'tcx>>>, NoSolution> {
debug!("dropck_outlives(goal={:#?})", canonical_goal); debug!("dropck_outlives(goal={:#?})", canonical_goal);