summaryrefslogtreecommitdiffstats
path: root/compiler/rustc_borrowck/src/type_check/mod.rs
diff options
context:
space:
mode:
Diffstat (limited to 'compiler/rustc_borrowck/src/type_check/mod.rs')
-rw-r--r--compiler/rustc_borrowck/src/type_check/mod.rs170
1 files changed, 77 insertions, 93 deletions
diff --git a/compiler/rustc_borrowck/src/type_check/mod.rs b/compiler/rustc_borrowck/src/type_check/mod.rs
index a49da3da6..2f10e30be 100644
--- a/compiler/rustc_borrowck/src/type_check/mod.rs
+++ b/compiler/rustc_borrowck/src/type_check/mod.rs
@@ -9,13 +9,12 @@ use either::Either;
use hir::OpaqueTyOrigin;
use rustc_data_structures::frozen::Frozen;
-use rustc_data_structures::fx::{FxHashMap, FxHashSet};
-use rustc_data_structures::vec_map::VecMap;
+use rustc_data_structures::fx::{FxIndexMap, FxIndexSet};
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::{Idx, 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;
@@ -36,8 +35,9 @@ use rustc_middle::ty::{
OpaqueHiddenType, OpaqueTypeKey, RegionVid, Ty, TyCtxt, UserType, UserTypeAnnotationIndex,
};
use rustc_span::def_id::CRATE_DEF_ID;
+use rustc_span::symbol::sym;
use rustc_span::{Span, DUMMY_SP};
-use rustc_target::abi::VariantIdx;
+use rustc_target::abi::{FieldIdx, FIRST_VARIANT};
use rustc_trait_selection::traits::query::type_op::custom::scrape_region_constraints;
use rustc_trait_selection::traits::query::type_op::custom::CustomTypeOp;
use rustc_trait_selection::traits::query::type_op::{TypeOp, TypeOpOutput};
@@ -56,7 +56,6 @@ use crate::{
facts::AllFacts,
location::LocationTable,
member_constraints::MemberConstraintSet,
- nll::ToRegionVid,
path_utils,
region_infer::values::{
LivenessValues, PlaceholderIndex, PlaceholderIndices, RegionValueElements,
@@ -126,7 +125,7 @@ pub(crate) fn type_check<'mir, 'tcx>(
infcx: &BorrowckInferCtxt<'_, 'tcx>,
param_env: ty::ParamEnv<'tcx>,
body: &Body<'tcx>,
- promoted: &IndexVec<Promoted, Body<'tcx>>,
+ promoted: &IndexSlice<Promoted, Body<'tcx>>,
universal_regions: &Rc<UniversalRegions<'tcx>>,
location_table: &LocationTable,
borrow_set: &BorrowSet<'tcx>,
@@ -145,7 +144,7 @@ pub(crate) fn type_check<'mir, 'tcx>(
outlives_constraints: OutlivesConstraintSet::default(),
member_constraints: MemberConstraintSet::default(),
type_tests: Vec::default(),
- universe_causes: FxHashMap::default(),
+ universe_causes: FxIndexMap::default(),
};
let CreateResult {
@@ -293,7 +292,7 @@ enum FieldAccessError {
/// is a problem.
struct TypeVerifier<'a, 'b, 'tcx> {
cx: &'a mut TypeChecker<'b, 'tcx>,
- promoted: &'b IndexVec<Promoted, Body<'tcx>>,
+ promoted: &'b IndexSlice<Promoted, Body<'tcx>>,
last_span: Span,
errors_reported: bool,
}
@@ -494,7 +493,7 @@ impl<'a, 'b, 'tcx> Visitor<'tcx> for TypeVerifier<'a, 'b, 'tcx> {
impl<'a, 'b, 'tcx> TypeVerifier<'a, 'b, 'tcx> {
fn new(
cx: &'a mut TypeChecker<'b, 'tcx>,
- promoted: &'b IndexVec<Promoted, Body<'tcx>>,
+ promoted: &'b IndexSlice<Promoted, Body<'tcx>>,
) -> Self {
TypeVerifier { promoted, last_span: cx.body.span, cx, errors_reported: false }
}
@@ -772,11 +771,14 @@ impl<'a, 'b, 'tcx> TypeVerifier<'a, 'b, 'tcx> {
match context {
PlaceContext::MutatingUse(_) => ty::Invariant,
- PlaceContext::NonUse(StorageDead | StorageLive | VarDebugInfo) => ty::Invariant,
+ PlaceContext::NonUse(StorageDead | StorageLive | PlaceMention | VarDebugInfo) => {
+ ty::Invariant
+ }
PlaceContext::NonMutatingUse(
- Inspect | Copy | Move | SharedBorrow | ShallowBorrow | UniqueBorrow | AddressOf
- | Projection,
- ) => ty::Covariant,
+ Inspect | Copy | Move | SharedBorrow | ShallowBorrow | AddressOf | Projection
+ ) => {
+ ty::Covariant
+ },
PlaceContext::NonUse(AscribeUserTy) => ty::Covariant,
}
}
@@ -785,7 +787,7 @@ impl<'a, 'b, 'tcx> TypeVerifier<'a, 'b, 'tcx> {
&mut self,
parent: &dyn fmt::Debug,
base_ty: PlaceTy<'tcx>,
- field: Field,
+ field: FieldIdx,
location: Location,
) -> Result<Ty<'tcx>, FieldAccessError> {
let tcx = self.tcx();
@@ -811,7 +813,7 @@ impl<'a, 'b, 'tcx> TypeVerifier<'a, 'b, 'tcx> {
},
PlaceTy { ty, variant_index: None } => match *ty.kind() {
ty::Adt(adt_def, substs) if !adt_def.is_enum() => {
- (adt_def.variant(VariantIdx::new(0)), substs)
+ (adt_def.variant(FIRST_VARIANT), substs)
}
ty::Closure(_, substs) => {
return match substs
@@ -853,7 +855,7 @@ impl<'a, 'b, 'tcx> TypeVerifier<'a, 'b, 'tcx> {
},
};
- if let Some(field) = variant.fields.get(field.index()) {
+ if let Some(field) = variant.fields.get(field) {
Ok(self.cx.normalize(field.ty(tcx, substs), location))
} else {
Err(FieldAccessError::OutOfRange { field_count: variant.fields.len() })
@@ -875,7 +877,7 @@ struct TypeChecker<'a, 'tcx> {
user_type_annotations: &'a CanonicalUserTypeAnnotations<'tcx>,
region_bound_pairs: &'a RegionBoundPairs<'tcx>,
implicit_region_bound: ty::Region<'tcx>,
- reported_errors: FxHashSet<(Ty<'tcx>, Span)>,
+ reported_errors: FxIndexSet<(Ty<'tcx>, Span)>,
borrowck_context: &'a mut BorrowCheckContext<'a, 'tcx>,
}
@@ -892,7 +894,7 @@ pub(crate) struct MirTypeckResults<'tcx> {
pub(crate) constraints: MirTypeckRegionConstraints<'tcx>,
pub(crate) universal_region_relations: Frozen<UniversalRegionRelations<'tcx>>,
pub(crate) opaque_type_values:
- VecMap<OpaqueTypeKey<'tcx>, (OpaqueHiddenType<'tcx>, OpaqueTyOrigin)>,
+ FxIndexMap<OpaqueTypeKey<'tcx>, (OpaqueHiddenType<'tcx>, OpaqueTyOrigin)>,
}
/// A collection of region constraints that must be satisfied for the
@@ -925,7 +927,7 @@ pub(crate) struct MirTypeckRegionConstraints<'tcx> {
pub(crate) member_constraints: MemberConstraintSet<'tcx, RegionVid>,
- pub(crate) universe_causes: FxHashMap<ty::UniverseIndex, UniverseInfo<'tcx>>,
+ pub(crate) universe_causes: FxIndexMap<ty::UniverseIndex, UniverseInfo<'tcx>>,
pub(crate) type_tests: Vec<TypeTest<'tcx>>,
}
@@ -1178,10 +1180,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
}
}
Some(l)
- if matches!(
- body.local_decls[l].local_info,
- Some(box LocalInfo::AggregateTemp)
- ) =>
+ if matches!(body.local_decls[l].local_info(), LocalInfo::AggregateTemp) =>
{
ConstraintCategory::Usage
}
@@ -1282,6 +1281,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
| StatementKind::Retag { .. }
| StatementKind::Coverage(..)
| StatementKind::ConstEvalCounter
+ | StatementKind::PlaceMention(..)
| StatementKind::Nop => {}
StatementKind::Deinit(..) | StatementKind::SetDiscriminant { .. } => {
bug!("Statement not allowed in this MIR phase")
@@ -1301,7 +1301,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
match &term.kind {
TerminatorKind::Goto { .. }
| TerminatorKind::Resume
- | TerminatorKind::Abort
+ | TerminatorKind::Terminate
| TerminatorKind::Return
| TerminatorKind::GeneratorDrop
| TerminatorKind::Unreachable
@@ -1312,24 +1312,6 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
// no checks needed for these
}
- TerminatorKind::DropAndReplace { place, value, target: _, unwind: _ } => {
- let place_ty = place.ty(body, tcx).ty;
- let rv_ty = value.ty(body, tcx);
-
- let locations = term_location.to_locations();
- if let Err(terr) =
- self.sub_types(rv_ty, place_ty, locations, ConstraintCategory::Assignment)
- {
- span_mirbug!(
- self,
- term,
- "bad DropAndReplace ({:?} = {:?}): {:?}",
- place_ty,
- rv_ty,
- terr
- );
- }
- }
TerminatorKind::SwitchInt { discr, .. } => {
self.check_operand(discr, term_location);
@@ -1357,20 +1339,13 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
};
let (sig, map) = tcx.replace_late_bound_regions(sig, |br| {
use crate::renumber::{BoundRegionInfo, RegionCtxt};
- use rustc_span::Symbol;
let region_ctxt_fn = || {
let reg_info = match br.kind {
- ty::BoundRegionKind::BrAnon(_, Some(span)) => {
- BoundRegionInfo::Span(span)
- }
- ty::BoundRegionKind::BrAnon(..) => {
- BoundRegionInfo::Name(Symbol::intern("anon"))
- }
+ ty::BoundRegionKind::BrAnon(Some(span)) => BoundRegionInfo::Span(span),
+ ty::BoundRegionKind::BrAnon(..) => BoundRegionInfo::Name(sym::anon),
ty::BoundRegionKind::BrNamed(_, name) => BoundRegionInfo::Name(name),
- ty::BoundRegionKind::BrEnv => {
- BoundRegionInfo::Name(Symbol::intern("env"))
- }
+ ty::BoundRegionKind::BrEnv => BoundRegionInfo::Name(sym::env),
};
RegionCtxt::LateBound(reg_info)
@@ -1603,7 +1578,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
span_mirbug!(self, block_data, "resume on non-cleanup block!")
}
}
- TerminatorKind::Abort => {
+ TerminatorKind::Terminate => {
if !is_cleanup {
span_mirbug!(self, block_data, "abort on non-cleanup block!")
}
@@ -1629,26 +1604,15 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
}
TerminatorKind::Unreachable => {}
TerminatorKind::Drop { target, unwind, .. }
- | TerminatorKind::DropAndReplace { target, unwind, .. }
- | TerminatorKind::Assert { target, cleanup: unwind, .. } => {
+ | TerminatorKind::Assert { target, unwind, .. } => {
self.assert_iscleanup(body, block_data, target, is_cleanup);
- if let Some(unwind) = unwind {
- if is_cleanup {
- span_mirbug!(self, block_data, "unwind on cleanup block")
- }
- self.assert_iscleanup(body, block_data, unwind, true);
- }
+ self.assert_iscleanup_unwind(body, block_data, unwind, is_cleanup);
}
- TerminatorKind::Call { ref target, cleanup, .. } => {
+ TerminatorKind::Call { ref target, unwind, .. } => {
if let &Some(target) = target {
self.assert_iscleanup(body, block_data, target, is_cleanup);
}
- if let Some(cleanup) = cleanup {
- if is_cleanup {
- span_mirbug!(self, block_data, "cleanup on cleanup block")
- }
- self.assert_iscleanup(body, block_data, cleanup, true);
- }
+ self.assert_iscleanup_unwind(body, block_data, unwind, is_cleanup);
}
TerminatorKind::FalseEdge { real_target, imaginary_target } => {
self.assert_iscleanup(body, block_data, real_target, is_cleanup);
@@ -1656,23 +1620,13 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
}
TerminatorKind::FalseUnwind { real_target, unwind } => {
self.assert_iscleanup(body, block_data, real_target, is_cleanup);
- if let Some(unwind) = unwind {
- if is_cleanup {
- span_mirbug!(self, block_data, "cleanup in cleanup block via false unwind");
- }
- self.assert_iscleanup(body, block_data, unwind, true);
- }
+ self.assert_iscleanup_unwind(body, block_data, unwind, is_cleanup);
}
- TerminatorKind::InlineAsm { destination, cleanup, .. } => {
+ TerminatorKind::InlineAsm { destination, unwind, .. } => {
if let Some(target) = destination {
self.assert_iscleanup(body, block_data, target, is_cleanup);
}
- if let Some(cleanup) = cleanup {
- if is_cleanup {
- span_mirbug!(self, block_data, "cleanup on cleanup block")
- }
- self.assert_iscleanup(body, block_data, cleanup, true);
- }
+ self.assert_iscleanup_unwind(body, block_data, unwind, is_cleanup);
}
}
}
@@ -1689,6 +1643,29 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
}
}
+ fn assert_iscleanup_unwind(
+ &mut self,
+ body: &Body<'tcx>,
+ ctxt: &dyn fmt::Debug,
+ unwind: UnwindAction,
+ is_cleanup: bool,
+ ) {
+ match unwind {
+ UnwindAction::Cleanup(unwind) => {
+ if is_cleanup {
+ span_mirbug!(self, ctxt, "unwind on cleanup block")
+ }
+ self.assert_iscleanup(body, ctxt, unwind, true);
+ }
+ UnwindAction::Continue => {
+ if is_cleanup {
+ span_mirbug!(self, ctxt, "unwind on cleanup block")
+ }
+ }
+ UnwindAction::Unreachable | UnwindAction::Terminate => (),
+ }
+ }
+
fn check_local(&mut self, body: &Body<'tcx>, local: Local, local_decl: &LocalDecl<'tcx>) {
match body.local_kind(local) {
LocalKind::ReturnPointer | LocalKind::Arg => {
@@ -1700,7 +1677,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
// - maybe we should make that a warning.
return;
}
- LocalKind::Var | LocalKind::Temp => {}
+ LocalKind::Temp => {}
}
// When `unsized_fn_params` or `unsized_locals` is enabled, only function calls
@@ -1736,7 +1713,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();
@@ -1753,7 +1730,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
}
}
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(),
@@ -1764,7 +1741,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(),
@@ -2242,6 +2219,13 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
}
}
}
+ CastKind::Transmute => {
+ span_mirbug!(
+ self,
+ rvalue,
+ "Unexpected CastKind::Transmute, which is not permitted in Analysis MIR",
+ );
+ }
}
}
@@ -2362,7 +2346,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();
@@ -2374,7 +2358,7 @@ 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 }) => {
@@ -2382,8 +2366,8 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
self,
rvalue,
"accessed field #{} but variant only has {}",
- i,
- field_count
+ i.as_u32(),
+ field_count,
);
continue;
}
@@ -2435,7 +2419,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
if let Some(all_facts) = all_facts {
let _prof_timer = self.infcx.tcx.prof.generic_activity("polonius_fact_generation");
if let Some(borrow_index) = borrow_set.get_index_of(&location) {
- let region_vid = borrow_region.to_region_vid();
+ let region_vid = borrow_region.as_var();
all_facts.loan_issued_at.push((
region_vid,
borrow_index,
@@ -2481,8 +2465,8 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
match base_ty.kind() {
ty::Ref(ref_region, _, mutbl) => {
constraints.outlives_constraints.push(OutlivesConstraint {
- sup: ref_region.to_region_vid(),
- sub: borrow_region.to_region_vid(),
+ sup: ref_region.as_var(),
+ sub: borrow_region.as_var(),
locations: location.to_locations(),
span: location.to_locations().span(body),
category,
@@ -2612,7 +2596,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
self.implicit_region_bound,
self.param_env,
location.to_locations(),
- DUMMY_SP, // irrelevant; will be overrided.
+ DUMMY_SP, // irrelevant; will be overridden.
ConstraintCategory::Boring, // same as above.
&mut self.borrowck_context.constraints,
)