1
Fork 0

intern offsetof fields

This commit is contained in:
DrMeepster 2023-03-11 16:01:25 -08:00
parent 511e457c4b
commit 61f23e0003
8 changed files with 33 additions and 11 deletions

View file

@ -719,7 +719,7 @@ impl<'a, 'tcx> Visitor<'tcx> for TypeChecker<'a, 'tcx> {
let mut current_ty = *container; let mut current_ty = *container;
for &field in fields { for field in fields.iter() {
match current_ty.kind() { match current_ty.kind() {
ty::Tuple(fields) => { ty::Tuple(fields) => {
let Some(&f_ty) = fields.get(field.as_usize()) else { let Some(&f_ty) = fields.get(field.as_usize()) else {

View file

@ -1115,7 +1115,7 @@ pub enum Rvalue<'tcx> {
CheckedBinaryOp(BinOp, Box<(Operand<'tcx>, Operand<'tcx>)>), CheckedBinaryOp(BinOp, Box<(Operand<'tcx>, Operand<'tcx>)>),
/// Computes a value as described by the operation. /// Computes a value as described by the operation.
NullaryOp(NullOp, Ty<'tcx>), NullaryOp(NullOp<'tcx>, Ty<'tcx>),
/// Exactly like `BinaryOp`, but less operands. /// Exactly like `BinaryOp`, but less operands.
/// ///
@ -1212,13 +1212,13 @@ pub enum AggregateKind<'tcx> {
} }
#[derive(Clone, Debug, PartialEq, Eq, TyEncodable, TyDecodable, Hash, HashStable)] #[derive(Clone, Debug, PartialEq, Eq, TyEncodable, TyDecodable, Hash, HashStable)]
pub enum NullOp { pub enum NullOp<'tcx> {
/// Returns the size of a value of that type /// Returns the size of a value of that type
SizeOf, SizeOf,
/// Returns the minimum alignment of a type /// Returns the minimum alignment of a type
AlignOf, AlignOf,
/// Returns the offset of a field /// Returns the offset of a field
OffsetOf(Vec<FieldIdx>), OffsetOf(&'tcx List<FieldIdx>),
} }
#[derive(Copy, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)] #[derive(Copy, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
@ -1288,6 +1288,6 @@ mod size_asserts {
static_assert_size!(Operand<'_>, 24); static_assert_size!(Operand<'_>, 24);
static_assert_size!(Place<'_>, 16); static_assert_size!(Place<'_>, 16);
static_assert_size!(PlaceElem<'_>, 24); static_assert_size!(PlaceElem<'_>, 24);
static_assert_size!(Rvalue<'_>, 48); static_assert_size!(Rvalue<'_>, 40);
// tidy-alphabetical-end // tidy-alphabetical-end
} }

View file

@ -16,7 +16,6 @@ TrivialTypeTraversalAndLiftImpls! {
UserTypeAnnotationIndex, UserTypeAnnotationIndex,
BorrowKind, BorrowKind,
CastKind, CastKind,
NullOp,
hir::Movability, hir::Movability,
BasicBlock, BasicBlock,
SwitchTargets, SwitchTargets,
@ -26,6 +25,7 @@ TrivialTypeTraversalAndLiftImpls! {
TrivialTypeTraversalImpls! { TrivialTypeTraversalImpls! {
ConstValue<'tcx>, ConstValue<'tcx>,
NullOp<'tcx>,
} }
impl<'tcx> TypeFoldable<TyCtxt<'tcx>> for &'tcx [InlineAsmTemplatePiece] { impl<'tcx> TypeFoldable<TyCtxt<'tcx>> for &'tcx [InlineAsmTemplatePiece] {

View file

@ -20,7 +20,7 @@ use rustc_middle::mir::interpret::AllocId;
use rustc_middle::mir::{self, BinOp, BorrowKind, FakeReadCause, Mutability, UnOp}; use rustc_middle::mir::{self, BinOp, BorrowKind, FakeReadCause, Mutability, UnOp};
use rustc_middle::ty::adjustment::PointerCast; use rustc_middle::ty::adjustment::PointerCast;
use rustc_middle::ty::subst::SubstsRef; use rustc_middle::ty::subst::SubstsRef;
use rustc_middle::ty::{self, AdtDef, FnSig, Ty, UpvarSubsts}; use rustc_middle::ty::{self, AdtDef, FnSig, List, Ty, UpvarSubsts};
use rustc_middle::ty::{CanonicalUserType, CanonicalUserTypeAnnotation}; use rustc_middle::ty::{CanonicalUserType, CanonicalUserTypeAnnotation};
use rustc_span::def_id::LocalDefId; use rustc_span::def_id::LocalDefId;
use rustc_span::{sym, Span, Symbol, DUMMY_SP}; use rustc_span::{sym, Span, Symbol, DUMMY_SP};
@ -484,7 +484,7 @@ pub enum ExprKind<'tcx> {
/// Field offset (`offset_of!`) /// Field offset (`offset_of!`)
OffsetOf { OffsetOf {
container: Ty<'tcx>, container: Ty<'tcx>,
fields: Vec<FieldIdx>, fields: &'tcx List<FieldIdx>,
}, },
/// An expression taking a reference to a thread local. /// An expression taking a reference to a thread local.
ThreadLocalRef(DefId), ThreadLocalRef(DefId),

View file

@ -19,6 +19,7 @@ use rustc_data_structures::fx::FxHashMap;
use rustc_middle::ty::TyCtxt; use rustc_middle::ty::TyCtxt;
use rustc_serialize::{Decodable, Encodable}; use rustc_serialize::{Decodable, Encodable};
use rustc_span::Span; use rustc_span::Span;
use rustc_target::abi::FieldIdx;
pub use rustc_type_ir::{TyDecoder, TyEncoder}; pub use rustc_type_ir::{TyDecoder, TyEncoder};
use std::hash::Hash; use std::hash::Hash;
use std::intrinsics; use std::intrinsics;
@ -401,6 +402,15 @@ impl<'tcx, D: TyDecoder<I = TyCtxt<'tcx>>> RefDecodable<'tcx, D> for ty::List<ty
} }
} }
impl<'tcx, D: TyDecoder<I = TyCtxt<'tcx>>> RefDecodable<'tcx, D> for ty::List<FieldIdx> {
fn decode(decoder: &mut D) -> &'tcx Self {
let len = decoder.read_usize();
decoder
.interner()
.mk_fields_from_iter((0..len).map::<FieldIdx, _>(|_| Decodable::decode(decoder)))
}
}
impl_decodable_via_ref! { impl_decodable_via_ref! {
&'tcx ty::TypeckResults<'tcx>, &'tcx ty::TypeckResults<'tcx>,
&'tcx ty::List<Ty<'tcx>>, &'tcx ty::List<Ty<'tcx>>,
@ -412,6 +422,7 @@ impl_decodable_via_ref! {
&'tcx mir::coverage::CodeRegion, &'tcx mir::coverage::CodeRegion,
&'tcx ty::List<ty::BoundVariableKind>, &'tcx ty::List<ty::BoundVariableKind>,
&'tcx ty::List<ty::Predicate<'tcx>>, &'tcx ty::List<ty::Predicate<'tcx>>,
&'tcx ty::List<FieldIdx>,
} }
#[macro_export] #[macro_export]

View file

@ -155,6 +155,7 @@ pub struct CtxtInterners<'tcx> {
layout: InternedSet<'tcx, LayoutS>, layout: InternedSet<'tcx, LayoutS>,
adt_def: InternedSet<'tcx, AdtDefData>, adt_def: InternedSet<'tcx, AdtDefData>,
external_constraints: InternedSet<'tcx, ExternalConstraintsData<'tcx>>, external_constraints: InternedSet<'tcx, ExternalConstraintsData<'tcx>>,
fields: InternedSet<'tcx, List<FieldIdx>>,
} }
impl<'tcx> CtxtInterners<'tcx> { impl<'tcx> CtxtInterners<'tcx> {
@ -178,6 +179,7 @@ impl<'tcx> CtxtInterners<'tcx> {
layout: Default::default(), layout: Default::default(),
adt_def: Default::default(), adt_def: Default::default(),
external_constraints: Default::default(), external_constraints: Default::default(),
fields: Default::default(),
} }
} }
@ -1585,6 +1587,7 @@ slice_interners!(
projs: pub mk_projs(ProjectionKind), projs: pub mk_projs(ProjectionKind),
place_elems: pub mk_place_elems(PlaceElem<'tcx>), place_elems: pub mk_place_elems(PlaceElem<'tcx>),
bound_variable_kinds: pub mk_bound_variable_kinds(ty::BoundVariableKind), bound_variable_kinds: pub mk_bound_variable_kinds(ty::BoundVariableKind),
fields: pub mk_fields(FieldIdx),
); );
impl<'tcx> TyCtxt<'tcx> { impl<'tcx> TyCtxt<'tcx> {
@ -2253,6 +2256,14 @@ impl<'tcx> TyCtxt<'tcx> {
T::collect_and_apply(iter, |xs| self.mk_place_elems(xs)) T::collect_and_apply(iter, |xs| self.mk_place_elems(xs))
} }
pub fn mk_fields_from_iter<I, T>(self, iter: I) -> T::Output
where
I: Iterator<Item = T>,
T: CollectAndApply<FieldIdx, &'tcx List<FieldIdx>>,
{
T::collect_and_apply(iter, |xs| self.mk_fields(xs))
}
pub fn mk_substs_trait( pub fn mk_substs_trait(
self, self,
self_ty: Ty<'tcx>, self_ty: Ty<'tcx>,

View file

@ -481,8 +481,8 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
})))) }))))
} }
ExprKind::OffsetOf { container, ref fields } => { ExprKind::OffsetOf { container, fields } => {
block.and(Rvalue::NullaryOp(NullOp::OffsetOf(fields.clone()), container)) block.and(Rvalue::NullaryOp(NullOp::OffsetOf(fields), container))
} }
ExprKind::Literal { .. } ExprKind::Literal { .. }

View file

@ -667,7 +667,7 @@ impl<'tcx> Cx<'tcx> {
hir::ExprKind::OffsetOf(_, _) => { hir::ExprKind::OffsetOf(_, _) => {
let data = self.typeck_results.offset_of_data(); let data = self.typeck_results.offset_of_data();
let &(container, ref indices) = data.get(expr.hir_id).unwrap(); let &(container, ref indices) = data.get(expr.hir_id).unwrap();
let fields = indices.iter().copied().collect(); let fields = tcx.mk_fields_from_iter(indices.iter().copied());
ExprKind::OffsetOf { container, fields } ExprKind::OffsetOf { container, fields }
} }