Trait FromZeros

unsafe trait FromZeros: TryFromBytes

Types for which a sequence of 0 bytes is a valid instance.

Any memory region of the appropriate length which is guaranteed to contain only zero bytes can be viewed as any FromZeros type with no runtime overhead. This is useful whenever memory is known to be in a zeroed state, such memory returned from some allocation routines.

Warning: Padding bytes

Note that, when a value is moved or copied, only the non-padding bytes of that value are guaranteed to be preserved. It is unsound to assume that values written to padding bytes are preserved after a move or copy. For more details, see the FromBytes docs.

Implementation

Do not implement this trait yourself! Instead, use #[derive(FromZeros)]; e.g.:

# use zerocopy_derive::{FromZeros, Immutable};
#[derive(FromZeros)]
struct MyStruct {
# /*
    ...
# */
}

#[derive(FromZeros)]
#[repr(u8)]
enum MyEnum {
#   Variant0,
# /*
    ...
# */
}

#[derive(FromZeros, Immutable)]
union MyUnion {
#   variant: u8,
# /*
    ...
# */
}

This derive performs a sophisticated, compile-time safety analysis to determine whether a type is FromZeros.

Safety

This section describes what is required in order for T: FromZeros, and what unsafe code may assume of such types. If you don't plan on implementing FromZeros manually, and you don't plan on writing unsafe code that operates on FromZeros types, then you don't need to read this section.

If T: FromZeros, then unsafe code may assume that it is sound to produce a T whose bytes are all initialized to zero. If a type is marked as FromZeros which violates this contract, it may cause undefined behavior.

#[derive(FromZeros)] only permits types which satisfy these requirements.

Provided Methods

fn zero(self: &mut Self)

Overwrites self with zeros.

Sets every byte in self to 0. While this is similar to doing *self = Self::new_zeroed(), it differs in that zero does not semantically drop the current value and replace it with a new one — it simply modifies the bytes of the existing value.

Examples

# use zerocopy::FromZeros;
# use zerocopy_derive::*;
#
#[derive(FromZeros)]
#[repr(C)]
struct PacketHeader {
    src_port: [u8; 2],
    dst_port: [u8; 2],
    length: [u8; 2],
    checksum: [u8; 2],
}

let mut header = PacketHeader {
    src_port: 100u16.to_be_bytes(),
    dst_port: 200u16.to_be_bytes(),
    length: 300u16.to_be_bytes(),
    checksum: 400u16.to_be_bytes(),
};

header.zero();

assert_eq!(header.src_port, [0, 0]);
assert_eq!(header.dst_port, [0, 0]);
assert_eq!(header.length, [0, 0]);
assert_eq!(header.checksum, [0, 0]);
fn new_zeroed() -> Self
where
    Self: Sized

Creates an instance of Self from zeroed bytes.

Examples

# use zerocopy::FromZeros;
# use zerocopy_derive::*;
#
#[derive(FromZeros)]
#[repr(C)]
struct PacketHeader {
    src_port: [u8; 2],
    dst_port: [u8; 2],
    length: [u8; 2],
    checksum: [u8; 2],
}

let header: PacketHeader = FromZeros::new_zeroed();

assert_eq!(header.src_port, [0, 0]);
assert_eq!(header.dst_port, [0, 0]);
assert_eq!(header.length, [0, 0]);
assert_eq!(header.checksum, [0, 0]);

Implementors