-
Notifications
You must be signed in to change notification settings - Fork 12.7k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
MaybeUninit::zeroed
isn't actually zeroed
#111616
Comments
use std::mem::MaybeUninit;
pub fn foo(thing: MaybeUninit<(u8, u16)>) {
let bytes: [u8; 4] = unsafe { core::mem::transmute(thing) };
println!("bytes = {bytes:?}");
}
fn main() {
foo(MaybeUninit::zeroed())
}
This happens, because |
Looks like a side effect of #99604 This is... not easy to fix. |
Since the problem in these examples is the behavior of copying |
Why? I don't see anything in the docs of // this is currently not overwriting the second byte
pub unsafe fn write_uninit(x: *mut MaybeUninit<(u8, u16)>) {
let zeroed = [0u8; 4];
*x = *(&zeroed as *const _ as *const _);
}
// this does zero all four
pub unsafe fn ptr_copy_uninit(x: *mut MaybeUninit<(u8, u16)>) {
let zeroed = [0u8; 4];
ptr::copy::<MaybeUninit<(u8, u16)>>(&zeroed as *const _ as *const _, x, 1);
} edit: playground (the code above has UB due to alignment, fixed in the linked code, but it didn't affect the results) |
Yeah the problem here is not |
Found while looking at #111608.
I tried this code: playground
I expected to see this happen: outputs
[0, 0, 0, 0]
Instead, this happened: outputs
[0, 1, 0, 0]
MaybeUninit<T>
should behave like an untyped bag of bytes that happens to have the same size and align asT
. In particular, it should not have padding.This affects debug and release mode.
The emitted LLVM IR with
-C opt-level=3 -C no-prepopulate-passes
looks like this, so this is on rustc and not on LLVM: goldboltMeta
rustc --version --verbose
:@rustbot label A-codegen
The text was updated successfully, but these errors were encountered: