Function std::ptr::write_unaligned 1.17.0[−][src]
pub const unsafe fn write_unaligned<T>(dst: *mut T, src: T)
Overwrites a memory location with the given value without reading or dropping the old value.
Unlike write(), the pointer may be unaligned.
write_unaligned does not drop the contents of dst. This is safe, but it
could leak allocations or resources, so care should be taken not to overwrite
an object that should be dropped.
Additionally, it does not drop src. Semantically, src is moved into the
location pointed to by dst.
This is appropriate for initializing uninitialized memory, or overwriting
memory that has previously been read with read_unaligned.
Safety
Behavior is undefined if any of the following conditions are violated:
dstmust be valid for writes.
Note that even if T has size 0, the pointer must be non-NULL.
On packed structs
It is currently impossible to create raw pointers to unaligned fields of a packed struct.
Attempting to create a raw pointer to an unaligned struct field with
an expression such as &packed.unaligned as *const FieldType creates an
intermediate unaligned reference before converting that to a raw pointer.
That this reference is temporary and immediately cast is inconsequential
as the compiler always expects references to be properly aligned.
As a result, using &packed.unaligned as *const FieldType causes immediate
undefined behavior in your program.
An example of what not to do and how this relates to write_unaligned is:
#[repr(packed, C)] struct Packed { _padding: u8, unaligned: u32, } let v = 0x01020304; let mut packed: Packed = unsafe { std::mem::zeroed() }; #[allow(unaligned_references)] let v = unsafe { // Here we attempt to take the address of a 32-bit integer which is not aligned. let unaligned = // A temporary unaligned reference is created here which results in // undefined behavior regardless of whether the reference is used or not. &mut packed.unaligned // Casting to a raw pointer doesn't help; the mistake already happened. as *mut u32; std::ptr::write_unaligned(unaligned, v); v };Run
Accessing unaligned fields directly with e.g. packed.unaligned is safe however.
Examples
Write an usize value to a byte buffer:
use std::mem; fn write_usize(x: &mut [u8], val: usize) { assert!(x.len() >= mem::size_of::<usize>()); let ptr = x.as_mut_ptr() as *mut usize; unsafe { ptr.write_unaligned(val) } }Run