Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use FieldIdx in various things related to aggregates #109849

Merged
merged 1 commit into from
Apr 3, 2023
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 3 additions & 2 deletions compiler/rustc_borrowck/src/diagnostics/mod.rs
Original file line number Diff line number Diff line change
@@ -6,6 +6,7 @@ use rustc_errors::{Applicability, Diagnostic};
use rustc_hir as hir;
use rustc_hir::def::{CtorKind, Namespace};
use rustc_hir::GeneratorKind;
use rustc_index::vec::IndexSlice;
use rustc_infer::infer::{LateBoundRegionConversionTime, TyCtxtInferExt};
use rustc_middle::mir::tcx::PlaceTy;
use rustc_middle::mir::{
@@ -825,7 +826,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
debug!("move_spans: def_id={:?} place={:?}", closure_def_id, place);
let places = &[Operand::Move(place)];
if let Some((args_span, generator_kind, capture_kind_span, path_span)) =
self.closure_span(closure_def_id, moved_place, places)
self.closure_span(closure_def_id, moved_place, IndexSlice::from_raw(places))
{
return ClosureUse {
generator_kind,
@@ -975,7 +976,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
&self,
def_id: LocalDefId,
target_place: PlaceRef<'tcx>,
places: &[Operand<'tcx>],
places: &IndexSlice<FieldIdx, Operand<'tcx>>,
) -> Option<(Span, Option<GeneratorKind>, Span, Span)> {
debug!(
"closure_span: def_id={:?} target_place={:?} places={:?}",
2 changes: 1 addition & 1 deletion compiler/rustc_borrowck/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1343,7 +1343,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
self.infcx.tcx.mir_borrowck(def_id);
debug!("{:?} used_mut_upvars={:?}", def_id, used_mut_upvars);
for field in used_mut_upvars {
self.propagate_closure_used_mut_upvar(&operands[field.index()]);
self.propagate_closure_used_mut_upvar(&operands[*field]);
}
}
AggregateKind::Adt(..)
19 changes: 9 additions & 10 deletions compiler/rustc_borrowck/src/type_check/mod.rs
Original file line number Diff line number Diff line change
@@ -14,7 +14,7 @@ use rustc_hir as hir;
use rustc_hir::def::DefKind;
use rustc_hir::def_id::LocalDefId;
use rustc_hir::lang_items::LangItem;
use rustc_index::vec::IndexVec;
use rustc_index::vec::{IndexSlice, IndexVec};
use rustc_infer::infer::canonical::QueryRegionConstraints;
use rustc_infer::infer::outlives::env::RegionBoundPairs;
use rustc_infer::infer::region_constraints::RegionConstraintData;
@@ -1716,7 +1716,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
fn aggregate_field_ty(
&mut self,
ak: &AggregateKind<'tcx>,
field_index: usize,
field_index: FieldIdx,
location: Location,
) -> Result<Ty<'tcx>, FieldAccessError> {
let tcx = self.tcx();
@@ -1725,16 +1725,15 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
AggregateKind::Adt(adt_did, variant_index, substs, _, active_field_index) => {
let def = tcx.adt_def(adt_did);
let variant = &def.variant(variant_index);
let adj_field_index =
FieldIdx::from_usize(active_field_index.unwrap_or(field_index));
let adj_field_index = active_field_index.unwrap_or(field_index);
if let Some(field) = variant.fields.get(adj_field_index) {
Ok(self.normalize(field.ty(tcx, substs), location))
} else {
Err(FieldAccessError::OutOfRange { field_count: variant.fields.len() })
}
}
AggregateKind::Closure(_, substs) => {
match substs.as_closure().upvar_tys().nth(field_index) {
match substs.as_closure().upvar_tys().nth(field_index.as_usize()) {
Some(ty) => Ok(ty),
None => Err(FieldAccessError::OutOfRange {
field_count: substs.as_closure().upvar_tys().count(),
@@ -1745,7 +1744,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
// It doesn't make sense to look at a field beyond the prefix;
// these require a variant index, and are not initialized in
// aggregate rvalues.
match substs.as_generator().prefix_tys().nth(field_index) {
match substs.as_generator().prefix_tys().nth(field_index.as_usize()) {
Some(ty) => Ok(ty),
None => Err(FieldAccessError::OutOfRange {
field_count: substs.as_generator().prefix_tys().count(),
@@ -2350,7 +2349,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
body: &Body<'tcx>,
rvalue: &Rvalue<'tcx>,
aggregate_kind: &AggregateKind<'tcx>,
operands: &[Operand<'tcx>],
operands: &IndexSlice<FieldIdx, Operand<'tcx>>,
location: Location,
) {
let tcx = self.tcx();
@@ -2362,16 +2361,16 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
return;
}

for (i, operand) in operands.iter().enumerate() {
for (i, operand) in operands.iter_enumerated() {
let field_ty = match self.aggregate_field_ty(aggregate_kind, i, location) {
Ok(field_ty) => field_ty,
Err(FieldAccessError::OutOfRange { field_count }) => {
span_mirbug!(
self,
rvalue,
"accessed field #{} but variant only has {}",
i,
field_count
i.as_u32(),
field_count,
);
continue;
}
7 changes: 4 additions & 3 deletions compiler/rustc_codegen_cranelift/src/base.rs
Original file line number Diff line number Diff line change
@@ -802,14 +802,15 @@ fn codegen_stmt<'tcx>(
if active_field_index.is_some() {
assert_eq!(operands.len(), 1);
}
for (i, operand) in operands.iter().enumerate() {
for (i, operand) in operands.iter_enumerated() {
let operand = codegen_operand(fx, operand);
let field_index = active_field_index.unwrap_or(i);
let to = if let mir::AggregateKind::Array(_) = **kind {
let index = fx.bcx.ins().iconst(fx.pointer_type, field_index as i64);
let array_index = i64::from(field_index.as_u32());
let index = fx.bcx.ins().iconst(fx.pointer_type, array_index);
variant_dest.place_index(fx, index)
} else {
variant_dest.place_field(fx, FieldIdx::new(field_index))
variant_dest.place_field(fx, field_index)
};
to.write_cvalue(fx, operand);
}
6 changes: 3 additions & 3 deletions compiler/rustc_codegen_ssa/src/base.rs
Original file line number Diff line number Diff line change
@@ -306,9 +306,9 @@ pub fn coerce_unsized_into<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>(
(&ty::Adt(def_a, _), &ty::Adt(def_b, _)) => {
assert_eq!(def_a, def_b);

for i in 0..def_a.variant(FIRST_VARIANT).fields.len() {
let src_f = src.project_field(bx, i);
let dst_f = dst.project_field(bx, i);
for i in def_a.variant(FIRST_VARIANT).fields.indices() {
let src_f = src.project_field(bx, i.as_usize());
let dst_f = dst.project_field(bx, i.as_usize());

if dst_f.layout.is_zst() {
continue;
6 changes: 3 additions & 3 deletions compiler/rustc_codegen_ssa/src/mir/rvalue.rs
Original file line number Diff line number Diff line change
@@ -123,16 +123,16 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
if active_field_index.is_some() {
assert_eq!(operands.len(), 1);
}
for (i, operand) in operands.iter().enumerate() {
for (i, operand) in operands.iter_enumerated() {
let op = self.codegen_operand(bx, operand);
// Do not generate stores and GEPis for zero-sized fields.
if !op.layout.is_zst() {
let field_index = active_field_index.unwrap_or(i);
let field = if let mir::AggregateKind::Array(_) = **kind {
let llindex = bx.cx().const_usize(field_index as u64);
let llindex = bx.cx().const_usize(field_index.as_u32().into());
variant_dest.project_index(bx, llindex)
} else {
variant_dest.project_field(bx, field_index)
variant_dest.project_field(bx, field_index.as_usize())
};
op.val.store(bx, field);
}
9 changes: 5 additions & 4 deletions compiler/rustc_const_eval/src/interpret/place.rs
Original file line number Diff line number Diff line change
@@ -5,10 +5,11 @@
use either::{Either, Left, Right};

use rustc_ast::Mutability;
use rustc_index::vec::IndexSlice;
use rustc_middle::mir;
use rustc_middle::ty;
use rustc_middle::ty::layout::{LayoutOf, TyAndLayout};
use rustc_target::abi::{self, Abi, Align, HasDataLayout, Size, FIRST_VARIANT};
use rustc_target::abi::{self, Abi, Align, FieldIdx, HasDataLayout, Size, FIRST_VARIANT};

use super::{
alloc_range, mir_assign_valid_types, AllocId, AllocRef, AllocRefMut, CheckInAllocMsg,
@@ -787,7 +788,7 @@ where
pub fn write_aggregate(
&mut self,
kind: &mir::AggregateKind<'tcx>,
operands: &[mir::Operand<'tcx>],
operands: &IndexSlice<FieldIdx, mir::Operand<'tcx>>,
dest: &PlaceTy<'tcx, M::Provenance>,
) -> InterpResult<'tcx> {
self.write_uninit(&dest)?;
@@ -801,9 +802,9 @@ where
if active_field_index.is_some() {
assert_eq!(operands.len(), 1);
}
for (field_index, operand) in operands.iter().enumerate() {
for (field_index, operand) in operands.iter_enumerated() {
let field_index = active_field_index.unwrap_or(field_index);
let field_dest = self.place_field(&variant_dest, field_index)?;
let field_dest = self.place_field(&variant_dest, field_index.as_usize())?;
let op = self.eval_operand(operand, Some(field_dest.layout))?;
self.copy_op(&op, &field_dest, /*allow_transmute*/ false)?;
}
6 changes: 6 additions & 0 deletions compiler/rustc_index/src/vec.rs
Original file line number Diff line number Diff line change
@@ -93,6 +93,12 @@ impl<I: Idx, T: fmt::Debug> fmt::Debug for IndexVec<I, T> {
}
}

impl<I: Idx, T: fmt::Debug> fmt::Debug for IndexSlice<I, T> {
fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
fmt::Debug::fmt(&self.raw, fmt)
}
}

impl<I: Idx, T> IndexVec<I, T> {
#[inline]
pub fn new() -> Self {
7 changes: 4 additions & 3 deletions compiler/rustc_middle/src/mir/syntax.rs
Original file line number Diff line number Diff line change
@@ -16,6 +16,7 @@ use rustc_ast::{InlineAsmOptions, InlineAsmTemplatePiece};
use rustc_hir::def_id::DefId;
use rustc_hir::{self as hir};
use rustc_hir::{self, GeneratorKind};
use rustc_index::vec::IndexVec;
use rustc_target::abi::{FieldIdx, VariantIdx};

use rustc_ast::Mutability;
@@ -1125,7 +1126,7 @@ pub enum Rvalue<'tcx> {
///
/// Disallowed after deaggregation for all aggregate kinds except `Array` and `Generator`. After
/// generator lowering, `Generator` aggregate kinds are disallowed too.
Aggregate(Box<AggregateKind<'tcx>>, Vec<Operand<'tcx>>),
Aggregate(Box<AggregateKind<'tcx>>, IndexVec<FieldIdx, Operand<'tcx>>),

/// Transmutes a `*mut u8` into shallow-initialized `Box<T>`.
///
@@ -1186,7 +1187,7 @@ pub enum AggregateKind<'tcx> {
/// active field number and is present only for union expressions
/// -- e.g., for a union expression `SomeUnion { c: .. }`, the
/// active field index would identity the field `c`
Adt(DefId, VariantIdx, SubstsRef<'tcx>, Option<UserTypeAnnotationIndex>, Option<usize>),
Adt(DefId, VariantIdx, SubstsRef<'tcx>, Option<UserTypeAnnotationIndex>, Option<FieldIdx>),

Closure(DefId, SubstsRef<'tcx>),
Generator(DefId, SubstsRef<'tcx>, hir::Movability),
@@ -1263,7 +1264,7 @@ pub enum BinOp {
mod size_asserts {
use super::*;
// tidy-alphabetical-start
static_assert_size!(AggregateKind<'_>, 40);
static_assert_size!(AggregateKind<'_>, 32);
static_assert_size!(Operand<'_>, 24);
static_assert_size!(Place<'_>, 16);
static_assert_size!(PlaceElem<'_>, 24);
Original file line number Diff line number Diff line change
@@ -185,7 +185,7 @@ impl<'tcx, 'body> ParseCtxt<'tcx, 'body> {
},
ExprKind::Adt(box AdtExpr{ adt_def, variant_index, substs, fields, .. }) => {
let is_union = adt_def.is_union();
let active_field_index = is_union.then(|| fields[0].name.index());
let active_field_index = is_union.then(|| fields[0].name);

Ok(Rvalue::Aggregate(
Box::new(AggregateKind::Adt(adt_def.did(), *variant_index, substs, None, active_field_index)),
13 changes: 6 additions & 7 deletions compiler/rustc_mir_build/src/build/expr/as_rvalue.rs
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
//! See docs in `build/expr/mod.rs`.

use rustc_index::vec::Idx;
use rustc_index::vec::{Idx, IndexVec};
use rustc_middle::ty::util::IntTypeExt;
use rustc_target::abi::{Abi, Primitive};
use rustc_target::abi::{Abi, FieldIdx, Primitive};

use crate::build::expr::as_place::PlaceBase;
use crate::build::expr::category::{Category, RvalueFunc};
@@ -17,7 +17,6 @@ use rustc_middle::thir::*;
use rustc_middle::ty::cast::{mir_cast_kind, CastTy};
use rustc_middle::ty::{self, Ty, UpvarSubsts};
use rustc_span::Span;
use rustc_target::abi::FieldIdx;

impl<'a, 'tcx> Builder<'a, 'tcx> {
/// Returns an rvalue suitable for use until the end of the current
@@ -327,7 +326,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {

// first process the set of fields
let el_ty = expr.ty.sequence_element_type(this.tcx);
let fields: Vec<_> = fields
let fields: IndexVec<FieldIdx, _> = fields
.into_iter()
.copied()
.map(|f| {
@@ -348,7 +347,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
ExprKind::Tuple { ref fields } => {
// see (*) above
// first process the set of fields
let fields: Vec<_> = fields
let fields: IndexVec<FieldIdx, _> = fields
.into_iter()
.copied()
.map(|f| {
@@ -402,7 +401,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
}

// see (*) above
let operands: Vec<_> = upvars
let operands: IndexVec<FieldIdx, _> = upvars
.into_iter()
.copied()
.map(|upvar| {
@@ -710,7 +709,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
}
this.record_operands_moved(&[value_operand]);
}
block.and(Rvalue::Aggregate(Box::new(AggregateKind::Array(elem_ty)), Vec::new()))
block.and(Rvalue::Aggregate(Box::new(AggregateKind::Array(elem_ty)), IndexVec::new()))
}

fn limit_capture_mutability(
11 changes: 4 additions & 7 deletions compiler/rustc_mir_build/src/build/expr/into.rs
Original file line number Diff line number Diff line change
@@ -6,11 +6,9 @@ use rustc_ast::InlineAsmOptions;
use rustc_data_structures::fx::FxHashMap;
use rustc_data_structures::stack::ensure_sufficient_stack;
use rustc_hir as hir;
use rustc_index::vec::Idx;
use rustc_middle::mir::*;
use rustc_middle::thir::*;
use rustc_middle::ty::CanonicalUserTypeAnnotation;
use rustc_target::abi::FieldIdx;
use std::iter;

impl<'a, 'tcx> Builder<'a, 'tcx> {
@@ -320,7 +318,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
// See the notes for `ExprKind::Array` in `as_rvalue` and for
// `ExprKind::Borrow` above.
let is_union = adt_def.is_union();
let active_field_index = is_union.then(|| fields[0].name.index());
let active_field_index = is_union.then(|| fields[0].name);

let scope = this.local_scope();

@@ -344,10 +342,9 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
})
.collect();

let field_names: Vec<_> =
(0..adt_def.variant(variant_index).fields.len()).map(FieldIdx::new).collect();
let field_names = adt_def.variant(variant_index).fields.indices();

let fields: Vec<_> = if let Some(FruInfo { base, field_types }) = base {
let fields = if let Some(FruInfo { base, field_types }) = base {
let place_builder =
unpack!(block = this.as_place_builder(block, &this.thir[*base]));

@@ -364,7 +361,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
})
.collect()
} else {
field_names.iter().filter_map(|n| fields_map.get(n).cloned()).collect()
field_names.filter_map(|n| fields_map.get(&n).cloned()).collect()
};

let inferred_ty = expr.ty;
4 changes: 2 additions & 2 deletions compiler/rustc_mir_transform/src/generator.rs
Original file line number Diff line number Diff line change
@@ -274,7 +274,7 @@ impl<'tcx> TransformVisitor<'tcx> {
statements.push(Statement {
kind: StatementKind::Assign(Box::new((
Place::return_place(),
Rvalue::Aggregate(Box::new(kind), vec![]),
Rvalue::Aggregate(Box::new(kind), IndexVec::new()),
))),
source_info,
});
@@ -287,7 +287,7 @@ impl<'tcx> TransformVisitor<'tcx> {
statements.push(Statement {
kind: StatementKind::Assign(Box::new((
Place::return_place(),
Rvalue::Aggregate(Box::new(kind), vec![val]),
Rvalue::Aggregate(Box::new(kind), IndexVec::from_iter([val])),
))),
source_info,
});