about summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
authorOliver Scherer <github35764891676564198441@oli-obk.de>2020-05-01 15:52:08 +0200
committerOliver Scherer <github35764891676564198441@oli-obk.de>2020-05-01 15:52:08 +0200
commit004208fc46467c5e171e739559f77c0fafbbe87a (patch)
treed31df1114e7298b5763124cb8e50a636c3c07b7c /src
parentfd61d06772d17c6242265d860fbfb5eafd282caa (diff)
downloadrust-004208fc46467c5e171e739559f77c0fafbbe87a.tar.gz
rust-004208fc46467c5e171e739559f77c0fafbbe87a.zip
Move recursion check for zsts back to read site instead of access check site.
Diffstat (limited to 'src')
-rw-r--r--src/librustc_mir/interpret/memory.rs13
-rw-r--r--src/librustc_mir/interpret/operand.rs9
-rw-r--r--src/test/ui/consts/static-ice.rs27
3 files changed, 37 insertions, 12 deletions
diff --git a/src/librustc_mir/interpret/memory.rs b/src/librustc_mir/interpret/memory.rs
index d1881524172..39e428cee1d 100644
--- a/src/librustc_mir/interpret/memory.rs
+++ b/src/librustc_mir/interpret/memory.rs
@@ -400,18 +400,7 @@ impl<'mir, 'tcx, M: Machine<'mir, 'tcx>> Memory<'mir, 'tcx, M> {
 
                 // We can still be zero-sized in this branch, in which case we have to
                 // return `None`.
-                if size.bytes() == 0 {
-                    // We may be reading from a static.
-                    // In order to ensure that `static FOO: Type = FOO;` causes a cycle error
-                    // instead of magically pulling *any* ZST value from the ether, we need to
-                    // actually access the referenced allocation. The caller is likely
-                    // to short-circuit on `None`, so we trigger the access here to
-                    // make sure it happens.
-                    self.get_raw(ptr.alloc_id)?;
-                    None
-                } else {
-                    Some(ptr)
-                }
+                if size.bytes() == 0 { None } else { Some(ptr) }
             }
         })
     }
diff --git a/src/librustc_mir/interpret/operand.rs b/src/librustc_mir/interpret/operand.rs
index b924f20ce7c..05844eb126c 100644
--- a/src/librustc_mir/interpret/operand.rs
+++ b/src/librustc_mir/interpret/operand.rs
@@ -240,6 +240,15 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
         {
             Some(ptr) => ptr,
             None => {
+                if let Scalar::Ptr(ptr) = mplace.ptr {
+                    // We may be reading from a static.
+                    // In order to ensure that `static FOO: Type = FOO;` causes a cycle error
+                    // instead of magically pulling *any* ZST value from the ether, we need to
+                    // actually access the referenced allocation. The caller is likely
+                    // to short-circuit on `None`, so we trigger the access here to
+                    // make sure it happens.
+                    self.memory.get_raw(ptr.alloc_id)?;
+                }
                 return Ok(Some(ImmTy {
                     // zero-sized type
                     imm: Scalar::zst().into(),
diff --git a/src/test/ui/consts/static-ice.rs b/src/test/ui/consts/static-ice.rs
new file mode 100644
index 00000000000..a6d90e44e34
--- /dev/null
+++ b/src/test/ui/consts/static-ice.rs
@@ -0,0 +1,27 @@
+// check-pass
+
+#[derive(Copy, Clone)]
+pub struct Glfw;
+
+static mut GLFW: Option<Glfw> = None;
+pub fn new() -> Glfw {
+    unsafe {
+        if let Some(glfw) = GLFW {
+            return glfw;
+        } else {
+            todo!()
+        }
+    };
+}
+
+extern "C" {
+    static _dispatch_queue_attr_concurrent: [u8; 0];
+}
+
+static DISPATCH_QUEUE_CONCURRENT: &'static [u8; 0] =
+    unsafe { &_dispatch_queue_attr_concurrent };
+
+fn main() {
+    *DISPATCH_QUEUE_CONCURRENT;
+    new();
+}