Move visitable bounds up into interner

This commit is contained in:
Michael Goulet 2024-02-13 15:53:15 +00:00
parent edc5053352
commit 7e80867f3c
4 changed files with 37 additions and 77 deletions

View File

@ -28,7 +28,7 @@ use crate::ty::{
self, AdtDef, AdtDefData, AdtKind, Binder, Clause, Const, ConstData, GenericParamDefKind,
ImplPolarity, List, ParamConst, ParamTy, PolyExistentialPredicate, PolyFnSig, Predicate,
PredicateKind, Region, RegionKind, ReprOptions, TraitObjectVisitor, Ty, TyKind, TyVid,
Visibility,
TypeVisitable, Visibility,
};
use crate::ty::{GenericArg, GenericArgs, GenericArgsRef};
use rustc_ast::{self as ast, attr};
@ -87,7 +87,7 @@ impl<'tcx> Interner for TyCtxt<'tcx> {
type GenericArg = ty::GenericArg<'tcx>;
type Term = ty::Term<'tcx>;
type Binder<T> = Binder<'tcx, T>;
type Binder<T: TypeVisitable<TyCtxt<'tcx>>> = Binder<'tcx, T>;
type BoundVars = &'tcx List<ty::BoundVariableKind>;
type BoundVar = ty::BoundVariableKind;
type CanonicalVars = CanonicalVarInfos<'tcx>;

View File

@ -1,7 +1,7 @@
use std::cmp::Ordering;
use rustc_type_ir::fold::{TypeFoldable, TypeFolder, TypeSuperFoldable};
use rustc_type_ir::visit::{Flags, TypeVisitableExt};
use rustc_type_ir::visit::TypeVisitableExt;
use rustc_type_ir::{
self as ty, Canonical, CanonicalTyVarKind, CanonicalVarInfo, CanonicalVarKind, ConstTy,
InferCtxtLike, Interner, IntoKind, PlaceholderLike,
@ -45,13 +45,7 @@ pub struct Canonicalizer<'a, Infcx: InferCtxtLike<Interner = I>, I: Interner> {
binder_index: ty::DebruijnIndex,
}
impl<'a, Infcx: InferCtxtLike<Interner = I>, I: Interner> Canonicalizer<'a, Infcx, I>
where
I::Ty: Flags,
I::Region: Flags,
I::Const: Flags,
I::Predicate: Flags,
{
impl<'a, Infcx: InferCtxtLike<Interner = I>, I: Interner> Canonicalizer<'a, Infcx, I> {
pub fn canonicalize<T: TypeFoldable<I>>(
infcx: &'a Infcx,
canonicalize_mode: CanonicalizeMode,

View File

@ -2,6 +2,7 @@ use smallvec::SmallVec;
use std::fmt::Debug;
use std::hash::Hash;
use crate::visit::{Flags, TypeSuperVisitable, TypeVisitable};
use crate::{
BoundVar, BoundVars, CanonicalVarInfo, ConstKind, DebruijnIndex, DebugWithInfcx, RegionKind,
TyKind, UniverseIndex,
@ -19,7 +20,7 @@ pub trait Interner: Sized {
type GenericArg: Copy + DebugWithInfcx<Self> + Hash + Ord;
type Term: Copy + Debug + Hash + Ord;
type Binder<T>: BoundVars<Self>;
type Binder<T: TypeVisitable<Self>>: BoundVars<Self> + TypeSuperVisitable<Self>;
type BoundVars: IntoIterator<Item = Self::BoundVar>;
type BoundVar;
@ -31,7 +32,9 @@ pub trait Interner: Sized {
+ Hash
+ Ord
+ Into<Self::GenericArg>
+ IntoKind<Kind = TyKind<Self>>;
+ IntoKind<Kind = TyKind<Self>>
+ TypeSuperVisitable<Self>
+ Flags;
type Tys: Copy + Debug + Hash + Ord + IntoIterator<Item = Self::Ty>;
type AliasTy: Copy + DebugWithInfcx<Self> + Hash + Ord;
type ParamTy: Copy + Debug + Hash + Ord;
@ -51,7 +54,9 @@ pub trait Interner: Sized {
+ Ord
+ Into<Self::GenericArg>
+ IntoKind<Kind = ConstKind<Self>>
+ ConstTy<Self>;
+ ConstTy<Self>
+ TypeSuperVisitable<Self>
+ Flags;
type AliasConst: Copy + DebugWithInfcx<Self> + Hash + Ord;
type PlaceholderConst: Copy + Debug + Hash + Ord + PlaceholderLike;
type ParamConst: Copy + Debug + Hash + Ord;
@ -65,7 +70,8 @@ pub trait Interner: Sized {
+ Hash
+ Ord
+ Into<Self::GenericArg>
+ IntoKind<Kind = RegionKind<Self>>;
+ IntoKind<Kind = RegionKind<Self>>
+ Flags;
type EarlyParamRegion: Copy + Debug + Hash + Ord;
type LateParamRegion: Copy + Debug + Hash + Ord;
type BoundRegion: Copy + Debug + Hash + Ord;
@ -73,7 +79,7 @@ pub trait Interner: Sized {
type PlaceholderRegion: Copy + Debug + Hash + Ord + PlaceholderLike;
// Predicates
type Predicate: Copy + Debug + Hash + Eq;
type Predicate: Copy + Debug + Hash + Eq + TypeSuperVisitable<Self> + Flags;
type TraitPredicate: Copy + Debug + Hash + Eq;
type RegionOutlivesPredicate: Copy + Debug + Hash + Eq;
type TypeOutlivesPredicate: Copy + Debug + Hash + Eq;

View File

@ -87,38 +87,28 @@ pub trait TypeVisitor<I: Interner>: Sized {
#[cfg(not(feature = "nightly"))]
type BreakTy;
fn visit_binder<T: TypeVisitable<I>>(&mut self, t: &I::Binder<T>) -> ControlFlow<Self::BreakTy>
where
I::Binder<T>: TypeSuperVisitable<I>,
{
fn visit_binder<T: TypeVisitable<I>>(
&mut self,
t: &I::Binder<T>,
) -> ControlFlow<Self::BreakTy> {
t.super_visit_with(self)
}
fn visit_ty(&mut self, t: I::Ty) -> ControlFlow<Self::BreakTy>
where
I::Ty: TypeSuperVisitable<I>,
{
fn visit_ty(&mut self, t: I::Ty) -> ControlFlow<Self::BreakTy> {
t.super_visit_with(self)
}
// The default region visitor is a no-op because `Region` is non-recursive
// and has no `super_visit_with` method to call. That also explains the
// lack of `I::Region: TypeSuperVisitable<I>` bound.
// and has no `super_visit_with` method to call.
fn visit_region(&mut self, _r: I::Region) -> ControlFlow<Self::BreakTy> {
ControlFlow::Continue(())
}
fn visit_const(&mut self, c: I::Const) -> ControlFlow<Self::BreakTy>
where
I::Const: TypeSuperVisitable<I>,
{
fn visit_const(&mut self, c: I::Const) -> ControlFlow<Self::BreakTy> {
c.super_visit_with(self)
}
fn visit_predicate(&mut self, p: I::Predicate) -> ControlFlow<Self::BreakTy>
where
I::Predicate: TypeSuperVisitable<I>,
{
fn visit_predicate(&mut self, p: I::Predicate) -> ControlFlow<Self::BreakTy> {
p.super_visit_with(self)
}
}
@ -327,13 +317,7 @@ pub trait TypeVisitableExt<I: Interner>: TypeVisitable<I> {
}
}
impl<I: Interner, T: TypeVisitable<I>> TypeVisitableExt<I> for T
where
I::Ty: Flags,
I::Region: Flags,
I::Const: Flags,
I::Predicate: Flags,
{
impl<I: Interner, T: TypeVisitable<I>> TypeVisitableExt<I> for T {
fn has_type_flags(&self, flags: TypeFlags) -> bool {
let res =
self.visit_with(&mut HasTypeFlagsVisitor { flags }) == ControlFlow::Break(FoundFlags);
@ -381,19 +365,13 @@ impl std::fmt::Debug for HasTypeFlagsVisitor {
// are present, regardless of whether those bound variables are used. This
// is important for anonymization of binders in `TyCtxt::erase_regions`. We
// specifically detect this case in `visit_binder`.
impl<I: Interner> TypeVisitor<I> for HasTypeFlagsVisitor
where
I::Ty: Flags,
I::Region: Flags,
I::Const: Flags,
I::Predicate: Flags,
{
impl<I: Interner> TypeVisitor<I> for HasTypeFlagsVisitor {
type BreakTy = FoundFlags;
fn visit_binder<T: TypeVisitable<I>>(&mut self, t: &I::Binder<T>) -> ControlFlow<Self::BreakTy>
where
I::Binder<T>: TypeSuperVisitable<I>,
{
fn visit_binder<T: TypeVisitable<I>>(
&mut self,
t: &I::Binder<T>,
) -> ControlFlow<Self::BreakTy> {
// If we're looking for the HAS_BINDER_VARS flag, check if the
// binder has vars. This won't be present in the binder's bound
// value, so we need to check here too.
@ -480,19 +458,13 @@ struct HasEscapingVarsVisitor {
outer_index: ty::DebruijnIndex,
}
impl<I: Interner> TypeVisitor<I> for HasEscapingVarsVisitor
where
I::Ty: Flags,
I::Region: Flags,
I::Const: Flags,
I::Predicate: Flags,
{
impl<I: Interner> TypeVisitor<I> for HasEscapingVarsVisitor {
type BreakTy = FoundEscapingVars;
fn visit_binder<T: TypeVisitable<I>>(&mut self, t: &I::Binder<T>) -> ControlFlow<Self::BreakTy>
where
I::Binder<T>: TypeSuperVisitable<I>,
{
fn visit_binder<T: TypeVisitable<I>>(
&mut self,
t: &I::Binder<T>,
) -> ControlFlow<Self::BreakTy> {
self.outer_index.shift_in(1);
let result = t.super_visit_with(self);
self.outer_index.shift_out(1);
@ -550,19 +522,10 @@ where
struct HasErrorVisitor;
impl<I: Interner> TypeVisitor<I> for HasErrorVisitor
where
I::Ty: Flags,
I::Region: Flags,
I::Const: Flags,
I::Predicate: Flags,
{
impl<I: Interner> TypeVisitor<I> for HasErrorVisitor {
type BreakTy = I::ErrorGuaranteed;
fn visit_ty(&mut self, t: <I as Interner>::Ty) -> ControlFlow<Self::BreakTy>
where
<I as Interner>::Ty: TypeSuperVisitable<I>,
{
fn visit_ty(&mut self, t: <I as Interner>::Ty) -> ControlFlow<Self::BreakTy> {
if let ty::Error(guar) = t.kind() {
ControlFlow::Break(guar)
} else {
@ -570,10 +533,7 @@ where
}
}
fn visit_const(&mut self, c: <I as Interner>::Const) -> ControlFlow<Self::BreakTy>
where
<I as Interner>::Const: TypeSuperVisitable<I>,
{
fn visit_const(&mut self, c: <I as Interner>::Const) -> ControlFlow<Self::BreakTy> {
if let ty::ConstKind::Error(guar) = c.kind() {
ControlFlow::Break(guar)
} else {