about summary refs log tree commit diff
diff options
context:
space:
mode:
authorChristian Poveda <christianpoveda@protonmail.com>2019-11-26 10:00:41 -0500
committerChristian Poveda <christianpoveda@protonmail.com>2019-12-02 09:10:09 -0500
commit683f5c9c23a07fc6434b3e15207aa12144c90420 (patch)
treecb35f92063d8f28ea3c1d8cda8862e7d59297e8b
parente31a1368fda9c5b4b4bc39e69754b19d36dff8c2 (diff)
downloadrust-683f5c9c23a07fc6434b3e15207aa12144c90420.tar.gz
rust-683f5c9c23a07fc6434b3e15207aa12144c90420.zip
Disallow cell borrowing
-rw-r--r--src/librustc_mir/transform/check_consts/ops.rs50
-rw-r--r--src/librustc_mir/transform/check_consts/validation.rs13
2 files changed, 36 insertions, 27 deletions
diff --git a/src/librustc_mir/transform/check_consts/ops.rs b/src/librustc_mir/transform/check_consts/ops.rs
index be5845eaa36..1d23b6e27f3 100644
--- a/src/librustc_mir/transform/check_consts/ops.rs
+++ b/src/librustc_mir/transform/check_consts/ops.rs
@@ -1,7 +1,6 @@
 //! Concrete error types for all operations which may be invalid in a certain const context.
 
 use rustc::hir::def_id::DefId;
-use rustc::mir::BorrowKind;
 use rustc::session::config::nightly_options;
 use rustc::ty::TyCtxt;
 use syntax::feature_gate::feature_err;
@@ -181,36 +180,39 @@ impl NonConstOp for Loop {
 }
 
 #[derive(Debug)]
-pub struct MutBorrow(pub BorrowKind);
+pub struct CellBorrow;
+impl NonConstOp for CellBorrow {
+    fn emit_error(&self, item: &Item<'_, '_>, span: Span) {
+        span_err!(item.tcx.sess, span, E0492,
+            "cannot borrow a constant which may contain \
+            interior mutability, create a static instead");
+    }
+}
+
+#[derive(Debug)]
+pub struct MutBorrow;
 impl NonConstOp for MutBorrow {
     fn feature_gate(tcx: TyCtxt<'_>) -> Option<bool> {
         Some(tcx.features().const_mut_refs)
     }
 
     fn emit_error(&self, item: &Item<'_, '_>, span: Span) {
-        let kind = self.0;
-        if let BorrowKind::Mut { .. } = kind {
-            let mut err = struct_span_err!(item.tcx.sess, span, E0017,
-                                           "references in {}s may only refer \
-                                            to immutable values", item.const_kind());
-            err.span_label(span, format!("{}s require immutable values",
-                                                item.const_kind()));
-            if item.tcx.sess.teach(&err.get_code().unwrap()) {
-                err.note("References in statics and constants may only refer \
-                          to immutable values.\n\n\
-                          Statics are shared everywhere, and if they refer to \
-                          mutable data one might violate memory safety since \
-                          holding multiple mutable references to shared data \
-                          is not allowed.\n\n\
-                          If you really want global mutable state, try using \
-                          static mut or a global UnsafeCell.");
-            }
-            err.emit();
-        } else {
-            span_err!(item.tcx.sess, span, E0492,
-                      "cannot borrow a constant which may contain \
-                       interior mutability, create a static instead");
+        let mut err = struct_span_err!(item.tcx.sess, span, E0017,
+                                       "references in {}s may only refer \
+                                        to immutable values", item.const_kind());
+        err.span_label(span, format!("{}s require immutable values",
+                                            item.const_kind()));
+        if item.tcx.sess.teach(&err.get_code().unwrap()) {
+            err.note("References in statics and constants may only refer \
+                      to immutable values.\n\n\
+                      Statics are shared everywhere, and if they refer to \
+                      mutable data one might violate memory safety since \
+                      holding multiple mutable references to shared data \
+                      is not allowed.\n\n\
+                      If you really want global mutable state, try using \
+                      static mut or a global UnsafeCell.");
         }
+        err.emit();
     }
 }
 
diff --git a/src/librustc_mir/transform/check_consts/validation.rs b/src/librustc_mir/transform/check_consts/validation.rs
index 783c64ece73..4a55bce767d 100644
--- a/src/librustc_mir/transform/check_consts/validation.rs
+++ b/src/librustc_mir/transform/check_consts/validation.rs
@@ -360,7 +360,11 @@ impl Visitor<'tcx> for Validator<'_, 'mir, 'tcx> {
                 };
 
                 if !is_allowed {
-                    self.check_op(ops::MutBorrow(kind));
+                    if let BorrowKind::Mut{ .. } = kind {
+                        self.check_op(ops::MutBorrow);
+                    } else {
+                        self.check_op(ops::CellBorrow);
+                    }
                 }
             }
 
@@ -385,7 +389,11 @@ impl Visitor<'tcx> for Validator<'_, 'mir, 'tcx> {
                 );
 
                 if borrowed_place_has_mut_interior {
-                    self.check_op(ops::MutBorrow(kind));
+                    if let BorrowKind::Mut{ .. } = kind {
+                        self.check_op(ops::MutBorrow);
+                    } else {
+                        self.check_op(ops::CellBorrow);
+                    }
                 }
             }
 
@@ -452,7 +460,6 @@ impl Visitor<'tcx> for Validator<'_, 'mir, 'tcx> {
             }
         }
     }
-
     fn visit_projection_elem(
         &mut self,
         place_base: &PlaceBase<'tcx>,