Type Alias PlaceElem

Source
pub type PlaceElem<'tcx> = ProjectionElem<Local, Ty<'tcx>>;
Expand description

Alias for projections as they appear in places, where the base is a place and the index is a local.

Aliased Type§

enum PlaceElem<'tcx> {
    Deref,
    Field(FieldIdx, Ty<'tcx>),
    Index(Local),
    ConstantIndex {
        offset: u64,
        min_length: u64,
        from_end: bool,
    },
    Subslice {
        from: u64,
        to: u64,
        from_end: bool,
    },
    Downcast(Option<Symbol>, VariantIdx),
    OpaqueCast(Ty<'tcx>),
    UnwrapUnsafeBinder(Ty<'tcx>),
    Subtype(Ty<'tcx>),
}

Variants§

§

Deref

§

Field(FieldIdx, Ty<'tcx>)

A field (e.g., f in _1.f) is one variant of ProjectionElem. Conceptually, rustc can identify that a field projection refers to either two different regions of memory or the same one between the base and the ‘projection element’. Read more about projections in the rustc-dev-guide

§

Index(Local)

Index into a slice/array.

Note that this does not also dereference, and so it does not exactly correspond to slice indexing in Rust. In other words, in the below Rust code:

let x = &[1, 2, 3, 4];
let i = 2;
x[i];

The x[i] is turned into a Deref followed by an Index, not just an Index. The same thing is true of the ConstantIndex and Subslice projections below.

§

ConstantIndex

These indices are generated by slice patterns. Easiest to explain by example:

[X, _, .._, _, _] => { offset: 0, min_length: 4, from_end: false },
[_, X, .._, _, _] => { offset: 1, min_length: 4, from_end: false },
[_, _, .._, X, _] => { offset: 2, min_length: 4, from_end: true },
[_, _, .._, _, X] => { offset: 1, min_length: 4, from_end: true },

Fields

§offset: u64

index or -index (in Python terms), depending on from_end

§min_length: u64

The thing being indexed must be at least this long – otherwise, the projection is UB.

For arrays this is always the exact length.

§from_end: bool

Counting backwards from end? This is always false when indexing an array.

§

Subslice

These indices are generated by slice patterns.

If from_end is true slice[from..slice.len() - to]. Otherwise array[from..to].

Fields

§from: u64
§to: u64
§from_end: bool

Whether to counts from the start or end of the array/slice. For PlaceElems this is true if and only if the base is a slice. For ProjectionKind, this can also be true for arrays.

§

Downcast(Option<Symbol>, VariantIdx)

“Downcast” to a variant of an enum or a coroutine.

The included Symbol is the name of the variant, used for printing MIR.

This operation itself is never UB, all it does is change the type of the place.

§

OpaqueCast(Ty<'tcx>)

Like an explicit cast from an opaque type to a concrete type, but without requiring an intermediate variable.

§

UnwrapUnsafeBinder(Ty<'tcx>)

A transmute from an unsafe binder to the type that it wraps. This is a projection of a place, so it doesn’t necessarily constitute a move out of the binder.

§

Subtype(Ty<'tcx>)

A Subtype(T) projection is applied to any StatementKind::Assign where type of lvalue doesn’t match the type of rvalue, the primary goal is making subtyping explicit during optimizations and codegen.

This projection doesn’t impact the runtime behavior of the program except for potentially changing some type metadata of the interpreter or codegen backend.

This goal is achieved with mir_transform pass Subtyper, which runs right after borrowchecker, as we only care about subtyping that can affect trait selection and TypeId.

Layout§

Note: Most layout information is completely unstable and may even differ between compilations. The only exception is types with certain repr(...) attributes. Please see the Rust Reference's “Type Layout” chapter for details on type layout guarantees.

Size: 24 bytes

Size for each variant:

  • Deref: 0 bytes
  • Field: 15 bytes
  • Index: 7 bytes
  • ConstantIndex: 23 bytes
  • Subslice: 23 bytes
  • Downcast: 11 bytes
  • OpaqueCast: 15 bytes
  • UnwrapUnsafeBinder: 15 bytes
  • Subtype: 15 bytes

Implementations

Source§

impl<V, T> ProjectionElem<V, T>

Source

fn is_indirect(&self) -> bool

Returns true if the target of this projection may refer to a different region of memory than the base.

Source

pub fn is_stable_offset(&self) -> bool

Returns true if the target of this projection always refers to the same memory region whatever the state of the program.

Source

pub fn is_downcast_to(&self, v: VariantIdx) -> bool

Returns true if this is a Downcast projection with the given VariantIdx.

Source

pub fn is_field_to(&self, f: FieldIdx) -> bool

Returns true if this is a Field projection with the given index.

Source

pub fn can_use_in_debuginfo(&self) -> bool

Returns true if this is accepted inside VarDebugInfoContents::Place.

Trait Implementations

Source§

impl<V: Clone, T: Clone> Clone for ProjectionElem<V, T>

Source§

fn clone(&self) -> ProjectionElem<V, T>

Returns a copy of the value. Read more
1.0.0 · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl<V: Debug, T: Debug> Debug for ProjectionElem<V, T>

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl<V, T, __D: TyDecoder> Decodable<__D> for ProjectionElem<V, T>
where T: Decodable<__D>, V: Decodable<__D>,

Source§

fn decode(__decoder: &mut __D) -> Self

Source§

impl<V, T, __E: TyEncoder> Encodable<__E> for ProjectionElem<V, T>
where T: Encodable<__E>, V: Encodable<__E>,

Source§

fn encode(&self, __encoder: &mut __E)

Source§

impl<V: Hash, T: Hash> Hash for ProjectionElem<V, T>

Source§

fn hash<__H: Hasher>(&self, state: &mut __H)

Feeds this value into the given Hasher. Read more
1.3.0 · Source§

fn hash_slice<H>(data: &[Self], state: &mut H)
where H: Hasher, Self: Sized,

Feeds a slice of this type into the given Hasher. Read more
Source§

impl<'__ctx, V, T> HashStable<StableHashingContext<'__ctx>> for ProjectionElem<V, T>

Source§

fn hash_stable( &self, __hcx: &mut StableHashingContext<'__ctx>, __hasher: &mut StableHasher, )

Source§

impl<V: PartialEq, T: PartialEq> PartialEq for ProjectionElem<V, T>

Source§

fn eq(&self, other: &ProjectionElem<V, T>) -> bool

Tests for self and other values to be equal, and is used by ==.
1.0.0 · Source§

fn ne(&self, other: &Rhs) -> bool

Tests for !=. The default implementation is almost always sufficient, and should not be overridden without very good reason.
Source§

impl<'tcx, V, T> TypeFoldable<TyCtxt<'tcx>> for ProjectionElem<V, T>
where T: TypeFoldable<TyCtxt<'tcx>>, V: TypeFoldable<TyCtxt<'tcx>>,

Source§

fn try_fold_with<__F: FallibleTypeFolder<TyCtxt<'tcx>>>( self, __folder: &mut __F, ) -> Result<Self, __F::Error>

The entry point for folding. To fold a value t with a folder f call: t.try_fold_with(f). Read more
Source§

fn fold_with<F>(self, folder: &mut F) -> Self
where F: TypeFolder<I>,

A convenient alternative to try_fold_with for use with infallible folders. Do not override this method, to ensure coherence with try_fold_with.
Source§

impl<'tcx, V, T> TypeVisitable<TyCtxt<'tcx>> for ProjectionElem<V, T>
where T: TypeVisitable<TyCtxt<'tcx>>, V: TypeVisitable<TyCtxt<'tcx>>,

Source§

fn visit_with<__V: TypeVisitor<TyCtxt<'tcx>>>( &self, __visitor: &mut __V, ) -> __V::Result

The entry point for visiting. To visit a value t with a visitor v call: t.visit_with(v). Read more
Source§

impl<V: Copy, T: Copy> Copy for ProjectionElem<V, T>

Source§

impl<V: Eq, T: Eq> Eq for ProjectionElem<V, T>

Source§

impl<V, T> StructuralPartialEq for ProjectionElem<V, T>