Closed
Description
The following code fails on stable:
When compiled in release mode, the "optimized out"
assert is optimized out by LLVM even though it checks the exact same condition as the other assert, as can be verified by testing in debug mode.
Note that it's theoretically possible for the stack to be aligned correctly such that the bug is suppressed, but that's not likely. The 256's can be replaced with larger alignments if that happens.
The bug is caused by the impl of Box<dyn FnOnce>
copying self
to the stack with the default alignment of 16.
#![allow(dead_code)]
#[repr(align(256))]
struct A {
v: u8
}
impl A {
fn f(&self) -> *const A {
assert_eq!(self as *const A as usize % 256, 0, "optimized out");
self
}
}
fn f2(v: u8) -> Box<dyn FnOnce() -> *const A> {
let a = A { v };
Box::new(move || {
a.f()
})
}
#[test]
fn test() {
let addr = f2(0)();
assert_eq!(addr as usize % 256, 0, "addr: {:?}", addr);
}
Metadata
Metadata
Assignees
Labels
Area: Dynamically-sized types (DSTs)Things relevant to the [future] cranelift backendCategory: This is a bug.`#![feature(unsized_locals)]`Issue: A soundness hole (worst kind of bug), see: https://en.wikipedia.org/wiki/SoundnessHigh priorityRelevant to the compiler team, which will review and decide on the PR/issue.