diff --git a/src/librustc/mir/mod.rs b/src/librustc/mir/mod.rs index 42d24d9f332..05bb1d96980 100644 --- a/src/librustc/mir/mod.rs +++ b/src/librustc/mir/mod.rs @@ -1655,7 +1655,7 @@ impl Debug for Statement<'_> { /// changing or disturbing program state. #[derive(Clone, PartialEq, Eq, PartialOrd, Ord, Hash, RustcEncodable, HashStable)] pub struct Place<'tcx> { - pub base: PlaceBase<'tcx>, + pub base: PlaceBase, /// projection out of a place (access a field, deref a pointer, etc) pub projection: &'tcx List>, @@ -1664,34 +1664,9 @@ pub struct Place<'tcx> { impl<'tcx> rustc_serialize::UseSpecializedDecodable for Place<'tcx> {} #[derive(Clone, PartialEq, Eq, PartialOrd, Ord, Hash, RustcEncodable, RustcDecodable, HashStable)] -pub enum PlaceBase<'tcx> { +pub enum PlaceBase { /// local variable Local(Local), - - /// static or static mut variable - Static(Box>), -} - -/// We store the normalized type to avoid requiring normalization when reading MIR -#[derive( - Clone, - Debug, - PartialEq, - Eq, - PartialOrd, - Ord, - Hash, - RustcEncodable, - RustcDecodable, - HashStable -)] -pub struct Static<'tcx> { - pub ty: Ty<'tcx>, - /// The `DefId` of the item this static was declared in. For promoted values, usually, this is - /// the same as the `DefId` of the `mir::Body` containing the `Place` this promoted appears in. - /// However, after inlining, that might no longer be the case as inlined `Place`s are copied - /// into the calling frame. - pub def_id: DefId, } #[derive(Copy, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)] @@ -1781,7 +1756,7 @@ rustc_index::newtype_index! { #[derive(Clone, Copy, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)] pub struct PlaceRef<'a, 'tcx> { - pub base: &'a PlaceBase<'tcx>, + pub base: &'a PlaceBase, pub projection: &'a [PlaceElem<'tcx>], } @@ -1830,7 +1805,7 @@ impl From for Place<'_> { } } -impl From for PlaceBase<'_> { +impl From for PlaceBase { fn from(local: Local) -> Self { PlaceBase::Local(local) } @@ -1921,13 +1896,10 @@ impl Debug for Place<'_> { } } -impl Debug for PlaceBase<'_> { +impl Debug for PlaceBase { fn fmt(&self, fmt: &mut Formatter<'_>) -> fmt::Result { match *self { PlaceBase::Local(id) => write!(fmt, "{:?}", id), - PlaceBase::Static(box self::Static { ty, def_id }) => { - write!(fmt, "({}: {:?})", ty::tls::with(|tcx| tcx.def_path_str(def_id)), ty) - } } } } @@ -3000,18 +2972,16 @@ impl<'tcx> TypeFoldable<'tcx> for Place<'tcx> { } } -impl<'tcx> TypeFoldable<'tcx> for PlaceBase<'tcx> { +impl<'tcx> TypeFoldable<'tcx> for PlaceBase { fn super_fold_with>(&self, folder: &mut F) -> Self { match self { PlaceBase::Local(local) => PlaceBase::Local(local.fold_with(folder)), - PlaceBase::Static(static_) => PlaceBase::Static(static_.fold_with(folder)), } } fn super_visit_with>(&self, visitor: &mut V) -> bool { match self { PlaceBase::Local(local) => local.visit_with(visitor), - PlaceBase::Static(static_) => (**static_).visit_with(visitor), } } } @@ -3027,18 +2997,6 @@ impl<'tcx> TypeFoldable<'tcx> for &'tcx ty::List> { } } -impl<'tcx> TypeFoldable<'tcx> for Static<'tcx> { - fn super_fold_with>(&self, folder: &mut F) -> Self { - Static { ty: self.ty.fold_with(folder), def_id: self.def_id } - } - - fn super_visit_with>(&self, visitor: &mut V) -> bool { - let Static { ty, def_id: _ } = self; - - ty.visit_with(visitor) - } -} - impl<'tcx> TypeFoldable<'tcx> for Rvalue<'tcx> { fn super_fold_with>(&self, folder: &mut F) -> Self { use crate::mir::Rvalue::*; diff --git a/src/librustc/mir/tcx.rs b/src/librustc/mir/tcx.rs index 77f3ff47ff2..5adf6447d39 100644 --- a/src/librustc/mir/tcx.rs +++ b/src/librustc/mir/tcx.rs @@ -114,7 +114,7 @@ impl<'tcx> PlaceTy<'tcx> { impl<'tcx> Place<'tcx> { pub fn ty_from( - base: &PlaceBase<'tcx>, + base: &PlaceBase, projection: &[PlaceElem<'tcx>], local_decls: &D, tcx: TyCtxt<'tcx>, @@ -135,14 +135,13 @@ impl<'tcx> Place<'tcx> { } } -impl<'tcx> PlaceBase<'tcx> { +impl<'tcx> PlaceBase { pub fn ty(&self, local_decls: &D) -> PlaceTy<'tcx> where D: HasLocalDecls<'tcx>, { match self { PlaceBase::Local(index) => PlaceTy::from_ty(local_decls.local_decls()[*index].ty), - PlaceBase::Static(data) => PlaceTy::from_ty(data.ty), } } } diff --git a/src/librustc/mir/visit.rs b/src/librustc/mir/visit.rs index 3924a1aa47e..a31931c8a99 100644 --- a/src/librustc/mir/visit.rs +++ b/src/librustc/mir/visit.rs @@ -164,7 +164,7 @@ macro_rules! make_mir_visitor { } fn visit_place_base(&mut self, - base: & $($mutability)? PlaceBase<'tcx>, + base: & $($mutability)? PlaceBase, context: PlaceContext, location: Location) { self.super_place_base(base, context, location); @@ -705,16 +705,13 @@ macro_rules! make_mir_visitor { } fn super_place_base(&mut self, - place_base: & $($mutability)? PlaceBase<'tcx>, + place_base: & $($mutability)? PlaceBase, context: PlaceContext, location: Location) { match place_base { PlaceBase::Local(local) => { self.visit_local(local, context, location); } - PlaceBase::Static(box Static { ty, def_id: _ }) => { - self.visit_ty(& $($mutability)? *ty, TyContext::Location(location)); - } } } @@ -889,7 +886,7 @@ macro_rules! visit_place_fns { () => ( fn visit_projection( &mut self, - base: &PlaceBase<'tcx>, + base: &PlaceBase, projection: &[PlaceElem<'tcx>], context: PlaceContext, location: Location, @@ -899,7 +896,7 @@ macro_rules! visit_place_fns { fn visit_projection_elem( &mut self, - base: &PlaceBase<'tcx>, + base: &PlaceBase, proj_base: &[PlaceElem<'tcx>], elem: &PlaceElem<'tcx>, context: PlaceContext, @@ -934,7 +931,7 @@ macro_rules! visit_place_fns { fn super_projection( &mut self, - base: &PlaceBase<'tcx>, + base: &PlaceBase, projection: &[PlaceElem<'tcx>], context: PlaceContext, location: Location, @@ -948,7 +945,7 @@ macro_rules! visit_place_fns { fn super_projection_elem( &mut self, - _base: &PlaceBase<'tcx>, + _base: &PlaceBase, _proj_base: &[PlaceElem<'tcx>], elem: &PlaceElem<'tcx>, _context: PlaceContext, diff --git a/src/librustc/ty/codec.rs b/src/librustc/ty/codec.rs index 9b2714082f1..c691cb44f01 100644 --- a/src/librustc/ty/codec.rs +++ b/src/librustc/ty/codec.rs @@ -226,7 +226,7 @@ pub fn decode_place(decoder: &mut D) -> Result, D::Error> where D: TyDecoder<'tcx>, { - let base: mir::PlaceBase<'tcx> = Decodable::decode(decoder)?; + let base: mir::PlaceBase = Decodable::decode(decoder)?; let len = decoder.read_usize()?; let projection: &'tcx List> = decoder.tcx().mk_place_elems((0..len).map(|_| Decodable::decode(decoder)))?; diff --git a/src/librustc_codegen_ssa/mir/analyze.rs b/src/librustc_codegen_ssa/mir/analyze.rs index 0ceb44d019b..7b9bc923cd6 100644 --- a/src/librustc_codegen_ssa/mir/analyze.rs +++ b/src/librustc_codegen_ssa/mir/analyze.rs @@ -14,7 +14,6 @@ use rustc::ty::layout::{HasTyCtxt, LayoutOf}; use rustc_data_structures::graph::dominators::Dominators; use rustc_index::bit_set::BitSet; use rustc_index::vec::{Idx, IndexVec}; -use rustc_span::DUMMY_SP; pub fn non_ssa_locals<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>( fx: &FunctionCx<'a, 'tcx, Bx>, @@ -135,10 +134,10 @@ impl> LocalAnalyzer<'mir, 'a, 'tcx, Bx> { // ZSTs don't require any actual memory access. let elem_ty = base_ty.projection_ty(cx.tcx(), elem).ty; let elem_ty = self.fx.monomorphize(&elem_ty); - let span = if let mir::PlaceBase::Local(index) = place_ref.base { - self.fx.mir.local_decls[*index].source_info.span - } else { - DUMMY_SP + let span = match place_ref.base { + mir::PlaceBase::Local(index) => { + self.fx.mir.local_decls[*index].source_info.span + } }; if cx.spanned_layout_of(elem_ty, span).is_zst() { return; @@ -179,8 +178,8 @@ impl> LocalAnalyzer<'mir, 'a, 'tcx, Bx> { // We use `NonUseContext::VarDebugInfo` for the base, // which might not force the base local to memory, // so we have to do it manually. - if let mir::PlaceBase::Local(local) = place_ref.base { - self.visit_local(&local, context, location); + match place_ref.base { + mir::PlaceBase::Local(local) => self.visit_local(&local, context, location), } } } diff --git a/src/librustc_codegen_ssa/mir/debuginfo.rs b/src/librustc_codegen_ssa/mir/debuginfo.rs index 6c17a01eb91..88e43c7f535 100644 --- a/src/librustc_codegen_ssa/mir/debuginfo.rs +++ b/src/librustc_codegen_ssa/mir/debuginfo.rs @@ -258,8 +258,8 @@ pub fn per_local_var_debug_info( if tcx.sess.opts.debuginfo == DebugInfo::Full || !tcx.sess.fewer_names() { let mut per_local = IndexVec::from_elem(vec![], &body.local_decls); for var in &body.var_debug_info { - if let mir::PlaceBase::Local(local) = var.place.base { - per_local[local].push(var); + match var.place.base { + mir::PlaceBase::Local(local) => per_local[local].push(var), } } Some(per_local) diff --git a/src/librustc_codegen_ssa/mir/operand.rs b/src/librustc_codegen_ssa/mir/operand.rs index d5306965437..be6e05b948c 100644 --- a/src/librustc_codegen_ssa/mir/operand.rs +++ b/src/librustc_codegen_ssa/mir/operand.rs @@ -373,44 +373,44 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> { ) -> Option> { debug!("maybe_codegen_consume_direct(place_ref={:?})", place_ref); - if let mir::PlaceBase::Local(index) = place_ref.base { - match self.locals[*index] { - LocalRef::Operand(Some(mut o)) => { - // Moves out of scalar and scalar pair fields are trivial. - for elem in place_ref.projection.iter() { - match elem { - mir::ProjectionElem::Field(ref f, _) => { - o = o.extract_field(bx, f.index()); - } - mir::ProjectionElem::Index(_) - | mir::ProjectionElem::ConstantIndex { .. } => { - // ZSTs don't require any actual memory access. - // FIXME(eddyb) deduplicate this with the identical - // checks in `codegen_consume` and `extract_field`. - let elem = o.layout.field(bx.cx(), 0); - if elem.is_zst() { - o = OperandRef::new_zst(bx, elem); - } else { - return None; + match place_ref.base { + mir::PlaceBase::Local(index) => { + match self.locals[*index] { + LocalRef::Operand(Some(mut o)) => { + // Moves out of scalar and scalar pair fields are trivial. + for elem in place_ref.projection.iter() { + match elem { + mir::ProjectionElem::Field(ref f, _) => { + o = o.extract_field(bx, f.index()); } + mir::ProjectionElem::Index(_) + | mir::ProjectionElem::ConstantIndex { .. } => { + // ZSTs don't require any actual memory access. + // FIXME(eddyb) deduplicate this with the identical + // checks in `codegen_consume` and `extract_field`. + let elem = o.layout.field(bx.cx(), 0); + if elem.is_zst() { + o = OperandRef::new_zst(bx, elem); + } else { + return None; + } + } + _ => return None, } - _ => return None, } - } - Some(o) - } - LocalRef::Operand(None) => { - bug!("use of {:?} before def", place_ref); - } - LocalRef::Place(..) | LocalRef::UnsizedPlace(..) => { - // watch out for locals that do not have an - // alloca; they are handled somewhat differently - None + Some(o) + } + LocalRef::Operand(None) => { + bug!("use of {:?} before def", place_ref); + } + LocalRef::Place(..) | LocalRef::UnsizedPlace(..) => { + // watch out for locals that do not have an + // alloca; they are handled somewhat differently + None + } } } - } else { - None } } diff --git a/src/librustc_codegen_ssa/mir/place.rs b/src/librustc_codegen_ssa/mir/place.rs index 49c3edbb2b3..3d94cf9aa2c 100644 --- a/src/librustc_codegen_ssa/mir/place.rs +++ b/src/librustc_codegen_ssa/mir/place.rs @@ -37,15 +37,6 @@ impl<'a, 'tcx, V: CodegenObject> PlaceRef<'tcx, V> { PlaceRef { llval, llextra: None, layout, align } } - fn new_thin_place>( - bx: &mut Bx, - llval: V, - layout: TyLayout<'tcx>, - ) -> PlaceRef<'tcx, V> { - assert!(!bx.cx().type_has_metadata(layout.ty)); - PlaceRef { llval, llextra: None, layout, align: layout.align.abi } - } - // FIXME(eddyb) pass something else for the name so no work is done // unless LLVM IR names are turned on (e.g. for `--emit=llvm-ir`). pub fn alloca>( @@ -437,16 +428,6 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> { } } } - mir::PlaceRef { - base: mir::PlaceBase::Static(box mir::Static { ty, def_id }), - projection: [], - } => { - // NB: The layout of a static may be unsized as is the case when working - // with a static that is an extern_type. - let layout = cx.layout_of(self.monomorphize(&ty)); - let static_ = bx.get_static(*def_id); - PlaceRef::new_thin_place(bx, static_, layout) - } mir::PlaceRef { base, projection: [proj_base @ .., mir::ProjectionElem::Deref] } => { // Load the pointer from its location. self.codegen_consume(bx, &mir::PlaceRef { base, projection: proj_base }) diff --git a/src/librustc_mir/borrow_check/borrow_set.rs b/src/librustc_mir/borrow_check/borrow_set.rs index b66b2e4b1f7..4c6b9bc02a4 100644 --- a/src/librustc_mir/borrow_check/borrow_set.rs +++ b/src/librustc_mir/borrow_check/borrow_set.rs @@ -208,8 +208,10 @@ impl<'a, 'tcx> Visitor<'tcx> for GatherBorrows<'a, 'tcx> { self.insert_as_pending_if_two_phase(location, &assigned_place, kind, idx); - if let mir::PlaceBase::Local(local) = borrowed_place.base { - self.local_map.entry(local).or_default().insert(idx); + match borrowed_place.base { + mir::PlaceBase::Local(local) => { + self.local_map.entry(local).or_default().insert(idx); + } } } diff --git a/src/librustc_mir/borrow_check/constraint_generation.rs b/src/librustc_mir/borrow_check/constraint_generation.rs index 67cd9c40db6..2a9ad6a1505 100644 --- a/src/librustc_mir/borrow_check/constraint_generation.rs +++ b/src/librustc_mir/borrow_check/constraint_generation.rs @@ -207,10 +207,6 @@ impl<'cx, 'cg, 'tcx> ConstraintGeneration<'cx, 'cg, 'tcx> { ); } - PlaceRef { base: &PlaceBase::Static(_), .. } => { - // Ignore kills of static or static mut variables. - } - PlaceRef { base: &PlaceBase::Local(local), projection: &[.., _] } => { // Kill conflicting borrows of the innermost local. debug!( diff --git a/src/librustc_mir/borrow_check/diagnostics/conflict_errors.rs b/src/librustc_mir/borrow_check/diagnostics/conflict_errors.rs index 7e251560a6c..dc3157f6b4d 100644 --- a/src/librustc_mir/borrow_check/diagnostics/conflict_errors.rs +++ b/src/librustc_mir/borrow_check/diagnostics/conflict_errors.rs @@ -688,7 +688,6 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { assert!(root_place.projection.is_empty()); let proper_span = match root_place.base { PlaceBase::Local(local) => self.body.local_decls[*local].source_info.span, - _ => drop_span, }; let root_place_projection = self.infcx.tcx.intern_place_elems(root_place.projection); @@ -709,12 +708,16 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { borrow_span, )); - if let PlaceBase::Local(local) = borrow.borrowed_place.base { - if self.body.local_decls[local].is_ref_to_thread_local() { - let err = self - .report_thread_local_value_does_not_live_long_enough(drop_span, borrow_span); - err.buffer(&mut self.errors_buffer); - return; + match borrow.borrowed_place.base { + PlaceBase::Local(local) => { + if self.body.local_decls[local].is_ref_to_thread_local() { + let err = self.report_thread_local_value_does_not_live_long_enough( + drop_span, + borrow_span, + ); + err.buffer(&mut self.errors_buffer); + return; + } } }; diff --git a/src/librustc_mir/borrow_check/diagnostics/mod.rs b/src/librustc_mir/borrow_check/diagnostics/mod.rs index 8ef4273a2f6..38c479c72c1 100644 --- a/src/librustc_mir/borrow_check/diagnostics/mod.rs +++ b/src/librustc_mir/borrow_check/diagnostics/mod.rs @@ -2,7 +2,7 @@ use rustc::mir::{ AggregateKind, Constant, Field, Local, LocalInfo, LocalKind, Location, Operand, Place, - PlaceBase, PlaceRef, ProjectionElem, Rvalue, Statement, StatementKind, Static, Terminator, + PlaceBase, PlaceRef, ProjectionElem, Rvalue, Statement, StatementKind, Terminator, TerminatorKind, }; use rustc::ty::layout::VariantIdx; @@ -172,9 +172,6 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { PlaceRef { base: PlaceBase::Local(local), projection: [] } => { self.append_local_to_string(*local, buf)?; } - PlaceRef { base: PlaceBase::Static(box Static { def_id, .. }), projection: [] } => { - buf.push_str(&self.infcx.tcx.item_name(*def_id).to_string()); - } PlaceRef { base: &PlaceBase::Local(local), projection: [ProjectionElem::Deref] } if self.body.local_decls[local].is_ref_for_guard() => { @@ -318,9 +315,6 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { let local = &self.body.local_decls[*local]; self.describe_field_from_ty(&local.ty, field, None) } - PlaceRef { base: PlaceBase::Static(static_), projection: [] } => { - self.describe_field_from_ty(&static_.ty, field, None) - } PlaceRef { base, projection: [proj_base @ .., elem] } => match elem { ProjectionElem::Deref => { self.describe_field(PlaceRef { base, projection: proj_base }, field) diff --git a/src/librustc_mir/borrow_check/diagnostics/move_errors.rs b/src/librustc_mir/borrow_check/diagnostics/move_errors.rs index 3f4204bc12f..ceb97a98f1f 100644 --- a/src/librustc_mir/borrow_check/diagnostics/move_errors.rs +++ b/src/librustc_mir/borrow_check/diagnostics/move_errors.rs @@ -243,9 +243,6 @@ impl<'a, 'tcx> MirBorrowckCtxt<'a, 'tcx> { ); ( match kind { - IllegalMoveOriginKind::Static => { - unreachable!(); - } IllegalMoveOriginKind::BorrowedContent { target_place } => self .report_cannot_move_from_borrowed_content( original_path, diff --git a/src/librustc_mir/borrow_check/diagnostics/mutability_errors.rs b/src/librustc_mir/borrow_check/diagnostics/mutability_errors.rs index 595acec2f74..e81a012cef5 100644 --- a/src/librustc_mir/borrow_check/diagnostics/mutability_errors.rs +++ b/src/librustc_mir/borrow_check/diagnostics/mutability_errors.rs @@ -136,8 +136,7 @@ impl<'a, 'tcx> MirBorrowckCtxt<'a, 'tcx> { } } - PlaceRef { base: PlaceBase::Static(_), .. } - | PlaceRef { base: _, projection: [.., ProjectionElem::Index(_)] } + PlaceRef { base: _, projection: [.., ProjectionElem::Index(_)] } | PlaceRef { base: _, projection: [.., ProjectionElem::ConstantIndex { .. }] } | PlaceRef { base: _, projection: [.., ProjectionElem::Subslice { .. }] } | PlaceRef { base: _, projection: [.., ProjectionElem::Downcast(..)] } => { diff --git a/src/librustc_mir/borrow_check/mod.rs b/src/librustc_mir/borrow_check/mod.rs index 5174f17ab88..d0b0a159e86 100644 --- a/src/librustc_mir/borrow_check/mod.rs +++ b/src/librustc_mir/borrow_check/mod.rs @@ -5,7 +5,7 @@ use rustc::lint::builtin::MUTABLE_BORROW_RESERVATION_CONFLICT; use rustc::lint::builtin::UNUSED_MUT; use rustc::mir::{ read_only, Body, BodyAndCache, ClearCrossCrate, Local, Location, Mutability, Operand, Place, - PlaceBase, PlaceElem, PlaceRef, ReadOnlyBodyAndCache, Static, + PlaceBase, PlaceElem, PlaceRef, ReadOnlyBodyAndCache, }; use rustc::mir::{AggregateKind, BasicBlock, BorrowCheckResult, BorrowKind}; use rustc::mir::{Field, ProjectionElem, Promoted, Rvalue, Statement, StatementKind}; @@ -815,7 +815,7 @@ enum InitializationRequiringAction { } struct RootPlace<'d, 'tcx> { - place_base: &'d PlaceBase<'tcx>, + place_base: &'d PlaceBase, place_projection: &'d [PlaceElem<'tcx>], is_local_mutation_allowed: LocalMutationIsAllowed, } @@ -1251,8 +1251,12 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { if let Some(field) = this.is_upvar_field_projection(place.as_ref()) { this.used_mut_upvars.push(field); } - } else if let PlaceBase::Local(local) = place.base { - this.used_mut.insert(local); + } else { + match place.base { + PlaceBase::Local(local) => { + this.used_mut.insert(local); + } + } } }; @@ -1385,7 +1389,6 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { // FIXME: allow thread-locals to borrow other thread locals? let (might_be_alive, will_be_dropped) = match root_place.base { - PlaceBase::Static(_) => (true, false), PlaceBase::Local(local) => { if self.body.local_decls[*local].is_ref_to_thread_local() { // Thread-locals might be dropped after the function exits @@ -1649,26 +1652,20 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { // This code covers scenarios 1, 2, and 3. debug!("check_if_full_path_is_moved place: {:?}", place_span.0); - match self.move_path_closest_to(place_span.0) { - Ok((prefix, mpi)) => { - if maybe_uninits.contains(mpi) { - self.report_use_of_moved_or_uninitialized( - location, - desired_action, - (prefix, place_span.0, place_span.1), - mpi, - ); - } - } - Err(NoMovePathFound::ReachedStatic) => { - // Okay: we do not build MoveData for static variables - } // Only query longest prefix with a MovePath, not further - // ancestors; dataflow recurs on children when parents - // move (to support partial (re)inits). - // - // (I.e., querying parents breaks scenario 7; but may want - // to do such a query based on partial-init feature-gate.) - } + let (prefix, mpi) = self.move_path_closest_to(place_span.0); + if maybe_uninits.contains(mpi) { + self.report_use_of_moved_or_uninitialized( + location, + desired_action, + (prefix, place_span.0, place_span.1), + mpi, + ); + } // Only query longest prefix with a MovePath, not further + // ancestors; dataflow recurs on children when parents + // move (to support partial (re)inits). + // + // (I.e., querying parents breaks scenario 7; but may want + // to do such a query based on partial-init feature-gate.) } /// Subslices correspond to multiple move paths, so we iterate through the @@ -1792,12 +1789,12 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { fn move_path_closest_to( &mut self, place: PlaceRef<'_, 'tcx>, - ) -> Result<(PlaceRef<'cx, 'tcx>, MovePathIndex), NoMovePathFound> { + ) -> (PlaceRef<'cx, 'tcx>, MovePathIndex) { match self.move_data.rev_lookup.find(place) { LookupResult::Parent(Some(mpi)) | LookupResult::Exact(mpi) => { - Ok((self.move_data.move_paths[mpi].place.as_ref(), mpi)) + (self.move_data.move_paths[mpi].place.as_ref(), mpi) } - LookupResult::Parent(None) => Err(NoMovePathFound::ReachedStatic), + LookupResult::Parent(None) => panic!("should have move path for every Local"), } } @@ -1881,7 +1878,7 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { projection: proj_base, }, span, flow_state); - if let PlaceBase::Local(local) = place.base { + match place.base { // rust-lang/rust#21232, // #54499, #54986: during // period where we reject @@ -1890,7 +1887,9 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { // unnecessary `mut` on an // attempt to do a partial // initialization. - self.used_mut.insert(local); + PlaceBase::Local(local) => { + self.used_mut.insert(local); + } } } @@ -2088,10 +2087,8 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { // partial initialization, do not complain about mutability // errors except for actual mutation (as opposed to an attempt // to do a partial initialization). - let previously_initialized = if let PlaceBase::Local(local) = place.base { - self.is_local_ever_initialized(local, flow_state).is_some() - } else { - true + let previously_initialized = match place.base { + PlaceBase::Local(local) => self.is_local_ever_initialized(local, flow_state).is_some(), }; // at this point, we have set up the error reporting state. @@ -2152,11 +2149,6 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { self.used_mut_upvars.push(field); } } - RootPlace { - place_base: PlaceBase::Static(..), - place_projection: [], - is_local_mutation_allowed: _, - } => {} } } @@ -2191,17 +2183,6 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { }), } } - PlaceRef { base: PlaceBase::Static(box Static { def_id, .. }), projection: [] } => { - if !self.infcx.tcx.is_mutable_static(*def_id) { - Err(place) - } else { - Ok(RootPlace { - place_base: place.base, - place_projection: place.projection, - is_local_mutation_allowed, - }) - } - } PlaceRef { base: _, projection: [proj_base @ .., elem] } => { match elem { ProjectionElem::Deref => { @@ -2356,11 +2337,6 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { } } -#[derive(Copy, Clone, PartialEq, Eq, Debug)] -enum NoMovePathFound { - ReachedStatic, -} - /// The degree of overlap between 2 places for borrow-checking. enum Overlap { /// The places might partially overlap - in this case, we give diff --git a/src/librustc_mir/borrow_check/path_utils.rs b/src/librustc_mir/borrow_check/path_utils.rs index 6fb0bbceb1b..41bf1aa47d4 100644 --- a/src/librustc_mir/borrow_check/path_utils.rs +++ b/src/librustc_mir/borrow_check/path_utils.rs @@ -132,8 +132,6 @@ pub(super) fn is_active<'tcx>( /// This is called for all Yield expressions on movable generators pub(super) fn borrow_of_local_data(place: &Place<'_>) -> bool { match place.base { - PlaceBase::Static(_) => false, - // Reborrow of already borrowed data is ignored // Any errors will be caught on the initial borrow PlaceBase::Local(_) => !place.is_indirect(), diff --git a/src/librustc_mir/borrow_check/place_ext.rs b/src/librustc_mir/borrow_check/place_ext.rs index 91ab314e2b9..445ba057c1b 100644 --- a/src/librustc_mir/borrow_check/place_ext.rs +++ b/src/librustc_mir/borrow_check/place_ext.rs @@ -47,7 +47,6 @@ impl<'tcx> PlaceExt<'tcx> for Place<'tcx> { } } }, - PlaceBase::Static(_) => return true, }; for (i, elem) in self.projection.iter().enumerate() { diff --git a/src/librustc_mir/borrow_check/places_conflict.rs b/src/librustc_mir/borrow_check/places_conflict.rs index 3988221e063..a09779a766f 100644 --- a/src/librustc_mir/borrow_check/places_conflict.rs +++ b/src/librustc_mir/borrow_check/places_conflict.rs @@ -122,7 +122,7 @@ fn place_components_conflict<'tcx>( let borrow_base = &borrow_place.base; let access_base = access_place.base; - match place_base_conflict(tcx, borrow_base, access_base) { + match place_base_conflict(borrow_base, access_base) { Overlap::Arbitrary => { bug!("Two base can't return Arbitrary"); } @@ -293,11 +293,7 @@ fn place_components_conflict<'tcx>( // Given that the bases of `elem1` and `elem2` are always either equal // or disjoint (and have the same type!), return the overlap situation // between `elem1` and `elem2`. -fn place_base_conflict<'tcx>( - tcx: TyCtxt<'tcx>, - elem1: &PlaceBase<'tcx>, - elem2: &PlaceBase<'tcx>, -) -> Overlap { +fn place_base_conflict(elem1: &PlaceBase, elem2: &PlaceBase) -> Overlap { match (elem1, elem2) { (PlaceBase::Local(l1), PlaceBase::Local(l2)) => { if l1 == l2 { @@ -310,24 +306,6 @@ fn place_base_conflict<'tcx>( Overlap::Disjoint } } - (PlaceBase::Static(s1), PlaceBase::Static(s2)) => { - if s1.def_id != s2.def_id { - debug!("place_element_conflict: DISJOINT-STATIC"); - Overlap::Disjoint - } else if tcx.is_mutable_static(s1.def_id) { - // We ignore mutable statics - they can only be unsafe code. - debug!("place_element_conflict: IGNORE-STATIC-MUT"); - Overlap::Disjoint - } else { - debug!("place_element_conflict: DISJOINT-OR-EQ-STATIC"); - Overlap::EqualOrDisjoint - } - } - (PlaceBase::Local(_), PlaceBase::Static(_)) - | (PlaceBase::Static(_), PlaceBase::Local(_)) => { - debug!("place_element_conflict: DISJOINT-STATIC-LOCAL-PROMOTED"); - Overlap::Disjoint - } } } @@ -337,7 +315,7 @@ fn place_base_conflict<'tcx>( fn place_projection_conflict<'tcx>( tcx: TyCtxt<'tcx>, body: &Body<'tcx>, - pi1_base: &PlaceBase<'tcx>, + pi1_base: &PlaceBase, pi1_proj_base: &[PlaceElem<'tcx>], pi1_elem: &PlaceElem<'tcx>, pi2_elem: &PlaceElem<'tcx>, diff --git a/src/librustc_mir/borrow_check/prefixes.rs b/src/librustc_mir/borrow_check/prefixes.rs index 1e88f696f23..c41f2f45012 100644 --- a/src/librustc_mir/borrow_check/prefixes.rs +++ b/src/librustc_mir/borrow_check/prefixes.rs @@ -69,39 +69,22 @@ impl<'cx, 'tcx> Iterator for Prefixes<'cx, 'tcx> { 'cursor: loop { match &cursor { - PlaceRef { - base: PlaceBase::Local(_), - projection: [], - } - | // search yielded this leaf - PlaceRef { - base: PlaceBase::Static(_), - projection: [], - } => { + PlaceRef { base: PlaceBase::Local(_), projection: [] } => { self.next = None; return Some(cursor); } - PlaceRef { - base: _, - projection: [proj_base @ .., elem], - } => { + PlaceRef { base: _, projection: [proj_base @ .., elem] } => { match elem { ProjectionElem::Field(_ /*field*/, _ /*ty*/) => { // FIXME: add union handling - self.next = Some(PlaceRef { - base: cursor.base, - projection: proj_base, - }); + self.next = Some(PlaceRef { base: cursor.base, projection: proj_base }); return Some(cursor); } - ProjectionElem::Downcast(..) | - ProjectionElem::Subslice { .. } | - ProjectionElem::ConstantIndex { .. } | - ProjectionElem::Index(_) => { - cursor = PlaceRef { - base: cursor.base, - projection: proj_base, - }; + ProjectionElem::Downcast(..) + | ProjectionElem::Subslice { .. } + | ProjectionElem::ConstantIndex { .. } + | ProjectionElem::Index(_) => { + cursor = PlaceRef { base: cursor.base, projection: proj_base }; continue 'cursor; } ProjectionElem::Deref => { @@ -122,10 +105,7 @@ impl<'cx, 'tcx> Iterator for Prefixes<'cx, 'tcx> { PrefixSet::All => { // All prefixes: just blindly enqueue the base // of the projection. - self.next = Some(PlaceRef { - base: cursor.base, - projection: proj_base, - }); + self.next = Some(PlaceRef { base: cursor.base, projection: proj_base }); return Some(cursor); } PrefixSet::Supporting => { @@ -140,35 +120,20 @@ impl<'cx, 'tcx> Iterator for Prefixes<'cx, 'tcx> { let ty = Place::ty_from(cursor.base, proj_base, *self.body, self.tcx).ty; match ty.kind { - ty::RawPtr(_) | - ty::Ref( - _, /*rgn*/ - _, /*ty*/ - hir::Mutability::Not - ) => { + ty::RawPtr(_) | ty::Ref(_ /*rgn*/, _ /*ty*/, hir::Mutability::Not) => { // don't continue traversing over derefs of raw pointers or shared // borrows. self.next = None; return Some(cursor); } - ty::Ref( - _, /*rgn*/ - _, /*ty*/ - hir::Mutability::Mut, - ) => { - self.next = Some(PlaceRef { - base: cursor.base, - projection: proj_base, - }); + ty::Ref(_ /*rgn*/, _ /*ty*/, hir::Mutability::Mut) => { + self.next = Some(PlaceRef { base: cursor.base, projection: proj_base }); return Some(cursor); } ty::Adt(..) if ty.is_box() => { - self.next = Some(PlaceRef { - base: cursor.base, - projection: proj_base, - }); + self.next = Some(PlaceRef { base: cursor.base, projection: proj_base }); return Some(cursor); } diff --git a/src/librustc_mir/borrow_check/type_check/mod.rs b/src/librustc_mir/borrow_check/type_check/mod.rs index f771330e2d7..001f2fc3b22 100644 --- a/src/librustc_mir/borrow_check/type_check/mod.rs +++ b/src/librustc_mir/borrow_check/type_check/mod.rs @@ -467,32 +467,6 @@ impl<'a, 'b, 'tcx> TypeVerifier<'a, 'b, 'tcx> { let mut place_ty = match &place.base { PlaceBase::Local(index) => PlaceTy::from_ty(self.body.local_decls[*index].ty), - PlaceBase::Static(box Static { ty, def_id }) => { - let san_ty = self.sanitize_type(place, ty); - let check_err = - |verifier: &mut TypeVerifier<'a, 'b, 'tcx>, place: &Place<'tcx>, ty, san_ty| { - if let Err(terr) = verifier.cx.eq_types( - san_ty, - ty, - location.to_locations(), - ConstraintCategory::Boring, - ) { - span_mirbug!( - verifier, - place, - "bad promoted type ({:?}: {:?}): {:?}", - ty, - san_ty, - terr - ); - }; - }; - let ty = self.tcx().type_of(*def_id); - let ty = self.cx.normalize(ty, location); - - check_err(self, place, ty, san_ty); - PlaceTy::from_ty(san_ty) - } }; if place.projection.is_empty() { diff --git a/src/librustc_mir/borrow_check/used_muts.rs b/src/librustc_mir/borrow_check/used_muts.rs index 608a2436bf3..ea530042913 100644 --- a/src/librustc_mir/borrow_check/used_muts.rs +++ b/src/librustc_mir/borrow_check/used_muts.rs @@ -57,8 +57,10 @@ impl GatherUsedMutsVisitor<'_, '_, '_> { // be those that were never initialized - we will consider those as being used as // they will either have been removed by unreachable code optimizations; or linted // as unused variables. - if let PlaceBase::Local(local) = into.base { - let _ = self.never_initialized_mut_locals.remove(&local); + match into.base { + PlaceBase::Local(local) => { + self.never_initialized_mut_locals.remove(&local); + } } } } @@ -80,12 +82,12 @@ impl<'visit, 'cx, 'tcx> Visitor<'tcx> for GatherUsedMutsVisitor<'visit, 'cx, 'tc fn visit_statement(&mut self, statement: &Statement<'tcx>, _location: Location) { match &statement.kind { StatementKind::Assign(box (into, _)) => { - if let PlaceBase::Local(local) = into.base { - debug!( + match into.base { + PlaceBase::Local(local) => debug!( "visit_statement: statement={:?} local={:?} \ - never_initialized_mut_locals={:?}", + never_initialized_mut_locals={:?}", statement, local, self.never_initialized_mut_locals - ); + ), } self.remove_never_initialized_mut_locals(into); } diff --git a/src/librustc_mir/build/expr/as_place.rs b/src/librustc_mir/build/expr/as_place.rs index 29eac5e4b3f..661111ed948 100644 --- a/src/librustc_mir/build/expr/as_place.rs +++ b/src/librustc_mir/build/expr/as_place.rs @@ -20,7 +20,7 @@ use rustc_index::vec::Idx; /// and `c` can be progressively pushed onto the place builder that is created when converting `a`. #[derive(Clone)] struct PlaceBuilder<'tcx> { - base: PlaceBase<'tcx>, + base: PlaceBase, projection: Vec>, } @@ -53,8 +53,8 @@ impl From for PlaceBuilder<'tcx> { } } -impl From> for PlaceBuilder<'tcx> { - fn from(base: PlaceBase<'tcx>) -> Self { +impl From for PlaceBuilder<'tcx> { + fn from(base: PlaceBase) -> Self { Self { base, projection: Vec::new() } } } diff --git a/src/librustc_mir/dataflow/impls/borrows.rs b/src/librustc_mir/dataflow/impls/borrows.rs index 583075980ec..d6ada916227 100644 --- a/src/librustc_mir/dataflow/impls/borrows.rs +++ b/src/librustc_mir/dataflow/impls/borrows.rs @@ -195,35 +195,37 @@ impl<'a, 'tcx> Borrows<'a, 'tcx> { fn kill_borrows_on_place(&self, trans: &mut GenKillSet, place: &Place<'tcx>) { debug!("kill_borrows_on_place: place={:?}", place); - if let PlaceBase::Local(local) = place.base { - let other_borrows_of_local = - self.borrow_set.local_map.get(&local).into_iter().flat_map(|bs| bs.into_iter()); + match place.base { + PlaceBase::Local(local) => { + let other_borrows_of_local = + self.borrow_set.local_map.get(&local).into_iter().flat_map(|bs| bs.into_iter()); - // If the borrowed place is a local with no projections, all other borrows of this - // local must conflict. This is purely an optimization so we don't have to call - // `places_conflict` for every borrow. - if place.projection.is_empty() { - if !self.body.local_decls[local].is_ref_to_static() { - trans.kill_all(other_borrows_of_local); + // If the borrowed place is a local with no projections, all other borrows of this + // local must conflict. This is purely an optimization so we don't have to call + // `places_conflict` for every borrow. + if place.projection.is_empty() { + if !self.body.local_decls[local].is_ref_to_static() { + trans.kill_all(other_borrows_of_local); + } + return; } - return; + + // By passing `PlaceConflictBias::NoOverlap`, we conservatively assume that any given + // pair of array indices are unequal, so that when `places_conflict` returns true, we + // will be assured that two places being compared definitely denotes the same sets of + // locations. + let definitely_conflicting_borrows = other_borrows_of_local.filter(|&&i| { + places_conflict( + self.tcx, + self.body, + &self.borrow_set.borrows[i].borrowed_place, + place, + PlaceConflictBias::NoOverlap, + ) + }); + + trans.kill_all(definitely_conflicting_borrows); } - - // By passing `PlaceConflictBias::NoOverlap`, we conservatively assume that any given - // pair of array indices are unequal, so that when `places_conflict` returns true, we - // will be assured that two places being compared definitely denotes the same sets of - // locations. - let definitely_conflicting_borrows = other_borrows_of_local.filter(|&&i| { - places_conflict( - self.tcx, - self.body, - &self.borrow_set.borrows[i].borrowed_place, - place, - PlaceConflictBias::NoOverlap, - ) - }); - - trans.kill_all(definitely_conflicting_borrows); } } } diff --git a/src/librustc_mir/dataflow/impls/storage_liveness.rs b/src/librustc_mir/dataflow/impls/storage_liveness.rs index 17f71e83cfd..e4d5d6adfc1 100644 --- a/src/librustc_mir/dataflow/impls/storage_liveness.rs +++ b/src/librustc_mir/dataflow/impls/storage_liveness.rs @@ -115,15 +115,13 @@ impl<'mir, 'tcx> BitDenotation<'tcx> for RequiresStorage<'mir, 'tcx> { match stmt.kind { StatementKind::StorageDead(l) => sets.kill(l), StatementKind::Assign(box (ref place, _)) - | StatementKind::SetDiscriminant { box ref place, .. } => { - if let PlaceBase::Local(local) = place.base { - sets.gen(local); - } - } + | StatementKind::SetDiscriminant { box ref place, .. } => match place.base { + PlaceBase::Local(local) => sets.gen(local), + }, StatementKind::InlineAsm(box InlineAsm { ref outputs, .. }) => { for p in &**outputs { - if let PlaceBase::Local(local) = p.base { - sets.gen(local); + match p.base { + PlaceBase::Local(local) => sets.gen(local), } } } @@ -171,8 +169,10 @@ impl<'mir, 'tcx> BitDenotation<'tcx> for RequiresStorage<'mir, 'tcx> { _dest_bb: mir::BasicBlock, dest_place: &mir::Place<'tcx>, ) { - if let PlaceBase::Local(local) = dest_place.base { - in_out.insert(local); + match dest_place.base { + PlaceBase::Local(local) => { + in_out.insert(local); + } } } } diff --git a/src/librustc_mir/dataflow/move_paths/builder.rs b/src/librustc_mir/dataflow/move_paths/builder.rs index c05f7f8959d..b0be49689f9 100644 --- a/src/librustc_mir/dataflow/move_paths/builder.rs +++ b/src/librustc_mir/dataflow/move_paths/builder.rs @@ -98,9 +98,6 @@ impl<'b, 'a, 'tcx> Gatherer<'b, 'a, 'tcx> { debug!("lookup({:?})", place); let mut base = match place.base { PlaceBase::Local(local) => self.builder.data.rev_lookup.locals[local], - PlaceBase::Static(..) => { - return Err(MoveError::cannot_move_out_of(self.loc, Static)); - } }; // The move path index of the first union that we find. Once this is diff --git a/src/librustc_mir/dataflow/move_paths/mod.rs b/src/librustc_mir/dataflow/move_paths/mod.rs index e5cddaf6c66..7133c46d6c7 100644 --- a/src/librustc_mir/dataflow/move_paths/mod.rs +++ b/src/librustc_mir/dataflow/move_paths/mod.rs @@ -248,7 +248,6 @@ impl MovePathLookup { pub fn find(&self, place: PlaceRef<'_, '_>) -> LookupResult { let mut result = match place.base { PlaceBase::Local(local) => self.locals[*local], - PlaceBase::Static(..) => return LookupResult::Parent(None), }; for elem in place.projection.iter() { @@ -281,9 +280,6 @@ pub struct IllegalMoveOrigin<'tcx> { #[derive(Debug)] pub(crate) enum IllegalMoveOriginKind<'tcx> { - /// Illegal move due to attempt to move from `static` variable. - Static, - /// Illegal move due to attempt to move from behind a reference. BorrowedContent { /// The place the reference refers to: if erroneous code was trying to diff --git a/src/librustc_mir/interpret/operand.rs b/src/librustc_mir/interpret/operand.rs index ebe600f25da..30725d781dc 100644 --- a/src/librustc_mir/interpret/operand.rs +++ b/src/librustc_mir/interpret/operand.rs @@ -474,7 +474,6 @@ impl<'mir, 'tcx, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> { self.access_local(self.frame(), *local, layout)? } - PlaceBase::Static(place_static) => self.eval_static_to_mplace(&place_static)?.into(), }; let op = place diff --git a/src/librustc_mir/interpret/place.rs b/src/librustc_mir/interpret/place.rs index aa15f3d1f17..bd3059951e8 100644 --- a/src/librustc_mir/interpret/place.rs +++ b/src/librustc_mir/interpret/place.rs @@ -10,7 +10,6 @@ use rustc::mir::interpret::truncate; use rustc::ty::layout::{ self, Align, HasDataLayout, LayoutOf, PrimitiveExt, Size, TyLayout, VariantIdx, }; -use rustc::ty::TypeFoldable; use rustc::ty::{self, Ty}; use rustc_macros::HashStable; @@ -619,35 +618,6 @@ where }) } - /// Evaluate statics and promoteds to an `MPlace`. Used to share some code between - /// `eval_place` and `eval_place_to_op`. - pub(super) fn eval_static_to_mplace( - &self, - place_static: &mir::Static<'tcx>, - ) -> InterpResult<'tcx, MPlaceTy<'tcx, M::PointerTag>> { - let ty = place_static.ty; - assert!(!ty.needs_subst()); - let layout = self.layout_of(ty)?; - // Just create a lazy reference, so we can support recursive statics. - // tcx takes care of assigning every static one and only one unique AllocId. - // When the data here is ever actually used, memory will notice, - // and it knows how to deal with alloc_id that are present in the - // global table but not in its local memory: It calls back into tcx through - // a query, triggering the CTFE machinery to actually turn this lazy reference - // into a bunch of bytes. IOW, statics are evaluated with CTFE even when - // this InterpCx uses another Machine (e.g., in miri). This is what we - // want! This way, computing statics works consistently between codegen - // and miri: They use the same query to eventually obtain a `ty::Const` - // and use that for further computation. - // - // Notice that statics have *two* AllocIds: the lazy one, and the resolved - // one. Here we make sure that the interpreted program never sees the - // resolved ID. Also see the doc comment of `Memory::get_static_alloc`. - let alloc_id = self.tcx.alloc_map.lock().create_static_alloc(place_static.def_id); - let ptr = self.tag_static_base_pointer(Pointer::from(alloc_id)); - Ok(MPlaceTy::from_aligned_ptr(ptr, layout)) - } - /// Computes a place. You should only use this if you intend to write into this /// place; for reading, a more efficient alternative is `eval_place_for_read`. pub fn eval_place( @@ -683,7 +653,6 @@ where place: Place::Local { frame: self.cur_frame(), local: *local }, layout: self.layout_of_local(self.frame(), *local, None)?, }, - PlaceBase::Static(place_static) => self.eval_static_to_mplace(&place_static)?.into(), }; for elem in place.projection.iter() { diff --git a/src/librustc_mir/monomorphize/collector.rs b/src/librustc_mir/monomorphize/collector.rs index 2ecae7c6b0c..5da5695a4d4 100644 --- a/src/librustc_mir/monomorphize/collector.rs +++ b/src/librustc_mir/monomorphize/collector.rs @@ -182,7 +182,7 @@ use rustc::mir::interpret::{AllocId, ConstValue}; use rustc::mir::interpret::{ErrorHandled, GlobalAlloc, Scalar}; use rustc::mir::mono::{InstantiationMode, MonoItem}; use rustc::mir::visit::Visitor as MirVisitor; -use rustc::mir::{self, Location, PlaceBase, Static}; +use rustc::mir::{self, Location, PlaceBase}; use rustc::session::config::EntryFnType; use rustc::ty::adjustment::{CustomCoerceUnsized, PointerCast}; use rustc::ty::print::obsolete::DefPathBasedNames; @@ -642,20 +642,11 @@ impl<'a, 'tcx> MirVisitor<'tcx> for MirNeighborCollector<'a, 'tcx> { fn visit_place_base( &mut self, - place_base: &mir::PlaceBase<'tcx>, + place_base: &mir::PlaceBase, _context: mir::visit::PlaceContext, - location: Location, + _location: Location, ) { match place_base { - PlaceBase::Static(box Static { def_id, .. }) => { - debug!("visiting static {:?} @ {:?}", def_id, location); - - let tcx = self.tcx; - let instance = Instance::mono(tcx, *def_id); - if should_monomorphize_locally(tcx, &instance) { - self.output.push(MonoItem::Static(*def_id)); - } - } PlaceBase::Local(_) => { // Locals have no relevance for collector. } diff --git a/src/librustc_mir/transform/check_consts/qualifs.rs b/src/librustc_mir/transform/check_consts/qualifs.rs index 253a5899768..8c52a4e7a29 100644 --- a/src/librustc_mir/transform/check_consts/qualifs.rs +++ b/src/librustc_mir/transform/check_consts/qualifs.rs @@ -76,9 +76,6 @@ pub trait Qualif { ) -> bool { match place { PlaceRef { base: PlaceBase::Local(local), projection: [] } => per_local(*local), - PlaceRef { base: PlaceBase::Static(_), projection: [] } => { - bug!("qualifying already promoted MIR") - } PlaceRef { base: _, projection: [.., _] } => Self::in_projection(cx, per_local, place), } } diff --git a/src/librustc_mir/transform/check_consts/validation.rs b/src/librustc_mir/transform/check_consts/validation.rs index b8183972476..c864abdae66 100644 --- a/src/librustc_mir/transform/check_consts/validation.rs +++ b/src/librustc_mir/transform/check_consts/validation.rs @@ -369,15 +369,6 @@ impl Visitor<'tcx> for Validator<'_, 'mir, 'tcx> { Rvalue::AddressOf(Mutability::Mut, _) => self.check_op(ops::MutAddressOf), - // At the moment, `PlaceBase::Static` is only used for promoted MIR. - Rvalue::Ref(_, BorrowKind::Shared, ref place) - | Rvalue::Ref(_, BorrowKind::Shallow, ref place) - | Rvalue::AddressOf(Mutability::Not, ref place) - if matches!(place.base, PlaceBase::Static(_)) => - { - bug!("Saw a promoted during const-checking, which must run before promotion") - } - Rvalue::Ref(_, BorrowKind::Shared, ref place) | Rvalue::Ref(_, BorrowKind::Shallow, ref place) => { self.check_immutable_borrow_like(location, place) @@ -423,7 +414,7 @@ impl Visitor<'tcx> for Validator<'_, 'mir, 'tcx> { fn visit_place_base( &mut self, - place_base: &PlaceBase<'tcx>, + place_base: &PlaceBase, context: PlaceContext, location: Location, ) { @@ -437,9 +428,6 @@ impl Visitor<'tcx> for Validator<'_, 'mir, 'tcx> { match place_base { PlaceBase::Local(_) => {} - PlaceBase::Static(_) => { - bug!("Promotion must be run after const validation"); - } } } @@ -453,7 +441,7 @@ impl Visitor<'tcx> for Validator<'_, 'mir, 'tcx> { } fn visit_projection_elem( &mut self, - place_base: &PlaceBase<'tcx>, + place_base: &PlaceBase, proj_base: &[PlaceElem<'tcx>], elem: &PlaceElem<'tcx>, context: PlaceContext, @@ -681,9 +669,11 @@ fn place_as_reborrow( // A borrow of a `static` also looks like `&(*_1)` in the MIR, but `_1` is a `const` // that points to the allocation for the static. Don't treat these as reborrows. - if let PlaceBase::Local(local) = place.base { - if body.local_decls[local].is_ref_to_static() { - return None; + match place.base { + PlaceBase::Local(local) => { + if body.local_decls[local].is_ref_to_static() { + return None; + } } } diff --git a/src/librustc_mir/transform/check_unsafety.rs b/src/librustc_mir/transform/check_unsafety.rs index be9c2b741a2..017d0f34674 100644 --- a/src/librustc_mir/transform/check_unsafety.rs +++ b/src/librustc_mir/transform/check_unsafety.rs @@ -194,9 +194,6 @@ impl<'a, 'tcx> Visitor<'tcx> for UnsafetyChecker<'a, 'tcx> { PlaceBase::Local(..) => { // Locals are safe. } - PlaceBase::Static(box Static { .. }) => { - bug!("Static should not exist"); - } } for (i, elem) in place.projection.iter().enumerate() { diff --git a/src/librustc_mir/transform/const_prop.rs b/src/librustc_mir/transform/const_prop.rs index 9614137b7e7..f9b24b00e87 100644 --- a/src/librustc_mir/transform/const_prop.rs +++ b/src/librustc_mir/transform/const_prop.rs @@ -872,8 +872,8 @@ impl<'mir, 'tcx> MutVisitor<'tcx> for ConstPropagator<'mir, 'tcx> { // doesn't use the invalid value match cond { Operand::Move(ref place) | Operand::Copy(ref place) => { - if let PlaceBase::Local(local) = place.base { - self.remove_const(local); + match place.base { + PlaceBase::Local(local) => self.remove_const(local), } } Operand::Constant(_) => {} diff --git a/src/librustc_mir/transform/generator.rs b/src/librustc_mir/transform/generator.rs index 96fb992e53b..b075a399516 100644 --- a/src/librustc_mir/transform/generator.rs +++ b/src/librustc_mir/transform/generator.rs @@ -275,18 +275,18 @@ impl MutVisitor<'tcx> for TransformVisitor<'tcx> { assert_eq!(self.remap.get(local), None); } - fn visit_place(&mut self, place: &mut Place<'tcx>, context: PlaceContext, location: Location) { - if let PlaceBase::Local(l) = place.base { + fn visit_place( + &mut self, + place: &mut Place<'tcx>, + _context: PlaceContext, + _location: Location, + ) { + match place.base { + PlaceBase::Local(l) => // Replace an Local in the remap with a generator struct access - if let Some(&(ty, variant_index, idx)) = self.remap.get(&l) { - replace_base(place, self.make_field(variant_index, idx, ty), self.tcx); - } - } else { - self.visit_place_base(&mut place.base, context, location); - - for elem in place.projection.iter() { - if let PlaceElem::Index(local) = elem { - assert_ne!(*local, self_arg()); + { + if let Some(&(ty, variant_index, idx)) = self.remap.get(&l) { + replace_base(place, self.make_field(variant_index, idx, ty), self.tcx); } } } diff --git a/src/librustc_mir/transform/inline.rs b/src/librustc_mir/transform/inline.rs index 3c5d2c9f310..52992f7d7a8 100644 --- a/src/librustc_mir/transform/inline.rs +++ b/src/librustc_mir/transform/inline.rs @@ -431,9 +431,6 @@ impl Inliner<'tcx> { } match place.base { - // Static variables need a borrow because the callee - // might modify the same static. - PlaceBase::Static(_) => true, _ => false, } } @@ -649,7 +646,6 @@ impl<'a, 'tcx> Integrator<'a, 'tcx> { if *local == RETURN_PLACE { match self.destination.base { PlaceBase::Local(l) => return l, - PlaceBase::Static(ref s) => bug!("Return place is {:?}, not local", s), } } @@ -673,7 +669,6 @@ impl<'a, 'tcx> MutVisitor<'tcx> for Integrator<'a, 'tcx> { fn visit_place(&mut self, place: &mut Place<'tcx>, context: PlaceContext, location: Location) { match &mut place.base { - PlaceBase::Static(_) => {} PlaceBase::Local(l) => { // If this is the `RETURN_PLACE`, we need to rebase any projections onto it. let dest_proj_len = self.destination.projection.len(); diff --git a/src/librustc_mir/transform/promote_consts.rs b/src/librustc_mir/transform/promote_consts.rs index 76f1e2d186e..494b61c5d1e 100644 --- a/src/librustc_mir/transform/promote_consts.rs +++ b/src/librustc_mir/transform/promote_consts.rs @@ -310,7 +310,6 @@ impl<'tcx> Validator<'_, 'tcx> { // don't get promoted anyway). let base = match place.base { PlaceBase::Local(local) => local, - _ => return Err(Unpromotable), }; self.validate_local(base)?; @@ -482,9 +481,6 @@ impl<'tcx> Validator<'_, 'tcx> { PlaceRef { base: PlaceBase::Local(local), projection: [] } => { self.validate_local(*local) } - PlaceRef { base: PlaceBase::Static(_), projection: [] } => { - bug!("qualifying already promoted MIR") - } PlaceRef { base: _, projection: [proj_base @ .., elem] } => { match *elem { ProjectionElem::Deref | ProjectionElem::Downcast(..) => { @@ -648,7 +644,6 @@ impl<'tcx> Validator<'_, 'tcx> { // `check_consts::qualifs` but without recursion. let mut has_mut_interior = match place.base { PlaceBase::Local(local) => self.qualif_local::(*local), - PlaceBase::Static(_) => false, }; if has_mut_interior { let mut place_projection = place.projection; diff --git a/src/librustc_mir/transform/simplify.rs b/src/librustc_mir/transform/simplify.rs index fb7f4fac4dc..e96baefc822 100644 --- a/src/librustc_mir/transform/simplify.rs +++ b/src/librustc_mir/transform/simplify.rs @@ -388,13 +388,9 @@ impl<'tcx> MutVisitor<'tcx> for LocalUpdater<'tcx> { // Remove unnecessary StorageLive and StorageDead annotations. data.statements.retain(|stmt| match &stmt.kind { StatementKind::StorageLive(l) | StatementKind::StorageDead(l) => self.map[*l].is_some(), - StatementKind::Assign(box (place, _)) => { - if let PlaceBase::Local(local) = place.base { - self.map[local].is_some() - } else { - true - } - } + StatementKind::Assign(box (place, _)) => match place.base { + PlaceBase::Local(local) => self.map[local].is_some(), + }, _ => true, }); self.super_basic_block_data(block, data);