]> git.lizzy.rs Git - rust.git/commitdiff
Also catch static mutation at evaluation time
authorOliver Scherer <github35764891676564198441@oli-obk.de>
Mon, 19 Nov 2018 12:49:07 +0000 (13:49 +0100)
committerOliver Scherer <github35764891676564198441@oli-obk.de>
Mon, 19 Nov 2018 15:46:03 +0000 (16:46 +0100)
15 files changed:
src/librustc/ich/impls_ty.rs
src/librustc/mir/interpret/error.rs
src/librustc_mir/interpret/memory.rs
src/librustc_mir/transform/const_prop.rs
src/librustc_mir/transform/qualify_consts.rs
src/test/ui/consts/const-eval/assign-to-static-within-other-static-2.rs [new file with mode: 0644]
src/test/ui/consts/const-eval/assign-to-static-within-other-static-2.stderr [new file with mode: 0644]
src/test/ui/consts/const-eval/assign-to-static-within-other-static.rs
src/test/ui/consts/const-eval/assign-to-static-within-other-static.stderr
src/test/ui/error-codes/E0017.rs
src/test/ui/error-codes/E0017.stderr
src/test/ui/error-codes/E0388.rs
src/test/ui/error-codes/E0388.stderr
src/test/ui/write-to-static-mut-in-static.rs
src/test/ui/write-to-static-mut-in-static.stderr

index f3a62975dd9f4547eb254960fc8d605c5ffa9a36..fc970400f6ccf98c5fbe7ecf893fd94641af588f 100644 (file)
@@ -423,6 +423,7 @@ impl<'tcx, O> for enum mir::interpret::EvalErrorKind<'tcx, O>
         CalledClosureAsFunction,
         VtableForArgumentlessMethod,
         ModifiedConstantMemory,
+        ModifiedStatic,
         AssumptionNotHeld,
         InlineAsm,
         ReallocateNonBasePtr,
index f28aa41ed42221a22053b389bd9cbdc429309312..5895b6cab9abd41336a2ef77e59eb200dbfef2e0 100644 (file)
@@ -276,6 +276,7 @@ pub enum EvalErrorKind<'tcx, O> {
     CalledClosureAsFunction,
     VtableForArgumentlessMethod,
     ModifiedConstantMemory,
