diff options
Diffstat (limited to 'src/librustc_mir')
| -rw-r--r-- | src/librustc_mir/borrow_check/invalidation.rs | 2 | ||||
| -rw-r--r-- | src/librustc_mir/borrow_check/mod.rs | 2 | ||||
| -rw-r--r-- | src/librustc_mir/borrow_check/type_check/mod.rs | 2 | ||||
| -rw-r--r-- | src/librustc_mir/dataflow/impls/borrowed_locals.rs | 1 | ||||
| -rw-r--r-- | src/librustc_mir/dataflow/move_paths/builder.rs | 1 | ||||
| -rw-r--r-- | src/librustc_mir/interpret/machine.rs | 7 | ||||
| -rw-r--r-- | src/librustc_mir/interpret/memory.rs | 2 | ||||
| -rw-r--r-- | src/librustc_mir/interpret/step.rs | 6 | ||||
| -rw-r--r-- | src/librustc_mir/interpret/validity.rs | 1 | ||||
| -rw-r--r-- | src/librustc_mir/monomorphize/collector.rs | 1 | ||||
| -rw-r--r-- | src/librustc_mir/transform/check_consts/qualifs.rs | 4 | ||||
| -rw-r--r-- | src/librustc_mir/transform/check_consts/validation.rs | 12 | ||||
| -rw-r--r-- | src/librustc_mir/transform/promote_consts.rs | 2 | ||||
| -rw-r--r-- | src/librustc_mir/transform/qualify_min_const_fn.rs | 3 |
14 files changed, 40 insertions, 6 deletions
diff --git a/src/librustc_mir/borrow_check/invalidation.rs b/src/librustc_mir/borrow_check/invalidation.rs index 178e3db17cd..213dae130a9 100644 --- a/src/librustc_mir/borrow_check/invalidation.rs +++ b/src/librustc_mir/borrow_check/invalidation.rs @@ -295,6 +295,8 @@ impl<'cx, 'tcx> InvalidationGenerator<'cx, 'tcx> { self.access_place(location, place, access_kind, LocalMutationIsAllowed::No); } + Rvalue::ThreadLocalRef(_) => {} + Rvalue::Use(ref operand) | Rvalue::Repeat(ref operand, _) | Rvalue::UnaryOp(_ /*un_op*/, ref operand) diff --git a/src/librustc_mir/borrow_check/mod.rs b/src/librustc_mir/borrow_check/mod.rs index e3098fc1cfc..8238f40bbc8 100644 --- a/src/librustc_mir/borrow_check/mod.rs +++ b/src/librustc_mir/borrow_check/mod.rs @@ -1290,6 +1290,8 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> { ); } + Rvalue::ThreadLocalRef(_) => {} + Rvalue::Use(ref operand) | Rvalue::Repeat(ref operand, _) | Rvalue::UnaryOp(_ /*un_op*/, ref operand) diff --git a/src/librustc_mir/borrow_check/type_check/mod.rs b/src/librustc_mir/borrow_check/type_check/mod.rs index ac7da7ee42d..fdc3b291ba4 100644 --- a/src/librustc_mir/borrow_check/type_check/mod.rs +++ b/src/librustc_mir/borrow_check/type_check/mod.rs @@ -2353,6 +2353,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> { } Rvalue::AddressOf(..) + | Rvalue::ThreadLocalRef(..) | Rvalue::Use(..) | Rvalue::Len(..) | Rvalue::BinaryOp(..) @@ -2368,6 +2369,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> { fn rvalue_user_ty(&self, rvalue: &Rvalue<'tcx>) -> Option<UserTypeAnnotationIndex> { match rvalue { Rvalue::Use(_) + | Rvalue::ThreadLocalRef(_) | Rvalue::Repeat(..) | Rvalue::Ref(..) | Rvalue::AddressOf(..) diff --git a/src/librustc_mir/dataflow/impls/borrowed_locals.rs b/src/librustc_mir/dataflow/impls/borrowed_locals.rs index b61dc56407e..99052657415 100644 --- a/src/librustc_mir/dataflow/impls/borrowed_locals.rs +++ b/src/librustc_mir/dataflow/impls/borrowed_locals.rs @@ -176,6 +176,7 @@ where mir::Rvalue::Cast(..) | mir::Rvalue::Use(..) + | mir::Rvalue::ThreadLocalRef(..) | mir::Rvalue::Repeat(..) | mir::Rvalue::Len(..) | mir::Rvalue::BinaryOp(..) diff --git a/src/librustc_mir/dataflow/move_paths/builder.rs b/src/librustc_mir/dataflow/move_paths/builder.rs index 427ab1ca5cd..2779c9e1073 100644 --- a/src/librustc_mir/dataflow/move_paths/builder.rs +++ b/src/librustc_mir/dataflow/move_paths/builder.rs @@ -324,6 +324,7 @@ impl<'b, 'a, 'tcx> Gatherer<'b, 'a, 'tcx> { fn gather_rvalue(&mut self, rvalue: &Rvalue<'tcx>) { match *rvalue { + Rvalue::ThreadLocalRef(_) => {} // not-a-move Rvalue::Use(ref operand) | Rvalue::Repeat(ref operand, _) | Rvalue::Cast(_, ref operand, _) diff --git a/src/librustc_mir/interpret/machine.rs b/src/librustc_mir/interpret/machine.rs index 39b0218c5d7..b5dc40d9551 100644 --- a/src/librustc_mir/interpret/machine.rs +++ b/src/librustc_mir/interpret/machine.rs @@ -358,6 +358,13 @@ pub trait Machine<'mir, 'tcx>: Sized { _mem: &Memory<'mir, 'tcx, Self>, _ptr: Pointer<Self::PointerTag>, ) -> InterpResult<'tcx, u64>; + + fn thread_local_alloc_id( + _ecx: &mut InterpCx<'mir, 'tcx, Self>, + did: DefId, + ) -> InterpResult<'tcx, AllocId> { + throw_unsup!(ThreadLocalStatic(did)) + } } // A lot of the flexibility above is just needed for `Miri`, but all "compile-time" machines diff --git a/src/librustc_mir/interpret/memory.rs b/src/librustc_mir/interpret/memory.rs index 61c365644c7..d7f64542aa7 100644 --- a/src/librustc_mir/interpret/memory.rs +++ b/src/librustc_mir/interpret/memory.rs @@ -437,6 +437,7 @@ impl<'mir, 'tcx, M: Machine<'mir, 'tcx>> Memory<'mir, 'tcx, M> { Some(GlobalAlloc::Function(..)) => throw_ub!(DerefFunctionPointer(id)), None => throw_ub!(PointerUseAfterFree(id)), Some(GlobalAlloc::Static(def_id)) => { + assert!(!tcx.is_thread_local_static(def_id)); // Notice that every static has two `AllocId` that will resolve to the same // thing here: one maps to `GlobalAlloc::Static`, this is the "lazy" ID, // and the other one is maps to `GlobalAlloc::Memory`, this is returned by @@ -592,6 +593,7 @@ impl<'mir, 'tcx, M: Machine<'mir, 'tcx>> Memory<'mir, 'tcx, M> { // be held throughout the match. match self.tcx.get_global_alloc(id) { Some(GlobalAlloc::Static(did)) => { + assert!(!self.tcx.is_thread_local_static(did)); // Use size and align of the type. let ty = self.tcx.type_of(did); let layout = self.tcx.layout_of(ParamEnv::empty().and(ty)).unwrap(); diff --git a/src/librustc_mir/interpret/step.rs b/src/librustc_mir/interpret/step.rs index fd9815975c1..c15714260dc 100644 --- a/src/librustc_mir/interpret/step.rs +++ b/src/librustc_mir/interpret/step.rs @@ -141,6 +141,12 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> { use rustc_middle::mir::Rvalue::*; match *rvalue { + ThreadLocalRef(did) => { + let id = M::thread_local_alloc_id(self, did)?; + let val = Scalar::Ptr(self.tag_global_base_pointer(id.into())); + self.write_scalar(val, dest)?; + } + Use(ref operand) => { // Avoid recomputing the layout let op = self.eval_operand(operand, Some(dest.layout))?; diff --git a/src/librustc_mir/interpret/validity.rs b/src/librustc_mir/interpret/validity.rs index e962dfb2b3e..b6676e8263e 100644 --- a/src/librustc_mir/interpret/validity.rs +++ b/src/librustc_mir/interpret/validity.rs @@ -418,6 +418,7 @@ impl<'rt, 'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> ValidityVisitor<'rt, 'mir, ' // Skip validation entirely for some external statics let alloc_kind = self.ecx.tcx.get_global_alloc(ptr.alloc_id); if let Some(GlobalAlloc::Static(did)) = alloc_kind { + assert!(!self.ecx.tcx.is_thread_local_static(did)); // See const_eval::machine::MemoryExtra::can_access_statics for why // this check is so important. // This check is reachable when the const just referenced the static, diff --git a/src/librustc_mir/monomorphize/collector.rs b/src/librustc_mir/monomorphize/collector.rs index c75e8414e8c..6d7b0c830da 100644 --- a/src/librustc_mir/monomorphize/collector.rs +++ b/src/librustc_mir/monomorphize/collector.rs @@ -1136,6 +1136,7 @@ fn create_mono_items_for_default_impls<'tcx>( fn collect_miri<'tcx>(tcx: TyCtxt<'tcx>, alloc_id: AllocId, output: &mut Vec<MonoItem<'tcx>>) { match tcx.global_alloc(alloc_id) { GlobalAlloc::Static(def_id) => { + assert!(!tcx.is_thread_local_static(def_id)); let instance = Instance::mono(tcx, def_id); if should_monomorphize_locally(tcx, &instance) { trace!("collecting static {:?}", def_id); diff --git a/src/librustc_mir/transform/check_consts/qualifs.rs b/src/librustc_mir/transform/check_consts/qualifs.rs index 05a7c78d59d..5d604d8e3d7 100644 --- a/src/librustc_mir/transform/check_consts/qualifs.rs +++ b/src/librustc_mir/transform/check_consts/qualifs.rs @@ -153,7 +153,9 @@ where F: FnMut(Local) -> bool, { match rvalue { - Rvalue::NullaryOp(..) => Q::in_any_value_of_ty(cx, rvalue.ty(cx.body, cx.tcx)), + Rvalue::ThreadLocalRef(_) | Rvalue::NullaryOp(..) => { + Q::in_any_value_of_ty(cx, rvalue.ty(cx.body, cx.tcx)) + } Rvalue::Discriminant(place) | Rvalue::Len(place) => { in_place::<Q, _>(cx, in_local, place.as_ref()) diff --git a/src/librustc_mir/transform/check_consts/validation.rs b/src/librustc_mir/transform/check_consts/validation.rs index 80094e154bf..354fd200fc5 100644 --- a/src/librustc_mir/transform/check_consts/validation.rs +++ b/src/librustc_mir/transform/check_consts/validation.rs @@ -263,11 +263,11 @@ impl Validator<'mir, 'tcx> { } fn check_static(&mut self, def_id: DefId, span: Span) { - if self.tcx.is_thread_local_static(def_id) { - self.check_op_spanned(ops::ThreadLocalAccess, span) - } else { - self.check_op_spanned(ops::StaticAccess, span) - } + assert!( + !self.tcx.is_thread_local_static(def_id), + "tls access is checked in `Rvalue::ThreadLocalRef" + ); + self.check_op_spanned(ops::StaticAccess, span) } } @@ -332,6 +332,8 @@ impl Visitor<'tcx> for Validator<'mir, 'tcx> { self.super_rvalue(rvalue, location); match *rvalue { + Rvalue::ThreadLocalRef(_) => self.check_op(ops::ThreadLocalAccess), + Rvalue::Use(_) | Rvalue::Repeat(..) | Rvalue::UnaryOp(UnOp::Neg, _) diff --git a/src/librustc_mir/transform/promote_consts.rs b/src/librustc_mir/transform/promote_consts.rs index 6caa2b48f3d..2c8ad00fd06 100644 --- a/src/librustc_mir/transform/promote_consts.rs +++ b/src/librustc_mir/transform/promote_consts.rs @@ -603,6 +603,8 @@ impl<'tcx> Validator<'_, 'tcx> { } match rvalue { + Rvalue::ThreadLocalRef(_) => Err(Unpromotable), + Rvalue::NullaryOp(..) => Ok(()), Rvalue::Discriminant(place) | Rvalue::Len(place) => self.validate_place(place.as_ref()), diff --git a/src/librustc_mir/transform/qualify_min_const_fn.rs b/src/librustc_mir/transform/qualify_min_const_fn.rs index ead530bded8..5615aa84eec 100644 --- a/src/librustc_mir/transform/qualify_min_const_fn.rs +++ b/src/librustc_mir/transform/qualify_min_const_fn.rs @@ -156,6 +156,9 @@ fn check_rvalue( span: Span, ) -> McfResult { match rvalue { + Rvalue::ThreadLocalRef(_) => { + Err((span, "cannot access thread local storage in const fn".into())) + } Rvalue::Repeat(operand, _) | Rvalue::Use(operand) => { check_operand(tcx, operand, span, def_id, body) } |
