Struct rustc::ty::ClosureSubsts
[−]
[src]
pub struct ClosureSubsts<'tcx> { pub substs: &'tcx Substs<'tcx>, }
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
A closure can be modeled as a struct that looks like:
struct Closure<'l0...'li, T0...Tj, CK, CS, U0...Uk> { upvar0: U0, ... upvark: Uk }
where:
- 'l0...'li and T0...Tj are the lifetime and type parameters in scope on the function that defined the closure,
- CK represents the closure kind (Fn vs FnMut vs FnOnce). This
is rather hackily encoded via a scalar type. See
TyS::to_opt_closure_kind
for details. - CS represents the closure signature, representing as a
fn()
type. For example,fn(u32, u32) -> u32
would mean that the closure implementsCK<(u32, u32), Output = u32>
, whereCK
is the trait specified above. - U0...Uk are type parameters representing the types of its upvars
(borrowed, if appropriate; that is, if Ui represents a by-ref upvar,
and the up-var has the type
Foo
, thenUi = &Foo
).
So, for example, given this function:
fn foo<'a, T>(data: &'a mut T) { do(|| data.count += 1) }
the type of the closure would be something like:
struct Closure<'a, T, U0> { data: U0 }
Note that the type of the upvar is not specified in the struct. You may wonder how the impl would then be able to use the upvar, if it doesn't know it's type? The answer is that the impl is (conceptually) not fully generic over Closure but rather tied to instances with the expected upvar types:
impl<'b, 'a, T> FnMut() for Closure<'a, T, &'b mut &'a mut T> { ... }
You can see that the impl fully specified the type of the upvar
and thus knows full well that data
has type &'b mut &'a mut T
.
(Here, I am assuming that data
is mut-borrowed.)
Now, the last question you may ask is: Why include the upvar types
as extra type parameters? The reason for this design is that the
upvar types can reference lifetimes that are internal to the
creating function. In my example above, for example, the lifetime
'b
represents the scope of the closure itself; this is some
subset of foo
, probably just the scope of the call to the to
do()
. If we just had the lifetime/type parameters from the
enclosing function, we couldn't name this lifetime 'b
. Note that
there can also be lifetimes in the types of the upvars themselves,
if one of them happens to be a reference to something that the
creating fn owns.
OK, you say, so why not create a more minimal set of parameters that just includes the extra lifetime parameters? The answer is primarily that it would be hard --- we don't know at the time when we create the closure type what the full types of the upvars are, nor do we know which are borrowed and which are not. In this design, we can just supply a fresh type parameter and figure that out later.
All right, you say, but why include the type parameters from the
original function then? The answer is that trans may need them
when monomorphizing, and they may not appear in the upvars. A
closure could capture no variables but still make use of some
in-scope type parameter with a bound (e.g., if our example above
had an extra U: Default
, and the closure called U::default()
).
There is another reason. This design (implicitly) prohibits closures from capturing themselves (except via a trait object). This simplifies closure inference considerably, since it means that when we infer the kind of a closure or its upvars, we don't have to handle cycles where the decisions we make for closure C wind up influencing the decisions we ought to make for closure C (which would then require fixed point iteration to handle). Plus it fixes an ICE. :P
Generators
Perhaps surprisingly, ClosureSubsts
are also used for
generators. In that case, what is written above is only half-true
-- the set of type parameters is similar, but the role of CK and
CS are different. CK represents the "yield type" and CS
represents the "return type" of the generator.
It'd be nice to split this struct into ClosureSubsts and GeneratorSubsts, I believe. -nmatsakis
Fields
substs: &'tcx Substs<'tcx>
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
Lifetime and type parameters from the enclosing function, concatenated with the types of the upvars.
These are separated out because trans wants to pass them around when monomorphizing.
Methods
impl<'tcx> ClosureSubsts<'tcx>
[src]
pub fn upvar_tys(
self,
def_id: DefId,
tcx: TyCtxt
) -> impl Iterator<Item = Ty<'tcx>> + 'tcx
[src]
self,
def_id: DefId,
tcx: TyCtxt
) -> impl Iterator<Item = Ty<'tcx>> + 'tcx
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
pub fn closure_kind_ty(self, def_id: DefId, tcx: TyCtxt) -> Ty<'tcx>
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
Returns the closure kind for this closure; may return a type
variable during inference. To get the closure kind during
inference, use infcx.closure_kind(def_id, substs)
.
pub fn closure_sig_ty(self, def_id: DefId, tcx: TyCtxt) -> Ty<'tcx>
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
Returns the type representing the closure signature for this
closure; may contain type variables during inference. To get
the closure signature during inference, use
infcx.fn_sig(def_id)
.
pub fn generator_yield_ty(self, def_id: DefId, tcx: TyCtxt) -> Ty<'tcx>
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
Returns the type representing the yield type of the generator.
pub fn generator_return_ty(self, def_id: DefId, tcx: TyCtxt) -> Ty<'tcx>
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
Returns the type representing the return type of the generator.
pub fn generator_poly_sig(self, def_id: DefId, tcx: TyCtxt) -> PolyGenSig<'tcx>
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
Return the "generator signature", which consists of its yield and return types.
NB. Some bits of the code prefers to see this wrapped in a binder, but it never contains bound regions. Probably this function should be removed.
pub fn generator_sig(self, def_id: DefId, tcx: TyCtxt) -> GenSig<'tcx>
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
Return the "generator signature", which consists of its yield and return types.
impl<'tcx> ClosureSubsts<'tcx>
[src]
pub fn closure_kind(
self,
def_id: DefId,
tcx: TyCtxt<'_, 'tcx, 'tcx>
) -> ClosureKind
[src]
self,
def_id: DefId,
tcx: TyCtxt<'_, 'tcx, 'tcx>
) -> ClosureKind
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
Returns the closure kind for this closure; only usable outside of an inference context, because in that context we know that there are no type variables.
If you have an inference context, use infcx.closure_kind()
.
pub fn closure_sig(
self,
def_id: DefId,
tcx: TyCtxt<'_, 'tcx, 'tcx>
) -> PolyFnSig<'tcx>
[src]
self,
def_id: DefId,
tcx: TyCtxt<'_, 'tcx, 'tcx>
) -> PolyFnSig<'tcx>
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
Extracts the signature from the closure; only usable outside of an inference context, because in that context we know that there are no type variables.
If you have an inference context, use infcx.closure_sig()
.
impl<'a, 'gcx, 'tcx> ClosureSubsts<'tcx>
[src]
pub fn state_tys(
self,
def_id: DefId,
tcx: TyCtxt<'a, 'gcx, 'tcx>
) -> impl Iterator<Item = Ty<'tcx>> + 'a
[src]
self,
def_id: DefId,
tcx: TyCtxt<'a, 'gcx, 'tcx>
) -> impl Iterator<Item = Ty<'tcx>> + 'a
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
This returns the types of the MIR locals which had to be stored across suspension points. It is calculated in rustc_mir::transform::generator::StateTransform. All the types here must be in the tuple in GeneratorInterior.
pub fn field_tys(
self,
def_id: DefId,
tcx: TyCtxt<'a, 'gcx, 'tcx>
) -> impl Iterator<Item = Ty<'tcx>> + 'a
[src]
self,
def_id: DefId,
tcx: TyCtxt<'a, 'gcx, 'tcx>
) -> impl Iterator<Item = Ty<'tcx>> + 'a
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
This is the types of all the fields stored in a generator. It includes the upvars, state types and the state discriminant which is u32.
Trait Implementations
impl<'tcx> HashStable<StableHashingContext<'tcx>> for ClosureSubsts<'tcx>
[src]
fn hash_stable<W: StableHasherResult>(
&self,
__ctx: &mut StableHashingContext<'tcx>,
__hasher: &mut StableHasher<W>
)
[src]
&self,
__ctx: &mut StableHashingContext<'tcx>,
__hasher: &mut StableHasher<W>
)
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
impl<'gcx> TransNormalize<'gcx> for ClosureSubsts<'gcx>
[src]
fn trans_normalize<'a, 'tcx>(
&self,
infcx: &InferCtxt<'a, 'gcx, 'tcx>,
param_env: ParamEnv<'tcx>
) -> Self
[src]
&self,
infcx: &InferCtxt<'a, 'gcx, 'tcx>,
param_env: ParamEnv<'tcx>
) -> Self
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
impl<'tcx> Relate<'tcx> for ClosureSubsts<'tcx>
[src]
fn relate<'a, 'gcx, R>(
relation: &mut R,
a: &ClosureSubsts<'tcx>,
b: &ClosureSubsts<'tcx>
) -> RelateResult<'tcx, ClosureSubsts<'tcx>> where
R: TypeRelation<'a, 'gcx, 'tcx>,
'gcx: 'a + 'tcx,
'tcx: 'a,
[src]
relation: &mut R,
a: &ClosureSubsts<'tcx>,
b: &ClosureSubsts<'tcx>
) -> RelateResult<'tcx, ClosureSubsts<'tcx>> where
R: TypeRelation<'a, 'gcx, 'tcx>,
'gcx: 'a + 'tcx,
'tcx: 'a,
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
impl<'a, 'tcx> Lift<'tcx> for ClosureSubsts<'a>
[src]
type Lifted = ClosureSubsts<'tcx>
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn lift_to_tcx<'b, 'gcx>(
&self,
tcx: TyCtxt<'b, 'gcx, 'tcx>
) -> Option<Self::Lifted>
[src]
&self,
tcx: TyCtxt<'b, 'gcx, 'tcx>
) -> Option<Self::Lifted>
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
impl<'tcx> TypeFoldable<'tcx> for ClosureSubsts<'tcx>
[src]
fn super_fold_with<'gcx: 'tcx, F: TypeFolder<'gcx, 'tcx>>(
&self,
folder: &mut F
) -> Self
[src]
&self,
folder: &mut F
) -> Self
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn super_visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn fold_with<'gcx: 'tcx, F: TypeFolder<'gcx, 'tcx>>(
&self,
folder: &mut F
) -> Self
[src]
&self,
folder: &mut F
) -> Self
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn visit_with<V: TypeVisitor<'tcx>>(&self, visitor: &mut V) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn has_regions_escaping_depth(&self, depth: u32) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn has_escaping_regions(&self) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn has_type_flags(&self, flags: TypeFlags) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn has_projections(&self) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn references_error(&self) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn has_param_types(&self) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn has_self_ty(&self) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn has_infer_types(&self) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn needs_infer(&self) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn needs_subst(&self) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn has_re_skol(&self) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn has_closure_types(&self) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn has_erasable_regions(&self) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn is_normalized_for_trans(&self) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
fn is_global(&self) -> bool
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?
Indicates whether this value references only 'global' types/lifetimes that are the same regardless of what fn we are in. This is used for caching. Errs on the side of returning false. Read more
impl<'tcx> Copy for ClosureSubsts<'tcx>
[src]
impl<'tcx> Clone for ClosureSubsts<'tcx>
[src]
fn clone(&self) -> ClosureSubsts<'tcx>
[src]
Returns a copy of the value. Read more
fn clone_from(&mut self, source: &Self)
1.0.0[src]
Performs copy-assignment from source
. Read more
impl<'tcx> PartialEq for ClosureSubsts<'tcx>
[src]
fn eq(&self, __arg_0: &ClosureSubsts<'tcx>) -> bool
[src]
This method tests for self
and other
values to be equal, and is used by ==
. Read more
fn ne(&self, __arg_0: &ClosureSubsts<'tcx>) -> bool
[src]
This method tests for !=
.
impl<'tcx> Eq for ClosureSubsts<'tcx>
[src]
impl<'tcx> Hash for ClosureSubsts<'tcx>
[src]
fn hash<__H: Hasher>(&self, __arg_0: &mut __H)
[src]
Feeds this value into the given [Hasher
]. Read more
fn hash_slice<H>(data: &[Self], state: &mut H) where
H: Hasher,
1.3.0[src]
H: Hasher,
Feeds a slice of this type into the given [Hasher
]. Read more
impl<'tcx> Debug for ClosureSubsts<'tcx>
[src]
fn fmt(&self, __arg_0: &mut Formatter) -> Result
[src]
Formats the value using the given formatter. Read more
impl<'tcx> Encodable for ClosureSubsts<'tcx>
[src]
fn encode<__S: Encoder>(&self, __arg_0: &mut __S) -> Result<(), __S::Error>
[src]
🔬 This is a nightly-only experimental API. (rustc_private
)
this crate is being loaded from the sysroot, an unstable location; did you mean to load this crate from crates.io via Cargo.toml
instead?