Struct rustc_infer::infer::nll_relate::TypeRelating [−][src]
pub struct TypeRelating<'me, 'tcx, D> where
D: TypeRelatingDelegate<'tcx>, {
infcx: &'me InferCtxt<'me, 'tcx>,
delegate: D,
ambient_variance: Variance,
ambient_variance_info: VarianceDiagInfo<'tcx>,
a_scopes: Vec<BoundRegionScope<'tcx>>,
b_scopes: Vec<BoundRegionScope<'tcx>>,
}
Fields
infcx: &'me InferCtxt<'me, 'tcx>
delegate: D
Callback to use when we deduce an outlives relationship.
ambient_variance: Variance
How are we relating a
and b
?
- Covariant means
a <: b
. - Contravariant means
b <: a
. - Invariant means `a == b.
- Bivariant means that it doesn’t matter.
ambient_variance_info: VarianceDiagInfo<'tcx>
a_scopes: Vec<BoundRegionScope<'tcx>>
When we pass through a set of binders (e.g., when looking into
a fn
type), we push a new bound region scope onto here. This
will contain the instantiated region for each region in those
binders. When we then encounter a ReLateBound(d, br)
, we can
use the De Bruijn index d
to find the right scope, and then
bound region name br
to find the specific instantiation from
within that scope. See replace_bound_region
.
This field stores the instantiations for late-bound regions in
the a
type.
b_scopes: Vec<BoundRegionScope<'tcx>>
Same as a_scopes
, but for the b
type.
Implementations
fn create_scope(
&mut self,
value: Binder<'tcx, impl Relate<'tcx>>,
universally_quantified: UniversallyQuantified
) -> BoundRegionScope<'tcx>
fn lookup_bound_region(
debruijn: DebruijnIndex,
br: &BoundRegion,
first_free_index: DebruijnIndex,
scopes: &[BoundRegionScope<'tcx>]
) -> Region<'tcx>
fn lookup_bound_region(
debruijn: DebruijnIndex,
br: &BoundRegion,
first_free_index: DebruijnIndex,
scopes: &[BoundRegionScope<'tcx>]
) -> Region<'tcx>
When we encounter binders during the type traversal, we record
the value to substitute for each of the things contained in
that binder. (This will be either a universal placeholder or
an existential inference variable.) Given the De Bruijn index
debruijn
(and name br
) of some binder we have now
encountered, this routine finds the value that we instantiated
the region with; to do so, it indexes backwards into the list
of ambient scopes scopes
.
fn replace_bound_region(
&self,
r: Region<'tcx>,
first_free_index: DebruijnIndex,
scopes: &[BoundRegionScope<'tcx>]
) -> Region<'tcx>
fn replace_bound_region(
&self,
r: Region<'tcx>,
first_free_index: DebruijnIndex,
scopes: &[BoundRegionScope<'tcx>]
) -> Region<'tcx>
If r
is a bound region, find the scope in which it is bound
(from scopes
) and return the value that we instantiated it
with. Otherwise just return r
.
fn push_outlives(
&mut self,
sup: Region<'tcx>,
sub: Region<'tcx>,
info: VarianceDiagInfo<'tcx>
)
fn push_outlives(
&mut self,
sup: Region<'tcx>,
sub: Region<'tcx>,
info: VarianceDiagInfo<'tcx>
)
Push a new outlives requirement into our output set of constraints.
fn relate_projection_ty(
&mut self,
projection_ty: ProjectionTy<'tcx>,
value_ty: Ty<'tcx>
) -> Ty<'tcx>
fn relate_projection_ty(
&mut self,
projection_ty: ProjectionTy<'tcx>,
value_ty: Ty<'tcx>
) -> Ty<'tcx>
Relate a projection type and some value type lazily. This will always
succeed, but we push an additional ProjectionEq
goal depending
on the value type:
- if the value type is any type
T
which is not a projection, we pushProjectionEq(projection = T)
. - if the value type is another projection
other_projection
, we create a new inference variable?U
and push the two goalsProjectionEq(projection = ?U)
,ProjectionEq(other_projection = ?U)
.
fn relate_ty_var<PAIR: VidValuePair<'tcx>>(
&mut self,
pair: PAIR
) -> RelateResult<'tcx, Ty<'tcx>>
fn relate_ty_var<PAIR: VidValuePair<'tcx>>(
&mut self,
pair: PAIR
) -> RelateResult<'tcx, Ty<'tcx>>
Relate a type inference variable with a value type. This works
by creating a “generalization” G of the value where all the
lifetimes are replaced with fresh inference values. This
generalization G becomes the value of the inference variable,
and is then related in turn to the value. So e.g. if you had
vid = ?0
and value = &'a u32
, we might first instantiate
?0
to a type like &'0 u32
where '0
is a fresh variable,
and then relate &'0 u32
with &'a u32
(resulting in
relations between '0
and 'a
).
The variable pair
can be either a (vid, ty)
or (ty, vid)
– in other words, it is always an (unresolved) inference
variable vid
and a type ty
that are being related, but the
vid may appear either as the “a” type or the “b” type,
depending on where it appears in the tuple. The trait
VidValuePair
lets us work with the vid/type while preserving
the “sidedness” when necessary – the sidedness is relevant in
particular for the variance and set of in-scope things.
fn generalize_value<T: Relate<'tcx>>(
&mut self,
value: T,
for_vid: TyVid
) -> RelateResult<'tcx, T>
Trait Implementations
impl<'tcx, D> ConstEquateRelation<'tcx> for TypeRelating<'_, 'tcx, D> where
D: TypeRelatingDelegate<'tcx>,
impl<'tcx, D> ConstEquateRelation<'tcx> for TypeRelating<'_, 'tcx, D> where
D: TypeRelatingDelegate<'tcx>,
Register an obligation that both constants must be equal to each other. Read more
impl<D, 'tcx, 'me> TypeRelation<'tcx> for TypeRelating<'me, 'tcx, D> where
D: TypeRelatingDelegate<'tcx>,
impl<D, 'tcx, 'me> TypeRelation<'tcx> for TypeRelating<'me, 'tcx, D> where
D: TypeRelatingDelegate<'tcx>,
Returns true
if the value a
is the “expected” type in the
relation. Just affects error messages. Read more
fn relate_with_variance<T: Relate<'tcx>>(
&mut self,
variance: Variance,
info: VarianceDiagInfo<'tcx>,
a: T,
b: T
) -> RelateResult<'tcx, T>
fn relate_with_variance<T: Relate<'tcx>>(
&mut self,
variance: Variance,
info: VarianceDiagInfo<'tcx>,
a: T,
b: T
) -> RelateResult<'tcx, T>
Switch variance for the purpose of relating a
and b
.
fn consts(
&mut self,
a: &'tcx Const<'tcx>,
b: &'tcx Const<'tcx>
) -> RelateResult<'tcx, &'tcx Const<'tcx>>
fn binders<T>(
&mut self,
a: Binder<'tcx, T>,
b: Binder<'tcx, T>
) -> RelateResult<'tcx, Binder<'tcx, T>> where
T: Relate<'tcx>,
Generic relation routine suitable for most anything.
fn relate_item_substs(
&mut self,
item_def_id: DefId,
a_subst: &'tcx List<GenericArg<'tcx>>,
b_subst: &'tcx List<GenericArg<'tcx>>
) -> Result<&'tcx List<GenericArg<'tcx>>, TypeError<'tcx>>
fn relate_item_substs(
&mut self,
item_def_id: DefId,
a_subst: &'tcx List<GenericArg<'tcx>>,
b_subst: &'tcx List<GenericArg<'tcx>>
) -> Result<&'tcx List<GenericArg<'tcx>>, TypeError<'tcx>>
Relate the two substitutions for the given item. The default is to look up the variance for the item and proceed accordingly. Read more
Auto Trait Implementations
impl<'me, 'tcx, D> !RefUnwindSafe for TypeRelating<'me, 'tcx, D>
impl<'me, 'tcx, D> !Send for TypeRelating<'me, 'tcx, D>
impl<'me, 'tcx, D> !Sync for TypeRelating<'me, 'tcx, D>
impl<'me, 'tcx, D> Unpin for TypeRelating<'me, 'tcx, D> where
D: Unpin,
'tcx: 'me,
impl<'me, 'tcx, D> !UnwindSafe for TypeRelating<'me, 'tcx, D>
Blanket Implementations
Layout
Note: Unable to compute type layout, possibly due to this type having generic parameters. Layout can only be computed for concrete, fully-instantiated types.