diff --git a/tests/ui/layout/randomize.rs b/tests/ui/layout/randomize.rs index da8414bc3e2df..b0d67b2097318 100644 --- a/tests/ui/layout/randomize.rs +++ b/tests/ui/layout/randomize.rs @@ -1,17 +1,25 @@ -//@ build-pass +//@ run-pass //@ revisions: normal randomize-layout -//@ [randomize-layout]compile-flags: -Zrandomize-layout +//@ [randomize-layout]compile-flags: -Zrandomize-layout -Zlayout-seed=1 -#![crate_type = "lib"] +use std::ptr; -struct Foo(u32, T, u8); - -struct Wrapper(T); +// these types only have their field offsets taken, they're never constructed +#[allow(dead_code)] +pub struct Foo(u32, T, u8); +#[allow(dead_code)] +pub struct Wrapper(T); #[repr(transparent)] -struct TransparentWrapper(u16); +#[allow(dead_code)] +pub struct TransparentWrapper(u16); const _: () = { + // fn pointers are treated interchangably and don't affect layout + assert!( + std::mem::offset_of!(Foo::, 1) == std::mem::offset_of!(Foo:: usize>, 1) + ); + // behavior of the current implementation, not guaranteed #[cfg(not(randomize_layout))] assert!(std::mem::offset_of!(Foo::, 1) == std::mem::offset_of!(Foo::>, 1)); @@ -28,3 +36,15 @@ const _: () = { std::mem::offset_of!(Foo::, 1) != std::mem::offset_of!(Foo::, 1) ); }; + +#[allow(dead_code)] +struct Unsizable(usize, T); + +fn main() { + // offset_of doesn't let us probe the unsized field, check at runtime. + let x = &Unsizable::<[u32; 4]>(0, [0; 4]); + let y: &Unsizable::<[u32]> = x; + + // type coercion must not change the layout. + assert_eq!(ptr::from_ref(&x.1).addr(), ptr::from_ref(&y.1).addr()); +}