Enum ConvertError

enum ConvertError<A, S, V>

Zerocopy's generic error type.

Generally speaking, zerocopy's conversions may fail for one of up to three reasons:

However, not all conversions produce all errors. For instance, FromBytes::ref_from_bytes may fail due to alignment or size issues, but not validity issues. This generic error type captures these (im)possibilities via parameterization: A is parameterized with AlignmentError, S is parameterized with SizeError, and V is parameterized with Infallible.

Zerocopy never uses this type directly in its API. Rather, we provide three pre-parameterized aliases:

Variants

Alignment(A)

The conversion source was improperly aligned.

Size(S)

The conversion source was of incorrect size.

Validity(V)

The conversion source contained invalid data.

Implementations

impl<Src, Dst: ?Sized + TryFromBytes> ConvertError<Infallible, SizeError<Src, Dst>, ValidityError<Src, Dst>>

fn into_src(self: Self) -> Src

Produces the source underlying the failed conversion.

fn map_src<NewSrc, impl FnOnce(Src) -> NewSrc: FnOnce(Src) -> NewSrc>(self: Self, f: impl FnOnce(Src) -> NewSrc) -> TryReadError<NewSrc, Dst>

Maps the source value associated with the conversion error.

This can help mitigate [issues with Send, Sync and 'static bounds][self#send-sync-and-static].

Examples

use core::num::NonZeroU32;
use zerocopy::*;

let source: [u8; 3] = [0, 0, 0];

// Try to read a `NonZeroU32` from `source`.
let maybe_u32: Result<NonZeroU32, TryReadError<&[u8], NonZeroU32>>
    = NonZeroU32::try_read_from_bytes(&source[..]);

// Map the error's source to its size.
let maybe_u32: Result<NonZeroU32, TryReadError<usize, NonZeroU32>> =
    maybe_u32.map_err(|err| {
        err.map_src(|src| src.len())
    });

impl<Src, Dst: ?Sized + TryFromBytes> ConvertError<AlignmentError<Src, Dst>, SizeError<Src, Dst>, ValidityError<Src, Dst>>

fn into_src(self: Self) -> Src

Produces the source underlying the failed conversion.

fn map_src<NewSrc, impl FnOnce(Src) -> NewSrc: FnOnce(Src) -> NewSrc>(self: Self, f: impl FnOnce(Src) -> NewSrc) -> TryCastError<NewSrc, Dst>

Maps the source value associated with the conversion error.

This can help mitigate [issues with Send, Sync and 'static bounds][self#send-sync-and-static].

Examples

use core::num::NonZeroU32;
use zerocopy::*;

let source: [u8; 3] = [0, 0, 0];

// Try to read a `NonZeroU32` from `source`.
let maybe_u32: Result<&NonZeroU32, TryCastError<&[u8], NonZeroU32>>
    = NonZeroU32::try_ref_from_bytes(&source[..]);

// Map the error's source to its size and address.
let maybe_u32: Result<&NonZeroU32, TryCastError<(usize, usize), NonZeroU32>> =
    maybe_u32.map_err(|err| {
        err.map_src(|src| (src.len(), src.as_ptr() as usize))
    });

impl<Src, Dst: ?Sized> ConvertError<AlignmentError<Src, Dst>, SizeError<Src, Dst>, Infallible>

fn into_src(self: Self) -> Src

Produces the source underlying the failed conversion.

fn map_src<NewSrc, impl FnOnce(Src) -> NewSrc: FnOnce(Src) -> NewSrc>(self: Self, f: impl FnOnce(Src) -> NewSrc) -> CastError<NewSrc, Dst>

Maps the source value associated with the conversion error.

This can help mitigate [issues with Send, Sync and 'static bounds][self#send-sync-and-static].

Examples

use zerocopy::*;

let source: [u8; 3] = [0, 1, 2];

// Try to read a `u32` from `source`. This will fail because there are insufficient
// bytes in `source`.
let maybe_u32: Result<&u32, CastError<&[u8], u32>> = u32::ref_from_bytes(&source[..]);

// Map the error's source to its size and address.
let maybe_u32: Result<&u32, CastError<(usize, usize), u32>> = maybe_u32.map_err(|err| {
    err.map_src(|src| (src.len(), src.as_ptr() as usize))
});

impl<A, S, V> Error for ConvertError<A, S, V>

impl<A, S, V> Freeze for ConvertError<A, S, V>

impl<A, S, V> RefUnwindSafe for ConvertError<A, S, V>

impl<A, S, V> Send for ConvertError<A, S, V>

impl<A, S, V> StructuralPartialEq for ConvertError<A, S, V>

impl<A, S, V> Sync for ConvertError<A, S, V>

impl<A, S, V> Unpin for ConvertError<A, S, V>

impl<A, S, V> UnsafeUnpin for ConvertError<A, S, V>

impl<A, S, V> UnwindSafe for ConvertError<A, S, V>

impl<A: $crate::clone::Clone, S: $crate::clone::Clone, V: $crate::clone::Clone> Clone for ConvertError<A, S, V>

fn clone(self: &Self) -> ConvertError<A, S, V>

impl<A: $crate::cmp::Eq, S: $crate::cmp::Eq, V: $crate::cmp::Eq> Eq for ConvertError<A, S, V>

impl<A: $crate::cmp::PartialEq, S: $crate::cmp::PartialEq, V: $crate::cmp::PartialEq> PartialEq for ConvertError<A, S, V>

fn eq(self: &Self, other: &ConvertError<A, S, V>) -> bool

impl<A: fmt::Debug, S: fmt::Debug, V: fmt::Debug> Debug for ConvertError<A, S, V>

fn fmt(self: &Self, f: &mut Formatter<'_>) -> Result

impl<A: fmt::Display, S: fmt::Display, V: fmt::Display> Display for ConvertError<A, S, V>

fn fmt(self: &Self, f: &mut Formatter<'_>) -> Result

impl<Src, Dst: ?Sized + TryFromBytes, A, S> From for ConvertError<A, S, ValidityError<Src, Dst>>

fn from(err: ValidityError<Src, Dst>) -> Self

impl<Src, Dst: ?Sized + Unaligned, S, V> From for ConvertError<Infallible, S, V>

fn from(err: ConvertError<AlignmentError<Src, Dst>, S, V>) -> ConvertError<Infallible, S, V>

Infallibly discards the alignment error from this ConvertError since Dst is unaligned.

Since Dst: Unaligned, it is impossible to encounter an alignment error. This method permits discarding that alignment error infallibly and replacing it with Infallible.

Examples

use core::convert::Infallible;
use zerocopy::*;
# use zerocopy_derive::*;

#[derive(TryFromBytes, KnownLayout, Unaligned, Immutable)]
#[repr(C, packed)]
struct Bools {
    one: bool,
    two: bool,
    many: [bool],
}

impl Bools {
    fn parse(bytes: &[u8]) -> Result<&Bools, AlignedTryCastError<&[u8], Bools>> {
        // Since `Bools: Unaligned`, we can infallibly discard
        // the alignment error.
        Bools::try_ref_from_bytes(bytes).map_err(Into::into)
    }
}

impl<Src, Dst: ?Sized, A, V> From for ConvertError<A, SizeError<Src, Dst>, V>

fn from(err: SizeError<Src, Dst>) -> Self

impl<Src, Dst: ?Sized, S, V> From for ConvertError<AlignmentError<Src, Dst>, S, V>

fn from(err: AlignmentError<Src, Dst>) -> Self

impl<T> Any for ConvertError<A, S, V>

fn type_id(self: &Self) -> TypeId

impl<T> Borrow for ConvertError<A, S, V>

fn borrow(self: &Self) -> &T

impl<T> BorrowMut for ConvertError<A, S, V>

fn borrow_mut(self: &mut Self) -> &mut T

impl<T> CloneToUninit for ConvertError<A, S, V>

unsafe fn clone_to_uninit(self: &Self, dest: *mut u8)

impl<T> From for ConvertError<A, S, V>

fn from(t: T) -> T

Returns the argument unchanged.

impl<T, U> Into for ConvertError<A, S, V>

fn into(self: Self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of [From]<T> for U chooses to do.

impl<T, U> TryFrom for ConvertError<A, S, V>

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

impl<T, U> TryInto for ConvertError<A, S, V>

fn try_into(self: Self) -> Result<U, <U as TryFrom<T>>::Error>