+    ModifiedStatic,
     AssumptionNotHeld,
     InlineAsm,
     TypeNotPrimitive(Ty<'tcx>),
@@ -380,6 +381,8 @@ pub fn description(&self) -> &str {
                 "tried to call a vtable function without arguments",
             ModifiedConstantMemory =>
                 "tried to modify constant memory",
+            ModifiedStatic =>
+                "tried to modify a static's initial value from another static's initializer",
             AssumptionNotHeld =>
                 "`assume` argument was false",
             InlineAsm =>
index e125927e7d2732ea8c0c97d1c7b4746371076065..68a91b0a3bd2806ec12fb15976ce0ef7d640f017 100644 (file)
@@ -423,10 +423,10 @@ pub fn get_mut(
             if alloc.mutability == Mutability::Immutable {
                 return err!(ModifiedConstantMemory);
             }
-            let kind = M::STATIC_KIND.expect(
-                "An allocation is being mutated but the machine does not expect that to happen"
-            );
-            Ok((MemoryKind::Machine(kind), alloc.into_owned()))
+            match M::STATIC_KIND {
+                Some(kind) => Ok((MemoryKind::Machine(kind), alloc.into_owned())),
+                None => err!(ModifiedStatic),
+            }
         });
         // Unpack the error type manually because type inference doesn't
         // work otherwise (and we cannot help it because `impl Trait`)
index 885d70dc4304dee3e3cd02c3118df7555aab58b6..51327464266d5baf45b45d088a9ab6ccd4aedb5d 100644 (file)
@@ -197,6 +197,7 @@ fn use_ecx<F, T>(
                     | CalledClosureAsFunction
                     | VtableForArgumentlessMethod
                     | ModifiedConstantMemory
+                    | ModifiedStatic
                     | AssumptionNotHeld
                     // FIXME: should probably be removed and turned into a bug! call
                     | TypeNotPrimitive(_)
index 31a0dc1494ce148d8bbb2d67ac061e05c85aa234..1371b9a9977075b766e6e864634595a62144cb1b 100644 (file)
@@ -249,7 +249,8 @@ fn assign(&mut self, dest: &Place<'tcx>, location: Location) {
                 match dest {
                     Place::Local(index) => break *index,
                     Place::Projection(proj) => dest = &proj.base,
-                    Place::Promoted(..) | Place::Static(..) => {
+                    Place::Promoted(..) => bug!("promoteds don't exist yet during promotion"),
+                    Place::Static(..) => {
                         // Catch more errors in the destination.
                         self.visit_place(
                             dest,
@@ -495,6 +496,10 @@ fn visit_place(&mut self,
                 // Only allow statics (not consts) to refer to other statics.
                 if self.mode == Mode::Static || self.mode == Mode::StaticMut {
                     if context.is_mutating_use() {
+                        // this is not strictly necessary as miri will also bail out
+                        // For interior mutability we can't really catch this statically as that
+                        // goes through raw pointers and intermediate temporaries, so miri has
+                        // to catch this anyway
                         self.tcx.sess.span_err(
                             self.span,
                             "cannot mutate statics in the initializer of another static",
diff --git a/src/test/ui/consts/const-eval/assign-to-static-within-other-static-2.rs b/src/test/ui/consts/const-eval/assign-to-static-within-other-static-2.rs
new file mode 100644 (file)
index 0000000..ef0de61
--- /dev/null
@@ -0,0 +1,30 @@
+// Copyright 2018 The Rust Project Developers. See the COPYRIGHT
+// file at the top-level directory of this distribution and at
+// http://rust-lang.org/COPYRIGHT.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+// New test for #53818: modifying static memory at compile-time is not allowed.
+// The test should never compile successfully
+
+#![feature(const_raw_ptr_deref)]
+#![feature(const_let)]
+
+use std::cell::UnsafeCell;
+
+struct Foo(UnsafeCell<u32>);
+
+unsafe impl Send for Foo {}
+unsafe impl Sync for Foo {}
+
+static FOO: Foo = Foo(UnsafeCell::new(42));
+
+static BAR: () = unsafe {
+    *FOO.0.get() = 5; //~ ERROR could not evaluate static initializer
+};
+
+fn main() {}
diff --git a/src/test/ui/consts/const-eval/assign-to-static-within-other-static-2.stderr b/src/test/ui/consts/const-eval/assign-to-static-within-other-static-2.stderr
new file mode 100644 (file)
index 0000000..0892b05
--- /dev/null
@@ -0,0 +1,9 @@
+error[E0080]: could not evaluate static initializer
+  --> $DIR/assign-to-static-within-other-static-2.rs:27:5
+   |
+LL |     *FOO.0.get() = 5; //~ ERROR could not evaluate static initializer
+   |     ^^^^^^^^^^^^^^^^ tried to modify a static's initial value from another static's initializer
+
+error: aborting due to previous error
+
+For more information about this error, try `rustc --explain E0080`.
index 5113d73b38414c41b8997e127f67846344f7fb26..6f16f644eec68177c7d9161f7c29d7b0c6589cb3 100644 (file)
 
 use std::cell::UnsafeCell;
 
-struct Foo(UnsafeCell<u32>);
-
-unsafe impl Send for Foo {}
-unsafe impl Sync for Foo {}
-
-static FOO: Foo = Foo(UnsafeCell::new(42));
-
-static BAR: () = unsafe {
-    *FOO.0.get() = 5;
-};
-
-static mut FOO2: u32 = 42;
-static BOO2: () = unsafe {
-    FOO2 = 5;
+static mut FOO: u32 = 42;
+static BOO: () = unsafe {
+    FOO = 5; //~ ERROR cannot mutate statics in the initializer of another static
 };
 
 fn main() {}
index 87f02e8e4cf7ef1384ab0d2bbadd15a9d0b25c47..ca652c9df32adb2c1f6869e2fcfc35d5118dbdca 100644 (file)
@@ -1,8 +1,8 @@
 error: cannot mutate statics in the initializer of another static
-  --> $DIR/assign-to-static-within-other-static.rs:32:5
+  --> $DIR/assign-to-static-within-other-static.rs:21:5
    |
-LL |     FOO2 = 5;
-   |     ^^^^^^^^
+LL |     FOO = 5; //~ ERROR cannot mutate statics in the initializer of another static
+   |     ^^^^^^^
 
 error: aborting due to previous error
 
index c98c35a1442add7ec66fd110eeef3d6da2fbf593..bf400fde365bea419f99a853a2ecb2781f179c05 100644 (file)
@@ -14,5 +14,6 @@
 const CR: &'static mut i32 = &mut C; //~ ERROR E0017
 static STATIC_REF: &'static mut i32 = &mut X; //~ ERROR E0017
                                               //~| ERROR cannot borrow
+                                              //~| ERROR cannot mutate statics
 static CONST_REF: &'static mut i32 = &mut C; //~ ERROR E0017
 fn main() {}
index 411b9f3139782571a53e30dc3c12e469ed17058b..94a90d92d3e77a43b0af0e2223b8fc70a1586fee 100644 (file)
@@ -4,6 +4,12 @@ error[E0017]: references in constants may only refer to immutable values
 LL | const CR: &'static mut i32 = &mut C; //~ ERROR E0017
    |                              ^^^^^^ constants require immutable values
 
+error: cannot mutate statics in the initializer of another static
+  --> $DIR/E0017.rs:15:39
+   |
+LL | static STATIC_REF: &'static mut i32 = &mut X; //~ ERROR E0017
+   |                                       ^^^^^^
+
 error[E0017]: references in statics may only refer to immutable values
   --> $DIR/E0017.rs:15:39
    |
@@ -17,12 +23,12 @@ LL | static STATIC_REF: &'static mut i32 = &mut X; //~ ERROR E0017
    |                                            ^
 
 error[E0017]: references in statics may only refer to immutable values
-  --> $DIR/E0017.rs:17:38
+  --> $DIR/E0017.rs:18:38
    |
 LL | static CONST_REF: &'static mut i32 = &mut C; //~ ERROR E0017
    |                                      ^^^^^^ statics require immutable values
 
-error: aborting due to 4 previous errors
+error: aborting due to 5 previous errors
 
 Some errors occurred: E0017, E0596.
 For more information about an error, try `rustc --explain E0017`.
index c002badfef64c34d4fc15e9902d08c65ddd6d526..3203798c70958de0538b45e5116264ab86da45d4 100644 (file)
@@ -14,6 +14,7 @@
 const CR: &'static mut i32 = &mut C; //~ ERROR E0017
 static STATIC_REF: &'static mut i32 = &mut X; //~ ERROR E0017
                                               //~| ERROR cannot borrow
+                                              //~| ERROR cannot mutate statics
 static CONST_REF: &'static mut i32 = &mut C; //~ ERROR E0017
 
 fn main() {}
index d2263cd4034b853a86a2477a8b95b16e79b5de16..46efda9147b6d5b686049e7cb7bea7e353504e90 100644 (file)
@@ -4,6 +4,12 @@ error[E0017]: references in constants may only refer to immutable values
 LL | const CR: &'static mut i32 = &mut C; //~ ERROR E0017
    |                              ^^^^^^ constants require immutable values
 
+error: cannot mutate statics in the initializer of another static
+  --> $DIR/E0388.rs:15:39
+   |
+LL | static STATIC_REF: &'static mut i32 = &mut X; //~ ERROR E0017
+   |                                       ^^^^^^
+
 error[E0017]: references in statics may only refer to immutable values
   --> $DIR/E0388.rs:15:39
    |
@@ -17,12 +23,12 @@ LL | static STATIC_REF: &'static mut i32 = &mut X; //~ ERROR E0017
    |                                            ^
 
 error[E0017]: references in statics may only refer to immutable values
-  --> $DIR/E0388.rs:17:38
+  --> $DIR/E0388.rs:18:38
    |
 LL | static CONST_REF: &'static mut i32 = &mut C; //~ ERROR E0017
    |                                      ^^^^^^ statics require immutable values
 
-error: aborting due to 4 previous errors
+error: aborting due to 5 previous errors
 
 Some errors occurred: E0017, E0596.
 For more information about an error, try `rustc --explain E0017`.
index 1ea74f73723b762224327b69e57a6184e55b2c8e..191f09b54ee7324a334877e8dc4405af6586dd81 100644 (file)
 
 pub static mut A: u32 = 0;
 pub static mut B: () = unsafe { A = 1; };
-//~^ ERROR statements in statics are unstable
+//~^ ERROR cannot mutate statics in the initializer of another static
 
 pub static mut C: u32 = unsafe { C = 1; 0 };
-//~^ ERROR statements in statics are unstable
+//~^ ERROR cannot mutate statics in the initializer of another static
 
 pub static D: u32 = D;
 
index f07d240746fdfe3c98947d39aa8a2483eeee0791..673a71b4642f39028ae47e1a13b093819a9fc8ef 100644 (file)
@@ -1,19 +1,14 @@
-error[E0658]: statements in statics are unstable (see issue #48821)
+error: cannot mutate statics in the initializer of another static
   --> $DIR/write-to-static-mut-in-static.rs:14:33
    |
 LL | pub static mut B: () = unsafe { A = 1; };
    |                                 ^^^^^
-   |
-   = help: add #![feature(const_let)] to the crate attributes to enable
 
-error[E0658]: statements in statics are unstable (see issue #48821)
+error: cannot mutate statics in the initializer of another static
   --> $DIR/write-to-static-mut-in-static.rs:17:34
    |
 LL | pub static mut C: u32 = unsafe { C = 1; 0 };
    |                                  ^^^^^
-   |
-   = help: add #![feature(const_let)] to the crate attributes to enable
 
 error: aborting due to 2 previous errors
 
-For more information about this error, try `rustc --explain E0658`.