diff --git a/src/impls.rs b/src/impls.rs index 8d05537d2b..afbbf36402 100644 --- a/src/impls.rs +++ b/src/impls.rs @@ -7,6 +7,8 @@ // This file may not be copied, modified, or distributed except according to // those terms. +use core::mem::MaybeUninit as CoreMaybeUninit; + use super::*; safety_comment! { @@ -628,14 +630,14 @@ safety_comment! { /// SAFETY: /// `TryFromBytes` (with no validator), `FromZeros`, `FromBytes`: /// `MaybeUninit` has no restrictions on its contents. - unsafe_impl!(T => TryFromBytes for MaybeUninit); - unsafe_impl!(T => FromZeros for MaybeUninit); - unsafe_impl!(T => FromBytes for MaybeUninit); + unsafe_impl!(T => TryFromBytes for CoreMaybeUninit); + unsafe_impl!(T => FromZeros for CoreMaybeUninit); + unsafe_impl!(T => FromBytes for CoreMaybeUninit); } -impl_for_transparent_wrapper!(T: Immutable => Immutable for MaybeUninit); -impl_for_transparent_wrapper!(T: Unaligned => Unaligned for MaybeUninit); -assert_unaligned!(MaybeUninit<()>, MaybeUninit); +impl_for_transparent_wrapper!(T: Immutable => Immutable for CoreMaybeUninit); +impl_for_transparent_wrapper!(T: Unaligned => Unaligned for CoreMaybeUninit); +assert_unaligned!(CoreMaybeUninit<()>, CoreMaybeUninit); impl_for_transparent_wrapper!(T: ?Sized + Immutable => Immutable for ManuallyDrop); impl_for_transparent_wrapper!(T: ?Sized + TryFromBytes => TryFromBytes for ManuallyDrop); @@ -1253,8 +1255,8 @@ mod tests { ManuallyDrop>, ManuallyDrop<[UnsafeCell]>, ManuallyDrop<[UnsafeCell]>, - MaybeUninit, - MaybeUninit>, + CoreMaybeUninit, + CoreMaybeUninit>, Wrapping> ); @@ -1296,9 +1298,9 @@ mod tests { Option, Option, Option, - MaybeUninit, - MaybeUninit, - MaybeUninit>, + CoreMaybeUninit, + CoreMaybeUninit, + CoreMaybeUninit>, ManuallyDrop>, ManuallyDrop<[UnsafeCell]>, ManuallyDrop<[UnsafeCell]>, @@ -1760,9 +1762,9 @@ mod tests { assert_impls!(ManuallyDrop<[UnsafeCell]>: KnownLayout, TryFromBytes, FromZeros, FromBytes, IntoBytes, Unaligned, !Immutable); assert_impls!(ManuallyDrop<[UnsafeCell]>: KnownLayout, TryFromBytes, FromZeros, IntoBytes, Unaligned, !Immutable, !FromBytes); - assert_impls!(MaybeUninit: KnownLayout, Immutable, TryFromBytes, FromZeros, FromBytes, Unaligned, !IntoBytes); - assert_impls!(MaybeUninit: KnownLayout, TryFromBytes, FromZeros, FromBytes, !Immutable, !IntoBytes, !Unaligned); - assert_impls!(MaybeUninit>: KnownLayout, TryFromBytes, FromZeros, FromBytes, Unaligned, !Immutable, !IntoBytes); + assert_impls!(CoreMaybeUninit: KnownLayout, Immutable, TryFromBytes, FromZeros, FromBytes, Unaligned, !IntoBytes); + assert_impls!(CoreMaybeUninit: KnownLayout, TryFromBytes, FromZeros, FromBytes, !Immutable, !IntoBytes, !Unaligned); + assert_impls!(CoreMaybeUninit>: KnownLayout, TryFromBytes, FromZeros, FromBytes, Unaligned, !Immutable, !IntoBytes); assert_impls!(Wrapping: KnownLayout, Immutable, TryFromBytes, FromZeros, FromBytes, IntoBytes, Unaligned); // This test is important because it allows us to test our hand-rolled diff --git a/src/lib.rs b/src/lib.rs index 1f9e519eef..fab398dc0d 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -349,7 +349,7 @@ use core::{ fmt::{self, Debug, Display, Formatter}, hash::Hasher, marker::PhantomData, - mem::{self, ManuallyDrop, MaybeUninit}, + mem::{self, ManuallyDrop, MaybeUninit as CoreMaybeUninit}, num::{ NonZeroI128, NonZeroI16, NonZeroI32, NonZeroI64, NonZeroI8, NonZeroIsize, NonZeroU128, NonZeroU16, NonZeroU32, NonZeroU64, NonZeroU8, NonZeroUsize, Wrapping, @@ -727,6 +727,14 @@ pub unsafe trait KnownLayout { /// This is `()` for sized types and `usize` for slice DSTs. type PointerMetadata: PointerMetadata; + /// A maybe-uninitialized analog of `Self` + /// + /// # Safety + /// + /// `Self::LAYOUT` and `Self::MaybeUninit::LAYOUT` are identical. + #[doc(hidden)] + type MaybeUninit: ?Sized + KnownLayout; + /// The layout of `Self`. /// /// # Safety @@ -859,6 +867,35 @@ unsafe impl KnownLayout for [T] { type PointerMetadata = usize; + // SAFETY: `CoreMaybeUninit::LAYOUT` and `T::LAYOUT` are identical + // because `CoreMaybeUninit` has the same size and alignment as `T` [1]. + // Consequently, `[CoreMaybeUninit]::LAYOUT` and `[T]::LAYOUT` are + // identical, because they both lack a fixed-sized prefix and because they + // inherit the alignments of their inner element type (which are identical) + // [2][3]. + // + // `[CoreMaybeUninit]` admits uninitialized bytes at all positions + // because `CoreMaybeUninit` admits uninitialized bytes at all positions + // and because the inner elements of `[CoreMaybeUninit]` are laid out + // back-to-back [2][3]. + // + // [1] Per https://doc.rust-lang.org/1.81.0/std/mem/union.MaybeUninit.html#layout-1: + // + // `MaybeUninit` is guaranteed to have the same size, alignment, and ABI as + // `T` + // + // [2] Per https://doc.rust-lang.org/1.82.0/reference/type-layout.html#slice-layout: + // + // Slices have the same layout as the section of the array they slice. + // + // [3] Per https://doc.rust-lang.org/1.82.0/reference/type-layout.html#array-layout: + // + // An array of `[T; N]` has a size of `size_of::() * N` and the same + // alignment of `T`. Arrays are laid out so that the zero-based `nth` + // element of the array is offset from the start of the array by `n * + // size_of::()` bytes. + type MaybeUninit = [CoreMaybeUninit]; + const LAYOUT: DstLayout = DstLayout::for_slice::(); // SAFETY: `.cast` preserves address and provenance. The returned pointer @@ -911,7 +948,7 @@ impl_known_layout!( T => Option, T: ?Sized => PhantomData, T => Wrapping, - T => MaybeUninit, + T => CoreMaybeUninit, T: ?Sized => *const T, T: ?Sized => *mut T ); @@ -944,6 +981,21 @@ safety_comment! { unsafe_impl_known_layout!(T: ?Sized + KnownLayout => #[repr(T)] UnsafeCell); } +safety_comment! { + /// SAFETY: + /// - By consequence of the invariant on `T::MaybeUninit` that `T::LAYOUT` + /// and `T::MaybeUninit::LAYOUT` are equal, `T` and `T::MaybeUninit` + /// have the same: + /// - Fixed prefix size + /// - Alignment + /// - (For DSTs) trailing slice element size + /// - By consequence of the above, referents `T::MaybeUninit` and `T` have + /// the require the same kind of pointer metadata, and thus it is valid to + /// perform an `as` cast from `*mut T` and `*mut T::MaybeUninit`, and this + /// operation preserves referent size (ie, `size_of_val_raw`). + unsafe_impl_known_layout!(T: ?Sized + KnownLayout => #[repr(T::MaybeUninit)] MaybeUninit); +} + /// Analyzes whether a type is [`FromZeros`]. /// /// This derive analyzes, at compile time, whether the annotated type satisfies @@ -2545,7 +2597,7 @@ pub unsafe trait TryFromBytes { where Self: Sized, { - let candidate = match MaybeUninit::::read_from_bytes(source) { + let candidate = match CoreMaybeUninit::::read_from_bytes(source) { Ok(candidate) => candidate, Err(e) => { return Err(TryReadError::Size(e.with_dst())); @@ -2606,7 +2658,7 @@ pub unsafe trait TryFromBytes { where Self: Sized, { - let (candidate, suffix) = match MaybeUninit::::read_from_prefix(source) { + let (candidate, suffix) = match CoreMaybeUninit::::read_from_prefix(source) { Ok(candidate) => candidate, Err(e) => { return Err(TryReadError::Size(e.with_dst())); @@ -2668,7 +2720,7 @@ pub unsafe trait TryFromBytes { where Self: Sized, { - let (prefix, candidate) = match MaybeUninit::::read_from_suffix(source) { + let (prefix, candidate) = match CoreMaybeUninit::::read_from_suffix(source) { Ok(candidate) => candidate, Err(e) => { return Err(TryReadError::Size(e.with_dst())); @@ -2741,7 +2793,7 @@ fn swap((t, u): (T, U)) -> (U, T) { #[inline(always)] unsafe fn try_read_from( source: S, - mut candidate: MaybeUninit, + mut candidate: CoreMaybeUninit, ) -> Result> { // We use `from_mut` despite not mutating via `c_ptr` so that we don't need // to add a `T: Immutable` bound. @@ -3030,72 +3082,9 @@ pub unsafe trait FromZeros: TryFromBytes { where Self: KnownLayout, { - let size = match count.size_for_metadata(Self::LAYOUT) { - Some(size) => size, - None => return Err(AllocError), - }; - - let align = Self::LAYOUT.align.get(); - // On stable Rust versions <= 1.64.0, `Layout::from_size_align` has a - // bug in which sufficiently-large allocations (those which, when - // rounded up to the alignment, overflow `isize`) are not rejected, - // which can cause undefined behavior. See #64 for details. - // - // TODO(#67): Once our MSRV is > 1.64.0, remove this assertion. - #[allow(clippy::as_conversions)] - let max_alloc = (isize::MAX as usize).saturating_sub(align); - if size > max_alloc { - return Err(AllocError); - } - - // TODO(https://github.com/rust-lang/rust/issues/55724): Use - // `Layout::repeat` once it's stabilized. - let layout = Layout::from_size_align(size, align).or(Err(AllocError))?; - - let ptr = if layout.size() != 0 { - // TODO(#429): Add a "SAFETY" comment and remove this `allow`. - #[allow(clippy::undocumented_unsafe_blocks)] - let ptr = unsafe { alloc::alloc::alloc_zeroed(layout) }; - match NonNull::new(ptr) { - Some(ptr) => ptr, - None => return Err(AllocError), - } - } else { - let align = Self::LAYOUT.align.get(); - // We use `transmute` instead of an `as` cast since Miri (with - // strict provenance enabled) notices and complains that an `as` - // cast creates a pointer with no provenance. Miri isn't smart - // enough to realize that we're only executing this branch when - // we're constructing a zero-sized `Box`, which doesn't require - // provenance. - // - // SAFETY: any initialized bit sequence is a bit-valid `*mut u8`. - // All bits of a `usize` are initialized. - #[allow(clippy::useless_transmute)] - let dangling = unsafe { mem::transmute::(align) }; - // SAFETY: `dangling` is constructed from `Self::LAYOUT.align`, - // which is a `NonZeroUsize`, which is guaranteed to be non-zero. - // - // `Box<[T]>` does not allocate when `T` is zero-sized or when `len` - // is zero, but it does require a non-null dangling pointer for its - // allocation. - // - // TODO(https://github.com/rust-lang/rust/issues/95228): Use - // `std::ptr::without_provenance` once it's stable. That may - // optimize better. As written, Rust may assume that this consumes - // "exposed" provenance, and thus Rust may have to assume that this - // may consume provenance from any pointer whose provenance has been - // exposed. - unsafe { NonNull::new_unchecked(dangling) } - }; - - let ptr = Self::raw_from_ptr_len(ptr, count); - - // TODO(#429): Add a "SAFETY" comment and remove this `allow`. Make sure - // to include a justification that `ptr.as_ptr()` is validly-aligned in - // the ZST case (in which we manually construct a dangling pointer). - #[allow(clippy::undocumented_unsafe_blocks)] - Ok(unsafe { Box::from_raw(ptr.as_ptr()) }) + // SAFETY: The referent of the pointer returned by `alloc_zeroed` is a + // valid instance of `Self`, because `Self` is `FromZeros`. + unsafe { crate::util::new_box(count, alloc::alloc::alloc_zeroed) } } #[deprecated(since = "0.8.0", note = "renamed to `FromZeros::new_box_zeroed_with_elems`")] @@ -4557,7 +4546,7 @@ pub unsafe trait FromBytes: FromZeros { Self: Sized, R: io::Read, { - let mut buf = MaybeUninit::::zeroed(); + let mut buf = CoreMaybeUninit::::zeroed(); let ptr = Ptr::from_mut(&mut buf); // SAFETY: `buf` consists entirely of initialized, zeroed bytes. let ptr = unsafe { ptr.assume_validity::() }; diff --git a/src/util/macros.rs b/src/util/macros.rs index 4745f9556c..248a2a753f 100644 --- a/src/util/macros.rs +++ b/src/util/macros.rs @@ -530,6 +530,17 @@ macro_rules! impl_known_layout { type PointerMetadata = (); + // SAFETY: `CoreMaybeUninit::LAYOUT` and `T::LAYOUT` are + // identical because `CoreMaybeUninit` has the same size and + // alignment as `T` [1], and `CoreMaybeUninit` admits + // uninitialized bytes in all positions. + // + // [1] Per https://doc.rust-lang.org/1.81.0/std/mem/union.MaybeUninit.html#layout-1: + // + // `MaybeUninit` is guaranteed to have the same size, + // alignment, and ABI as `T` + type MaybeUninit = core::mem::MaybeUninit; + const LAYOUT: crate::DstLayout = crate::DstLayout::for_type::<$ty>(); // SAFETY: `.cast` preserves address and provenance. @@ -572,6 +583,7 @@ macro_rules! unsafe_impl_known_layout { fn only_derive_is_allowed_to_implement_this_trait() {} type PointerMetadata = <$repr as KnownLayout>::PointerMetadata; + type MaybeUninit = <$repr as KnownLayout>::MaybeUninit; const LAYOUT: DstLayout = <$repr as KnownLayout>::LAYOUT; diff --git a/src/util/mod.rs b/src/util/mod.rs index d7d1710158..be0d845262 100644 --- a/src/util/mod.rs +++ b/src/util/mod.rs @@ -683,6 +683,114 @@ pub(crate) unsafe fn copy_unchecked(src: &[u8], dst: &mut [u8]) { }; } +/// Unsafely transmutes the given `src` into a type `Dst`. +/// +/// # Safety +/// +/// The value `src` must be a bit-valid instance of `Dst`. +#[inline(always)] +pub(crate) const unsafe fn transmute_unchecked(src: Src) -> Dst { + static_assert!(Src, Dst => core::mem::size_of::() == core::mem::size_of::()); + #[repr(C)] + union Transmute { + src: ManuallyDrop, + dst: ManuallyDrop, + } + // SAFETY: The caller promises that `src` is a bit-valid instance of `Dst`. + unsafe { ManuallyDrop::into_inner(Transmute { src: ManuallyDrop::new(src) }.dst) } +} + +/// Use `allocate` to create a `Box`. +/// +/// # Errors +/// +/// Returns an error on allocation failure. Allocation failure is guaranteed +/// never to cause a panic or an abort. +/// +/// # Safety +/// +/// The referent of the pointer returned by `allocate` must be a bit-valid +/// instance of `T`. +#[must_use = "has no side effects (other than allocation)"] +#[cfg(feature = "alloc")] +#[inline] +pub(crate) unsafe fn new_box( + meta: T::PointerMetadata, + allocate: unsafe fn(core::alloc::Layout) -> *mut u8, +) -> Result, crate::error::AllocError> +where + T: ?Sized + crate::KnownLayout, +{ + use crate::error::AllocError; + use crate::PointerMetadata; + use core::alloc::Layout; + + let size = match meta.size_for_metadata(T::LAYOUT) { + Some(size) => size, + None => return Err(AllocError), + }; + + let align = T::LAYOUT.align.get(); + // On stable Rust versions <= 1.64.0, `Layout::from_size_align` has a bug in + // which sufficiently-large allocations (those which, when rounded up to the + // alignment, overflow `isize`) are not rejected, which can cause undefined + // behavior. See #64 for details. + // + // TODO(#67): Once our MSRV is > 1.64.0, remove this assertion. + #[allow(clippy::as_conversions)] + let max_alloc = (isize::MAX as usize).saturating_sub(align); + if size > max_alloc { + return Err(AllocError); + } + + // TODO(https://github.com/rust-lang/rust/issues/55724): Use + // `Layout::repeat` once it's stabilized. + let layout = Layout::from_size_align(size, align).or(Err(AllocError))?; + + let ptr = if layout.size() != 0 { + // TODO(#429): Add a "SAFETY" comment and remove this `allow`. + #[allow(clippy::undocumented_unsafe_blocks)] + let ptr = unsafe { allocate(layout) }; + match NonNull::new(ptr) { + Some(ptr) => ptr, + None => return Err(AllocError), + } + } else { + let align = T::LAYOUT.align.get(); + // We use `transmute` instead of an `as` cast since Miri (with strict + // provenance enabled) notices and complains that an `as` cast creates a + // pointer with no provenance. Miri isn't smart enough to realize that + // we're only executing this branch when we're constructing a zero-sized + // `Box`, which doesn't require provenance. + // + // SAFETY: any initialized bit sequence is a bit-valid `*mut u8`. All + // bits of a `usize` are initialized. + #[allow(clippy::useless_transmute)] + let dangling = unsafe { mem::transmute::(align) }; + // SAFETY: `dangling` is constructed from `T::LAYOUT.align`, which is a + // `NonZeroUsize`, which is guaranteed to be non-zero. + // + // `Box<[T]>` does not allocate when `T` is zero-sized or when `len` is + // zero, but it does require a non-null dangling pointer for its + // allocation. + // + // TODO(https://github.com/rust-lang/rust/issues/95228): Use + // `std::ptr::without_provenance` once it's stable. That may optimize + // better. As written, Rust may assume that this consumes "exposed" + // provenance, and thus Rust may have to assume that this may consume + // provenance from any pointer whose provenance has been exposed. + unsafe { NonNull::new_unchecked(dangling) } + }; + + let ptr = T::raw_from_ptr_len(ptr, meta); + + // TODO(#429): Add a "SAFETY" comment and remove this `allow`. Make sure to + // include a justification that `ptr.as_ptr()` is validly-aligned in the ZST + // case (in which we manually construct a dangling pointer). + #[allow(clippy::undocumented_unsafe_blocks)] + Ok(unsafe { alloc::boxed::Box::from_raw(ptr.as_ptr()) }) +} + /// Since we support multiple versions of Rust, there are often features which /// have been stabilized in the most recent stable release which do not yet /// exist (stably) on our MSRV. This module provides polyfills for those diff --git a/src/wrappers.rs b/src/wrappers.rs index 0637d76025..97461500dd 100644 --- a/src/wrappers.rs +++ b/src/wrappers.rs @@ -6,7 +6,7 @@ // This file may not be copied, modified, or distributed except according to // those terms. -use core::hash::Hash; +use core::{fmt, hash::Hash}; use super::*; @@ -464,6 +464,137 @@ impl Display for Unalign { } } +/// A wrapper type to construct uninitialized instances of `T`. +/// +/// `MaybeUninit` is identical to the [standard library +/// `MaybeUninit`][core-maybe-uninit] type except that it supports unsized +/// types. +/// +/// # Layout +/// +/// The same layout guarantees and caveats apply to `MaybeUninit` as apply to +/// the [standard library `MaybeUninit`][core-maybe-uninit] with one exception: +/// for `T: !Sized`, there is no single value for `T`'s size. Instead, for such +/// types, the following are guaranteed: +/// - Every [valid size][valid-size] for `T` is a valid size for +/// `MaybeUninit` and vice versa +/// - Given `t: *const T` and `m: *const MaybeUninit` with identical fat +/// pointer metadata, `t` and `m` address the same number of bytes (and +/// likewise for `*mut`) +/// +/// [core-maybe-uninit]: core::mem::MaybeUninit +/// [valid-size]: crate::KnownLayout#what-is-a-valid-size +#[repr(transparent)] +#[doc(hidden)] +pub struct MaybeUninit( + // SAFETY: `MaybeUninit` has the same size as `T`, because (by invariant + // on `T::MaybeUninit`) `T::MaybeUninit` has `T::LAYOUT` identical to `T`, + // and because (invariant on `T::LAYOUT`) we can trust that `LAYOUT` + // accurately reflects the layout of `T`. By invariant on `T::MaybeUninit`, + // it admits uninitialized bytes in all positions. Because `MabyeUninit` is + // marked `repr(transparent)`, these properties additionally hold true for + // `MaybeUninit`. + T::MaybeUninit, +); + +#[doc(hidden)] +impl MaybeUninit { + /// Constructs a `MaybeUninit` initialized with the given value. + #[inline(always)] + pub fn new(val: T) -> Self + where + T: Sized + KnownLayout, + Self: Sized, + { + // SAFETY: It is valid to transmute `val` to `MaybeUninit` because it + // is both valid to transmute `val` to `T::MaybeUninit`, and it is valid + // to transmute from `T::MaybeUninit` to `MaybeUninit`. + // + // First, it is valid to transmute `val` to `T::MaybeUninit` because, by + // invariant on `T::MaybeUninit`: + // - For `T: Sized`, `T` and `T::MaybeUninit` have the same size. + // - All byte sequences of the correct size are valid values of + // `T::MaybeUninit`. + // + // Second, it is additionally valid to transmute from `T::MaybeUninit` + // to `MaybeUninit`, because `MaybeUninit` is a + // `repr(transparent)` wrapper around `T::MaybeUninit`. + // + // These two transmutes are collapsed into one so we don't need to add a + // `T::MaybeUninit: Sized` bound to this function's `where` clause. + unsafe { crate::util::transmute_unchecked(val) } + } + + /// Constructs an uninitialized `MaybeUninit`. + #[must_use] + #[inline(always)] + pub fn uninit() -> Self + where + T: Sized + KnownLayout, + Self: Sized, + { + let uninit = CoreMaybeUninit::::uninit(); + // SAFETY: It is valid to transmute from `CoreMaybeUninit` to + // `MaybeUninit` since they both admit uninitialized bytes in all + // positions, and they have the same size (i.e., that of `T`). + // + // `MaybeUninit` has the same size as `T`, because (by invariant on + // `T::MaybeUninit`) `T::MaybeUninit` has `T::LAYOUT` identical to `T`, + // and because (invariant on `T::LAYOUT`) we can trust that `LAYOUT` + // accurately reflects the layout of `T`. + // + // `CoreMaybeUninit` has the same size as `T` [1] and admits + // uninitialized bytes in all positions. + // + // [1] Per https://doc.rust-lang.org/1.81.0/std/mem/union.MaybeUninit.html#layout-1: + // + // `MaybeUninit` is guaranteed to have the same size, alignment, + // and ABI as `T` + unsafe { crate::util::transmute_unchecked(uninit) } + } + + /// Creates a `Box>`. + /// + /// This function is useful for allocating large, uninit values on the heap + /// without ever creating a temporary instance of `Self` on the stack. + /// + /// # Errors + /// + /// Returns an error on allocation failure. Allocation failure is guaranteed + /// never to cause a panic or an abort. + #[cfg(feature = "alloc")] + #[inline] + pub fn new_boxed_uninit(meta: T::PointerMetadata) -> Result, AllocError> { + // SAFETY: The referent of the pointer returned by `alloc` is a valid + // instance of `Self`, because `Self` is `MaybeUninit` and thus admits + // arbitrary (un)initialized bytes. + unsafe { crate::util::new_box(meta, alloc::alloc::alloc) } + } + + /// Extracts the value from the `MaybeUninit`` container. + /// + /// # Safety + /// + /// The caller must ensure that `self` is in an bit-valid state. Depending + /// on subsequent use, it may also need to be in a library-valid state. + #[inline(always)] + pub unsafe fn assume_init(self) -> T + where + T: Sized + KnownLayout, + Self: Sized, + { + // SAFETY: The caller guarantees that `self` is in an bit-valid state. + unsafe { crate::util::transmute_unchecked(self) } + } +} + +impl fmt::Debug for MaybeUninit { + #[inline] + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.pad(core::any::type_name::()) + } +} + #[cfg(test)] mod tests { use core::panic::AssertUnwindSafe; diff --git a/zerocopy-derive/src/lib.rs b/zerocopy-derive/src/lib.rs index 65414b51fa..acba0dfe56 100644 --- a/zerocopy-derive/src/lib.rs +++ b/zerocopy-derive/src/lib.rs @@ -75,7 +75,8 @@ macro_rules! derive { ($trait:ident => $outer:ident => $inner:ident) => { #[proc_macro_derive($trait)] pub fn $outer(ts: proc_macro::TokenStream) -> proc_macro::TokenStream { - let ast = syn::parse_macro_input!(ts as DeriveInput); + let mut ast = syn::parse_macro_input!(ts as DeriveInput); + ast.generics.make_where_clause(); $inner(&ast, Trait::$trait).into_ts().into() } }; @@ -139,7 +140,31 @@ fn derive_known_layout_inner(ast: &DeriveInput, _top_level: Trait) -> Result = ast + .generics + .params + .iter() + .map(|param| match param { + GenericParam::Type(ty) => { + let ident = &ty.ident; + quote!(#ident) + } + GenericParam::Lifetime(l) => { + let ident = &l.lifetime; + quote!(#ident) + } + GenericParam::Const(cnst) => { + let ident = &cnst.ident; + quote!({#ident}) + } + }) + .collect(); + + let (self_bounds, inner_extras, maybe_uninit_extras) = if let ( + Some(repr), + Some((trailing_field, leading_fields)), + ) = (is_repr_c_struct, fields.split_last()) { let (_name, trailing_field_ty) = trailing_field; @@ -161,11 +186,62 @@ fn derive_known_layout_inner(ast: &DeriveInput, _top_level: Trait) -> Result, + meta: Self::PointerMetadata, + ) -> ::zerocopy::util::macro_util::core_reexport::ptr::NonNull { + use ::zerocopy::KnownLayout; + let trailing = <#trailing_field_ty as KnownLayout>::raw_from_ptr_len(bytes, meta); + let slf = trailing.as_ptr() as *mut Self; + // SAFETY: Constructed from `trailing`, which is non-null. + unsafe { ::zerocopy::util::macro_util::core_reexport::ptr::NonNull::new_unchecked(slf) } + } + + #[inline(always)] + fn pointer_to_metadata(ptr: *mut Self) -> Self::PointerMetadata { + <#trailing_field_ty>::pointer_to_metadata(ptr as *mut _) + } + }; + + let inner_extras = { + let leading_fields_tys = leading_fields_tys.clone(); + quote!( type PointerMetadata = <#trailing_field_ty as ::zerocopy::KnownLayout>::PointerMetadata; + type MaybeUninit = __ZerocopyKnownLayoutMaybeUninit<#(#param_idents,)*>; + // SAFETY: `LAYOUT` accurately describes the layout of `Self`. // The layout of `Self` is reflected using a sequence of // invocations of `DstLayout::{new_zst,extend,pad_to_align}`. @@ -193,53 +269,11 @@ fn derive_known_layout_inner(ast: &DeriveInput, _top_level: Trait) -> Result, - meta: Self::PointerMetadata, - ) -> ::zerocopy::util::macro_util::core_reexport::ptr::NonNull { - use ::zerocopy::KnownLayout; - let trailing = <#trailing_field_ty as KnownLayout>::raw_from_ptr_len(bytes, meta); - let slf = trailing.as_ptr() as *mut Self; - // SAFETY: Constructed from `trailing`, which is non-null. - unsafe { ::zerocopy::util::macro_util::core_reexport::ptr::NonNull::new_unchecked(slf) } - } + #methods + ) + }; - #[inline(always)] - fn pointer_to_metadata(ptr: *mut Self) -> Self::PointerMetadata { - <#trailing_field_ty>::pointer_to_metadata(ptr as *mut _) - } - ), - ) + (SelfBounds::None, inner_extras, Some((repr, methods))) } else { // For enums, unions, and non-`repr(C)` structs, we require that // `Self` is sized, and as a result don't need to reason about the @@ -248,6 +282,8 @@ fn derive_known_layout_inner(ast: &DeriveInput, _top_level: Trait) -> Result; // SAFETY: `LAYOUT` is guaranteed to accurately describe the // layout of `Self`, because that is the documented safety @@ -270,9 +306,88 @@ fn derive_known_layout_inner(ast: &DeriveInput, _top_level: Trait) -> Result () {} ), + None, ) }; + let outer_extras = if let Some((repr, methods)) = maybe_uninit_extras { + let ident = &ast.ident; + let vis = &ast.vis; + let params: Vec<_> = ast.generics.params.iter().collect(); + let (impl_generics, ty_generics, where_clause) = ast.generics.split_for_impl(); + + let (leading, trailing) = if let Some(((_, trailing), leading)) = fields.split_last() { + // Wrap each leading field in `MaybeUninit`. + let leading: Box> = + Box::new(leading.iter().map(|(_name, ty)| { + quote! { + ::zerocopy::util::macro_util::core_reexport::mem::MaybeUninit<#ty> + } + })); + // Defer to the trailing field's `KnownLayout::MaybeUninit`. + let trailing = quote! { + <#trailing as ::zerocopy::KnownLayout>::MaybeUninit + }; + (leading, Some(trailing)) + } else { + let leading: Box> = Box::new(core::iter::empty()); + (leading, None) + }; + + let trailing_ty_for_field = trailing.clone().into_iter(); + let trailing_ty_for_predicate = trailing.into_iter(); + + let predicates = if let Some(ref where_clause) = where_clause { + where_clause.predicates.clone() + } else { + Default::default() + }; + + Some(quote! { + // SAFETY: This has the same layout as the derive target type, + // except that it admits uninit bytes. This is ensured by using the + // same repr as the target type, and by using field types which have + // the same layout as the target type's fields, except that they + // admit uninit bytes. + #repr + #[doc(hidden)] + #vis struct __ZerocopyKnownLayoutMaybeUninit<#(#params),*>( + #(#leading,)* + #(#trailing_ty_for_field,)* + ) #where_clause; + + // SAFETY: We largely defer to the `KnownLayout` implementation on + // the derive target type (both by using the same tokens, and by + // deferring to impl via type-level indirection). This is sound, + // since `__ZerocopyKnownLayoutMaybeUninit` is guaranteed to be + // identical to that of the derive target type, except that + // `__ZerocopyKnownLayoutMaybeUninit` admits uninit bytes. + unsafe impl #impl_generics ::zerocopy::KnownLayout for __ZerocopyKnownLayoutMaybeUninit #ty_generics + where + #(#trailing_ty_for_predicate: ::zerocopy::KnownLayout,)* + #predicates + { + #[allow(clippy::missing_inline_in_public_items)] + #[cfg_attr(coverage_nightly, coverage(off))] + fn only_derive_is_allowed_to_implement_this_trait() {} + + type PointerMetadata = <#ident #ty_generics as ::zerocopy::KnownLayout>::PointerMetadata; + + type MaybeUninit = Self; + + const LAYOUT: ::zerocopy::DstLayout = <#ident #ty_generics as ::zerocopy::KnownLayout>::LAYOUT; + + // SAFETY: Because `__ZerocopyKnownLayoutMaybeUninit` has the + // same layout as `#ident`, it is sound to re-use these method + // implementations across the `KnownLayout` impls for both + // types. + #methods + } + }) + } else { + None + }; + Ok(match &ast.data { Data::Struct(strct) => { let require_trait_bound_on_field_types = if self_bounds == SelfBounds::SIZED { @@ -292,7 +407,8 @@ fn derive_known_layout_inner(ast: &DeriveInput, _top_level: Trait) -> Result { @@ -305,7 +421,8 @@ fn derive_known_layout_inner(ast: &DeriveInput, _top_level: Trait) -> Result { @@ -318,7 +435,8 @@ fn derive_known_layout_inner(ast: &DeriveInput, _top_level: Trait) -> Result TokenStream { SelfBounds::None, None, None, + None, ), Data::Enum(enm) => impl_block( ast, @@ -343,6 +462,7 @@ fn derive_no_cell_inner(ast: &DeriveInput, _top_level: Trait) -> TokenStream { SelfBounds::None, None, None, + None, ), Data::Union(unn) => impl_block( ast, @@ -352,6 +472,7 @@ fn derive_no_cell_inner(ast: &DeriveInput, _top_level: Trait) -> TokenStream { SelfBounds::None, None, None, + None, ), } } @@ -453,6 +574,7 @@ fn derive_try_from_bytes_struct( SelfBounds::None, None, Some(extras), + None, )) } @@ -511,6 +633,7 @@ fn derive_try_from_bytes_union( SelfBounds::None, None, Some(extras), + None, ) } @@ -547,6 +670,7 @@ fn derive_try_from_bytes_enum( SelfBounds::None, None, Some(extra), + None, )) } @@ -629,7 +753,16 @@ unsafe fn gen_trivial_is_bit_valid_unchecked() -> proc_macro2::TokenStream { /// A struct is `FromZeros` if: /// - all fields are `FromZeros` fn derive_from_zeros_struct(ast: &DeriveInput, strct: &DataStruct) -> TokenStream { - impl_block(ast, strct, Trait::FromZeros, FieldBounds::ALL_SELF, SelfBounds::None, None, None) + impl_block( + ast, + strct, + Trait::FromZeros, + FieldBounds::ALL_SELF, + SelfBounds::None, + None, + None, + None, + ) } /// Returns `Ok(index)` if variant `index` of the enum has a discriminant of @@ -765,6 +898,7 @@ fn derive_from_zeros_enum(ast: &DeriveInput, enm: &DataEnum) -> Result TokenStream { // compatibility with `derive(TryFromBytes)` on unions; not for soundness. let field_type_trait_bounds = FieldBounds::All(&[TraitBound::Slf, TraitBound::Other(Trait::Immutable)]); - impl_block(ast, unn, Trait::FromZeros, field_type_trait_bounds, SelfBounds::None, None, None) + impl_block( + ast, + unn, + Trait::FromZeros, + field_type_trait_bounds, + SelfBounds::None, + None, + None, + None, + ) } /// A struct is `FromBytes` if: /// - all fields are `FromBytes` fn derive_from_bytes_struct(ast: &DeriveInput, strct: &DataStruct) -> TokenStream { - impl_block(ast, strct, Trait::FromBytes, FieldBounds::ALL_SELF, SelfBounds::None, None, None) + impl_block( + ast, + strct, + Trait::FromBytes, + FieldBounds::ALL_SELF, + SelfBounds::None, + None, + None, + None, + ) } /// An enum is `FromBytes` if: @@ -813,7 +965,16 @@ fn derive_from_bytes_enum(ast: &DeriveInput, enm: &DataEnum) -> Result TokenStream { // compatibility with `derive(TryFromBytes)` on unions; not for soundness. let field_type_trait_bounds = FieldBounds::All(&[TraitBound::Slf, TraitBound::Other(Trait::Immutable)]); - impl_block(ast, unn, Trait::FromBytes, field_type_trait_bounds, SelfBounds::None, None, None) + impl_block( + ast, + unn, + Trait::FromBytes, + field_type_trait_bounds, + SelfBounds::None, + None, + None, + None, + ) } fn derive_into_bytes_struct(ast: &DeriveInput, strct: &DataStruct) -> Result { @@ -913,6 +1083,7 @@ fn derive_into_bytes_struct(ast: &DeriveInput, strct: &DataStruct) -> Result Result Result Result Result( field_type_trait_bounds: FieldBounds, self_type_trait_bounds: SelfBounds, padding_check: Option, - extras: Option, + inner_extras: Option, + outer_extras: Option, ) -> TokenStream { // In this documentation, we will refer to this hypothetical struct: // @@ -1335,7 +1519,7 @@ fn impl_block( } }); - quote! { + let impl_tokens = quote! { // TODO(#553): Add a test that generates a warning when // `#[allow(deprecated)]` isn't present. #[allow(deprecated)] @@ -1345,8 +1529,22 @@ fn impl_block( { fn only_derive_is_allowed_to_implement_this_trait() {} - #extras + #inner_extras } + }; + + if let Some(outer_extras) = outer_extras { + // So that any items defined in `#outer_extras` don't conflict with + // existing names defined in this scope. + quote! { + const _: () = { + #impl_tokens + + #outer_extras + }; + } + } else { + impl_tokens } } diff --git a/zerocopy-derive/src/output_tests.rs b/zerocopy-derive/src/output_tests.rs index bda09dbbf4..ea429291ea 100644 --- a/zerocopy-derive/src/output_tests.rs +++ b/zerocopy-derive/src/output_tests.rs @@ -110,6 +110,8 @@ fn test_known_layout() { type PointerMetadata = (); + type MaybeUninit = ::zerocopy::util::macro_util::core_reexport::mem::MaybeUninit; + const LAYOUT: ::zerocopy::DstLayout = ::zerocopy::DstLayout::for_type::(); #[inline(always)] @@ -125,6 +127,96 @@ fn test_known_layout() { } } no_build } + + test! { + KnownLayout { + #[repr(C, align(2))] + struct Foo(T, U); + } + expands to { + const _: () = { + #[allow(deprecated)] + unsafe impl ::zerocopy::KnownLayout for Foo + where + U: ::zerocopy::KnownLayout, + { + fn only_derive_is_allowed_to_implement_this_trait() {} + type PointerMetadata = ::PointerMetadata; + type MaybeUninit = __ZerocopyKnownLayoutMaybeUninit; + const LAYOUT: ::zerocopy::DstLayout = { + use ::zerocopy::util::macro_util::core_reexport::num::NonZeroUsize; + use ::zerocopy::{DstLayout, KnownLayout}; + let repr_align = ::zerocopy::util::macro_util::core_reexport::num::NonZeroUsize::new( + 2u32 as usize, + ); + let repr_packed = ::zerocopy::util::macro_util::core_reexport::option::Option::None; + DstLayout::new_zst(repr_align) + .extend(DstLayout::for_type::(), repr_packed) + .extend(::LAYOUT, repr_packed) + .pad_to_align() + }; + #[inline(always)] + fn raw_from_ptr_len( + bytes: ::zerocopy::util::macro_util::core_reexport::ptr::NonNull, + meta: Self::PointerMetadata, + ) -> ::zerocopy::util::macro_util::core_reexport::ptr::NonNull { + use ::zerocopy::KnownLayout; + let trailing = ::raw_from_ptr_len(bytes, meta); + let slf = trailing.as_ptr() as *mut Self; + unsafe { + ::zerocopy::util::macro_util::core_reexport::ptr::NonNull::new_unchecked( + slf, + ) + } + } + #[inline(always)] + fn pointer_to_metadata(ptr: *mut Self) -> Self::PointerMetadata { + ::pointer_to_metadata(ptr as *mut _) + } + } + #[repr(C)] + #[repr(align(2))] + #[doc(hidden)] + struct __ZerocopyKnownLayoutMaybeUninit( + ::zerocopy::util::macro_util::core_reexport::mem::MaybeUninit, + ::MaybeUninit, + ); + unsafe impl ::zerocopy::KnownLayout + for __ZerocopyKnownLayoutMaybeUninit + where + ::MaybeUninit: ::zerocopy::KnownLayout, + { + #[allow(clippy::missing_inline_in_public_items)] + #[cfg_attr(coverage_nightly, coverage(off))] + fn only_derive_is_allowed_to_implement_this_trait() {} + type PointerMetadata = as ::zerocopy::KnownLayout>::PointerMetadata; + type MaybeUninit = Self; + const LAYOUT: ::zerocopy::DstLayout = as ::zerocopy::KnownLayout>::LAYOUT; + #[inline(always)] + fn raw_from_ptr_len( + bytes: ::zerocopy::util::macro_util::core_reexport::ptr::NonNull, + meta: Self::PointerMetadata, + ) -> ::zerocopy::util::macro_util::core_reexport::ptr::NonNull { + use ::zerocopy::KnownLayout; + let trailing = ::raw_from_ptr_len(bytes, meta); + let slf = trailing.as_ptr() as *mut Self; + unsafe { + ::zerocopy::util::macro_util::core_reexport::ptr::NonNull::new_unchecked( + slf, + ) + } + } + #[inline(always)] + fn pointer_to_metadata(ptr: *mut Self) -> Self::PointerMetadata { + ::pointer_to_metadata(ptr as *mut _) + } + } + }; + } no_build + } } #[test] @@ -620,7 +712,7 @@ fn test_try_from_bytes_enum() { }) }; let variant = unsafe { variant.assume_initialized() }; - <___ZerocopyVariantStruct_StructLike<'a, N, X, Y> as ::zerocopy ::TryFromBytes>::is_bit_valid ( + <___ZerocopyVariantStruct_StructLike<'a, N, X, Y> as ::zerocopy ::TryFromBytes>::is_bit_valid ( variant) } ___ZEROCOPY_TAG_TupleLike => { @@ -630,7 +722,7 @@ fn test_try_from_bytes_enum() { }) }; let variant = unsafe { variant.assume_initialized() }; - <___ZerocopyVariantStruct_TupleLike<'a, N, X, Y> as ::zerocopy ::TryFromBytes>::is_bit_valid ( + <___ZerocopyVariantStruct_TupleLike<'a, N, X, Y> as ::zerocopy ::TryFromBytes>::is_bit_valid ( variant) } _ => false, @@ -914,7 +1006,7 @@ fn test_try_from_bytes_enum() { }) }; let variant = unsafe { variant.assume_initialized() }; - <___ZerocopyVariantStruct_StructLike<'a, N, X, Y> as ::zerocopy ::TryFromBytes>::is_bit_valid ( + <___ZerocopyVariantStruct_StructLike<'a, N, X, Y> as ::zerocopy ::TryFromBytes>::is_bit_valid ( variant) } ___ZEROCOPY_TAG_TupleLike => { @@ -924,7 +1016,7 @@ fn test_try_from_bytes_enum() { }) }; let variant = unsafe { variant.assume_initialized() }; - <___ZerocopyVariantStruct_TupleLike<'a, N, X, Y> as ::zerocopy ::TryFromBytes>::is_bit_valid ( + <___ZerocopyVariantStruct_TupleLike<'a, N, X, Y> as ::zerocopy ::TryFromBytes>::is_bit_valid ( variant) } _ => false, @@ -1208,7 +1300,7 @@ fn test_try_from_bytes_enum() { }) }; let variant = unsafe { variant.assume_initialized() }; - <___ZerocopyVariantStruct_StructLike<'a, N, X, Y> as ::zerocopy ::TryFromBytes>::is_bit_valid ( + <___ZerocopyVariantStruct_StructLike<'a, N, X, Y> as ::zerocopy ::TryFromBytes>::is_bit_valid ( variant) } ___ZEROCOPY_TAG_TupleLike => { @@ -1218,7 +1310,7 @@ fn test_try_from_bytes_enum() { }) }; let variant = unsafe { variant.assume_initialized() }; - <___ZerocopyVariantStruct_TupleLike<'a, N, X, Y> as ::zerocopy ::TryFromBytes>::is_bit_valid ( + <___ZerocopyVariantStruct_TupleLike<'a, N, X, Y> as ::zerocopy ::TryFromBytes>::is_bit_valid ( variant) } _ => false, diff --git a/zerocopy-derive/tests/ui-msrv/mid_compile_pass.stderr b/zerocopy-derive/tests/ui-msrv/mid_compile_pass.stderr index 1d6d22df3f..e6f690545f 100644 --- a/zerocopy-derive/tests/ui-msrv/mid_compile_pass.stderr +++ b/zerocopy-derive/tests/ui-msrv/mid_compile_pass.stderr @@ -1,98 +1,159 @@ error[E0277]: the trait bound `T: KnownLayout` is not satisfied - --> tests/ui-msrv/mid_compile_pass.rs:59:26 - | -59 | fn test_kl13(t: T) -> impl KnownLayout { - | ^^^^^^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` + --> tests/ui-msrv/mid_compile_pass.rs:45:10 | -note: required because of the requirements on the impl of `KnownLayout` for `KL13` - --> tests/ui-msrv/mid_compile_pass.rs:55:10 +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` | -55 | #[derive(KnownLayout)] - | ^^^^^^^^^^^ = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) -help: consider restricting type parameter `T` +help: consider further restricting this bound | -59 | fn test_kl13(t: T) -> impl KnownLayout { - | +++++++++++++++++++++++ +47 | struct KL12(u8, T); + | +++++++++++++++++++++++ -error[E0277]: the size for values of type `T` cannot be known at compilation time - --> tests/ui-msrv/mid_compile_pass.rs:31:15 +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-msrv/mid_compile_pass.rs:45:10 | -30 | fn test_kl04(kl: &KL04) { - | - this type parameter needs to be `std::marker::Sized` -31 | assert_kl(kl); - | ^^ doesn't have a size known at compile-time +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` | -note: required because it appears within the type `KL04` - --> tests/ui-msrv/mid_compile_pass.rs:28:8 + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: consider further restricting type parameter `T` | -28 | struct KL04(u8, T); - | ^^^^ -note: required because of the requirements on the impl of `KnownLayout` for `KL04` - --> tests/ui-msrv/mid_compile_pass.rs:27:10 +45 | #[derive(KnownLayout, T: zerocopy::KnownLayout)] + | ++++++++++++++++++++++++++ + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-msrv/mid_compile_pass.rs:45:10 | -27 | #[derive(KnownLayout)] - | ^^^^^^^^^^^ -note: required by a bound in `assert_kl` - --> tests/ui-msrv/mid_compile_pass.rs:23:26 +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` | -23 | fn assert_kl(_: &T) {} - | ^^^^^^^^^^^ required by this bound in `assert_kl` - = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) -help: consider removing the `?Sized` bound to make the type parameter `Sized` +note: required because of the requirements on the impl of `KnownLayout` for `KL12` + --> tests/ui-msrv/mid_compile_pass.rs:45:10 | -30 - fn test_kl04(kl: &KL04) { -30 + fn test_kl04(kl: &KL04) { +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ +note: required by a bound in `KnownLayout` + --> $WORKSPACE/src/lib.rs + | + | / pub unsafe trait KnownLayout { + | | // The `Self: Sized` bound makes it so that `KnownLayout` can still be + | | // object safe. It's not currently object safe thanks to `const LAYOUT`, and + | | // it likely won't be in the future, but there's no reason not to be +... | + | | } + | | } + | |_^ required by this bound in `KnownLayout` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: consider further restricting type parameter `T` | +45 | #[derive(KnownLayout, T: zerocopy::KnownLayout)] + | ++++++++++++++++++++++++++ -error[E0277]: the size for values of type `T` cannot be known at compilation time - --> tests/ui-msrv/mid_compile_pass.rs:40:15 - | -39 | fn test_kl06(kl: &KL06) { - | - this type parameter needs to be `std::marker::Sized` -40 | assert_kl(kl); - | ^^ doesn't have a size known at compile-time +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-msrv/mid_compile_pass.rs:45:10 | -note: required because it appears within the type `KL06` - --> tests/ui-msrv/mid_compile_pass.rs:37:8 +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` | -37 | struct KL06(u8, T); - | ^^^^ -note: required because of the requirements on the impl of `KnownLayout` for `KL06` - --> tests/ui-msrv/mid_compile_pass.rs:36:10 +note: required because of the requirements on the impl of `KnownLayout` for `_::__ZerocopyKnownLayoutMaybeUninit` + --> tests/ui-msrv/mid_compile_pass.rs:45:10 | -36 | #[derive(KnownLayout)] +45 | #[derive(KnownLayout)] | ^^^^^^^^^^^ -note: required by a bound in `assert_kl` - --> tests/ui-msrv/mid_compile_pass.rs:23:26 +note: required by a bound in `KnownLayout` + --> $WORKSPACE/src/lib.rs + | + | / pub unsafe trait KnownLayout { + | | // The `Self: Sized` bound makes it so that `KnownLayout` can still be + | | // object safe. It's not currently object safe thanks to `const LAYOUT`, and + | | // it likely won't be in the future, but there's no reason not to be +... | + | | } + | | } + | |_^ required by this bound in `KnownLayout` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: consider further restricting type parameter `T` + | +45 | #[derive(KnownLayout, T: zerocopy::KnownLayout)] + | ++++++++++++++++++++++++++ + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-msrv/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` | -23 | fn assert_kl(_: &T) {} - | ^^^^^^^^^^^ required by this bound in `assert_kl` = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) -help: consider removing the `?Sized` bound to make the type parameter `Sized` +help: consider restricting type parameter `T` + | +57 | struct KL13(u8, T); + | +++++++++++++++++++++++ + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-msrv/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` | -39 - fn test_kl06(kl: &KL06) { -39 + fn test_kl06(kl: &KL06) { + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: consider further restricting type parameter `T` | +55 | #[derive(KnownLayout, T: zerocopy::KnownLayout)] + | ++++++++++++++++++++++++++ error[E0277]: the trait bound `T: KnownLayout` is not satisfied - --> tests/ui-msrv/mid_compile_pass.rs:50:15 + --> tests/ui-msrv/mid_compile_pass.rs:55:10 | -50 | assert_kl(kl) - | ^^ the trait `KnownLayout` is not implemented for `T` +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` | -note: required because of the requirements on the impl of `KnownLayout` for `KL12` - --> tests/ui-msrv/mid_compile_pass.rs:45:10 +note: required because of the requirements on the impl of `KnownLayout` for `KL13` + --> tests/ui-msrv/mid_compile_pass.rs:55:10 | -45 | #[derive(KnownLayout)] +55 | #[derive(KnownLayout)] | ^^^^^^^^^^^ -note: required by a bound in `assert_kl` - --> tests/ui-msrv/mid_compile_pass.rs:23:26 +note: required by a bound in `KnownLayout` + --> $WORKSPACE/src/lib.rs + | + | / pub unsafe trait KnownLayout { + | | // The `Self: Sized` bound makes it so that `KnownLayout` can still be + | | // object safe. It's not currently object safe thanks to `const LAYOUT`, and + | | // it likely won't be in the future, but there's no reason not to be +... | + | | } + | | } + | |_^ required by this bound in `KnownLayout` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: consider further restricting type parameter `T` + | +55 | #[derive(KnownLayout, T: zerocopy::KnownLayout)] + | ++++++++++++++++++++++++++ + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-msrv/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` + | +note: required because of the requirements on the impl of `KnownLayout` for `_::__ZerocopyKnownLayoutMaybeUninit` + --> tests/ui-msrv/mid_compile_pass.rs:55:10 | -23 | fn assert_kl(_: &T) {} - | ^^^^^^^^^^^ required by this bound in `assert_kl` +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ +note: required by a bound in `KnownLayout` + --> $WORKSPACE/src/lib.rs + | + | / pub unsafe trait KnownLayout { + | | // The `Self: Sized` bound makes it so that `KnownLayout` can still be + | | // object safe. It's not currently object safe thanks to `const LAYOUT`, and + | | // it likely won't be in the future, but there's no reason not to be +... | + | | } + | | } + | |_^ required by this bound in `KnownLayout` = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) -help: consider further restricting this bound +help: consider further restricting type parameter `T` | -49 | fn test_kl12(kl: &KL12) { - | +++++++++++++++++++++++ +55 | #[derive(KnownLayout, T: zerocopy::KnownLayout)] + | ++++++++++++++++++++++++++ diff --git a/zerocopy-derive/tests/ui-msrv/struct.stderr b/zerocopy-derive/tests/ui-msrv/struct.stderr index 4fc4a581ff..609a15ecfd 100644 --- a/zerocopy-derive/tests/ui-msrv/struct.stderr +++ b/zerocopy-derive/tests/ui-msrv/struct.stderr @@ -125,6 +125,62 @@ error[E0277]: the trait bound `NotKnownLayoutDst: zerocopy::KnownLayout` is not = help: see issue #48214 = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +error[E0277]: the trait bound `NotKnownLayoutDst: zerocopy::KnownLayout` is not satisfied + --> tests/ui-msrv/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayoutDst` + | + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `NotKnownLayoutDst: zerocopy::KnownLayout` is not satisfied + --> tests/ui-msrv/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayoutDst` + | +note: required because of the requirements on the impl of `zerocopy::KnownLayout` for `KL08` + --> tests/ui-msrv/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ +note: required by a bound in `zerocopy::KnownLayout` + --> $WORKSPACE/src/lib.rs + | + | / pub unsafe trait KnownLayout { + | | // The `Self: Sized` bound makes it so that `KnownLayout` can still be + | | // object safe. It's not currently object safe thanks to `const LAYOUT`, and + | | // it likely won't be in the future, but there's no reason not to be +... | + | | } + | | } + | |_^ required by this bound in `zerocopy::KnownLayout` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `NotKnownLayoutDst: zerocopy::KnownLayout` is not satisfied + --> tests/ui-msrv/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayoutDst` + | +note: required because of the requirements on the impl of `zerocopy::KnownLayout` for `_::__ZerocopyKnownLayoutMaybeUninit` + --> tests/ui-msrv/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ +note: required by a bound in `zerocopy::KnownLayout` + --> $WORKSPACE/src/lib.rs + | + | / pub unsafe trait KnownLayout { + | | // The `Self: Sized` bound makes it so that `KnownLayout` can still be + | | // object safe. It's not currently object safe thanks to `const LAYOUT`, and + | | // it likely won't be in the future, but there's no reason not to be +... | + | | } + | | } + | |_^ required by this bound in `zerocopy::KnownLayout` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not satisfied --> tests/ui-msrv/struct.rs:47:10 | @@ -134,6 +190,62 @@ error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not sat = help: see issue #48214 = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not satisfied + --> tests/ui-msrv/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayout` + | + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not satisfied + --> tests/ui-msrv/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayout` + | +note: required because of the requirements on the impl of `zerocopy::KnownLayout` for `KL09` + --> tests/ui-msrv/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ +note: required by a bound in `zerocopy::KnownLayout` + --> $WORKSPACE/src/lib.rs + | + | / pub unsafe trait KnownLayout { + | | // The `Self: Sized` bound makes it so that `KnownLayout` can still be + | | // object safe. It's not currently object safe thanks to `const LAYOUT`, and + | | // it likely won't be in the future, but there's no reason not to be +... | + | | } + | | } + | |_^ required by this bound in `zerocopy::KnownLayout` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not satisfied + --> tests/ui-msrv/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayout` + | +note: required because of the requirements on the impl of `zerocopy::KnownLayout` for `_::__ZerocopyKnownLayoutMaybeUninit` + --> tests/ui-msrv/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ +note: required by a bound in `zerocopy::KnownLayout` + --> $WORKSPACE/src/lib.rs + | + | / pub unsafe trait KnownLayout { + | | // The `Self: Sized` bound makes it so that `KnownLayout` can still be + | | // object safe. It's not currently object safe thanks to `const LAYOUT`, and + | | // it likely won't be in the future, but there's no reason not to be +... | + | | } + | | } + | |_^ required by this bound in `zerocopy::KnownLayout` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + error[E0277]: the trait bound `UnsafeCell<()>: zerocopy::Immutable` is not satisfied --> tests/ui-msrv/struct.rs:55:10 | diff --git a/zerocopy-derive/tests/ui-nightly/mid_compile_pass.stderr b/zerocopy-derive/tests/ui-nightly/mid_compile_pass.stderr index c80f1beee7..f3c889d2fd 100644 --- a/zerocopy-derive/tests/ui-nightly/mid_compile_pass.stderr +++ b/zerocopy-derive/tests/ui-nightly/mid_compile_pass.stderr @@ -1,3 +1,102 @@ +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-nightly/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: consider further restricting this bound + | +47 | struct KL12(u8, T); + | +++++++++++++++++++++++ + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-nightly/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` +note: required for `KL12` to implement `KnownLayout` + --> tests/ui-nightly/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: consider further restricting this bound + | +47 | struct KL12(u8, T); + | +++++++++++++++++++++++ + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-nightly/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` +note: required for `_::__ZerocopyKnownLayoutMaybeUninit` to implement `KnownLayout` + --> tests/ui-nightly/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: consider further restricting this bound + | +47 | struct KL12(u8, T); + | +++++++++++++++++++++++ + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-nightly/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: consider restricting type parameter `T` + | +57 | struct KL13(u8, T); + | +++++++++++++++++++++++ + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-nightly/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-nightly/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` +note: required for `KL13` to implement `KnownLayout` + --> tests/ui-nightly/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-nightly/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` +note: required for `_::__ZerocopyKnownLayoutMaybeUninit` to implement `KnownLayout` + --> tests/ui-nightly/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + error[E0277]: the trait bound `T: KnownLayout` is not satisfied --> tests/ui-nightly/mid_compile_pass.rs:59:26 | @@ -82,6 +181,49 @@ help: consider removing the `?Sized` bound to make the type parameter `Sized` 39 + fn test_kl06(kl: &KL06) { | +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-nightly/mid_compile_pass.rs:47:8 + | +47 | struct KL12(u8, T); + | ^^^^^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` +note: required for `KL12` to implement `KnownLayout` + --> tests/ui-nightly/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: consider further restricting this bound + | +47 | struct KL12(u8, T); + | +++++++++++++++++++++++ + +error[E0641]: cannot cast to a pointer of an unknown kind + --> tests/ui-nightly/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ needs more type information + | + = note: the type information given here is insufficient to check whether the pointer cast is valid + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0599]: no function or associated item named `pointer_to_metadata` found for type parameter `T` in the current scope + --> tests/ui-nightly/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ function or associated item not found in `T` +46 | #[repr(C)] +47 | struct KL12(u8, T); + | - function or associated item `pointer_to_metadata` not found for this type parameter + | + = help: items from traits can only be used if the type parameter is bounded by the trait + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: the following trait defines an item `pointer_to_metadata`, perhaps you need to restrict type parameter `T` with it: + | +47 | struct KL12(u8, T); + | +++++++++++++ + error[E0277]: the trait bound `T: KnownLayout` is not satisfied --> tests/ui-nightly/mid_compile_pass.rs:50:15 | @@ -106,3 +248,42 @@ help: consider further restricting this bound | 49 | fn test_kl12(kl: &KL12) { | +++++++++++++++++++++++ + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-nightly/mid_compile_pass.rs:57:8 + | +57 | struct KL13(u8, T); + | ^^^^^^^ the trait `KnownLayout` is not implemented for `T` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` +note: required for `KL13` to implement `KnownLayout` + --> tests/ui-nightly/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0641]: cannot cast to a pointer of an unknown kind + --> tests/ui-nightly/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ needs more type information + | + = note: the type information given here is insufficient to check whether the pointer cast is valid + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0599]: no function or associated item named `pointer_to_metadata` found for type parameter `T` in the current scope + --> tests/ui-nightly/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ function or associated item not found in `T` +56 | #[repr(C)] +57 | struct KL13(u8, T); + | - function or associated item `pointer_to_metadata` not found for this type parameter + | + = help: items from traits can only be used if the type parameter is bounded by the trait + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: the following trait defines an item `pointer_to_metadata`, perhaps you need to restrict type parameter `T` with it: + | +57 | struct KL13(u8, T); + | +++++++++++++ diff --git a/zerocopy-derive/tests/ui-nightly/struct.stderr b/zerocopy-derive/tests/ui-nightly/struct.stderr index 200a12683b..09258d5c3f 100644 --- a/zerocopy-derive/tests/ui-nightly/struct.stderr +++ b/zerocopy-derive/tests/ui-nightly/struct.stderr @@ -151,6 +151,73 @@ help: add `#![feature(trivial_bounds)]` to the crate attributes to enable 9 + #![feature(trivial_bounds)] | +error[E0277]: the trait bound `NotKnownLayoutDst: zerocopy::KnownLayout` is not satisfied + --> tests/ui-nightly/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayoutDst` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayoutDst` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `NotKnownLayoutDst: zerocopy::KnownLayout` is not satisfied + --> tests/ui-nightly/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayoutDst` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayoutDst` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others +note: required for `KL08` to implement `zerocopy::KnownLayout` + --> tests/ui-nightly/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `NotKnownLayoutDst: zerocopy::KnownLayout` is not satisfied + --> tests/ui-nightly/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayoutDst` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayoutDst` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others +note: required for `_::__ZerocopyKnownLayoutMaybeUninit` to implement `zerocopy::KnownLayout` + --> tests/ui-nightly/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not satisfied --> tests/ui-nightly/struct.rs:47:10 | @@ -175,6 +242,73 @@ help: add `#![feature(trivial_bounds)]` to the crate attributes to enable 9 + #![feature(trivial_bounds)] | +error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not satisfied + --> tests/ui-nightly/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayout` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not satisfied + --> tests/ui-nightly/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayout` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others +note: required for `KL09` to implement `zerocopy::KnownLayout` + --> tests/ui-nightly/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not satisfied + --> tests/ui-nightly/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayout` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others +note: required for `_::__ZerocopyKnownLayoutMaybeUninit` to implement `zerocopy::KnownLayout` + --> tests/ui-nightly/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + error[E0277]: the trait bound `UnsafeCell<()>: zerocopy::Immutable` is not satisfied --> tests/ui-nightly/struct.rs:55:10 | @@ -374,6 +508,100 @@ error[E0587]: type has conflicting packed and align representation hints 188 | struct Unaligned3; | ^^^^^^^^^^^^^^^^^ +error[E0277]: the trait bound `NotKnownLayoutDst: zerocopy::KnownLayout` is not satisfied + --> tests/ui-nightly/struct.rs:43:8 + | +43 | struct KL08(u8, NotKnownLayoutDst); + | ^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayoutDst` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayoutDst` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others +note: required for `KL08` to implement `zerocopy::KnownLayout` + --> tests/ui-nightly/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0641]: cannot cast to a pointer of an unknown kind + --> tests/ui-nightly/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ needs more type information + | + = note: the type information given here is insufficient to check whether the pointer cast is valid + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0599]: no function or associated item named `pointer_to_metadata` found for struct `NotKnownLayoutDst` in the current scope + --> tests/ui-nightly/struct.rs:41:10 + | +27 | struct NotKnownLayoutDst([u8]); + | ------------------------ function or associated item `pointer_to_metadata` not found for this struct +... +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ function or associated item not found in `NotKnownLayoutDst` + | + = help: items from traits can only be used if the trait is implemented and in scope + = note: the following trait defines an item `pointer_to_metadata`, perhaps you need to implement it: + candidate #1: `zerocopy::KnownLayout` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not satisfied + --> tests/ui-nightly/struct.rs:49:8 + | +49 | struct KL09(NotKnownLayout, NotKnownLayout); + | ^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayout` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others +note: required for `KL09` to implement `zerocopy::KnownLayout` + --> tests/ui-nightly/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0641]: cannot cast to a pointer of an unknown kind + --> tests/ui-nightly/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ needs more type information + | + = note: the type information given here is insufficient to check whether the pointer cast is valid + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0599]: no function or associated item named `pointer_to_metadata` found for struct `NotKnownLayout` in the current scope + --> tests/ui-nightly/struct.rs:47:10 + | +25 | struct NotKnownLayout; + | --------------------- function or associated item `pointer_to_metadata` not found for this struct +... +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ function or associated item not found in `NotKnownLayout` + | + = help: items from traits can only be used if the trait is implemented and in scope + = note: the following trait defines an item `pointer_to_metadata`, perhaps you need to implement it: + candidate #1: `zerocopy::KnownLayout` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + error[E0277]: the trait bound `AU16: Unaligned` is not satisfied --> tests/ui-nightly/struct.rs:161:28 | diff --git a/zerocopy-derive/tests/ui-stable/mid_compile_pass.stderr b/zerocopy-derive/tests/ui-stable/mid_compile_pass.stderr index 6b1875b036..5bd659b2ee 100644 --- a/zerocopy-derive/tests/ui-stable/mid_compile_pass.stderr +++ b/zerocopy-derive/tests/ui-stable/mid_compile_pass.stderr @@ -1,3 +1,102 @@ +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-stable/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: consider further restricting this bound + | +47 | struct KL12(u8, T); + | +++++++++++++++++++++++ + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-stable/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T`, which is required by `KL12: KnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` +note: required for `KL12` to implement `KnownLayout` + --> tests/ui-stable/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: consider further restricting this bound + | +47 | struct KL12(u8, T); + | +++++++++++++++++++++++ + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-stable/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T`, which is required by `_::__ZerocopyKnownLayoutMaybeUninit: KnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` +note: required for `_::__ZerocopyKnownLayoutMaybeUninit` to implement `KnownLayout` + --> tests/ui-stable/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: consider further restricting this bound + | +47 | struct KL12(u8, T); + | +++++++++++++++++++++++ + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-stable/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: consider restricting type parameter `T` + | +57 | struct KL13(u8, T); + | +++++++++++++++++++++++ + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-stable/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-stable/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T`, which is required by `KL13: KnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` +note: required for `KL13` to implement `KnownLayout` + --> tests/ui-stable/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-stable/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T`, which is required by `_::__ZerocopyKnownLayoutMaybeUninit: KnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` +note: required for `_::__ZerocopyKnownLayoutMaybeUninit` to implement `KnownLayout` + --> tests/ui-stable/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + error[E0277]: the trait bound `T: KnownLayout` is not satisfied --> tests/ui-stable/mid_compile_pass.rs:59:26 | @@ -80,6 +179,49 @@ help: consider removing the `?Sized` bound to make the type parameter `Sized` 39 + fn test_kl06(kl: &KL06) { | +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-stable/mid_compile_pass.rs:47:8 + | +47 | struct KL12(u8, T); + | ^^^^^^^^^^^^^^^ the trait `KnownLayout` is not implemented for `T`, which is required by `KL12: KnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` +note: required for `KL12` to implement `KnownLayout` + --> tests/ui-stable/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: consider further restricting this bound + | +47 | struct KL12(u8, T); + | +++++++++++++++++++++++ + +error[E0641]: cannot cast to a pointer of an unknown kind + --> tests/ui-stable/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ needs more type information + | + = note: the type information given here is insufficient to check whether the pointer cast is valid + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0599]: no function or associated item named `pointer_to_metadata` found for type parameter `T` in the current scope + --> tests/ui-stable/mid_compile_pass.rs:45:10 + | +45 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ function or associated item not found in `T` +46 | #[repr(C)] +47 | struct KL12(u8, T); + | - function or associated item `pointer_to_metadata` not found for this type parameter + | + = help: items from traits can only be used if the type parameter is bounded by the trait + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: the following trait defines an item `pointer_to_metadata`, perhaps you need to restrict type parameter `T` with it: + | +47 | struct KL12(u8, T); + | +++++++++++++ + error[E0277]: the trait bound `T: KnownLayout` is not satisfied --> tests/ui-stable/mid_compile_pass.rs:50:15 | @@ -104,3 +246,42 @@ help: consider further restricting this bound | 49 | fn test_kl12(kl: &KL12) { | +++++++++++++++++++++++ + +error[E0277]: the trait bound `T: KnownLayout` is not satisfied + --> tests/ui-stable/mid_compile_pass.rs:57:8 + | +57 | struct KL13(u8, T); + | ^^^^^^^ the trait `KnownLayout` is not implemented for `T`, which is required by `KL13: KnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `T` +note: required for `KL13` to implement `KnownLayout` + --> tests/ui-stable/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0641]: cannot cast to a pointer of an unknown kind + --> tests/ui-stable/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ needs more type information + | + = note: the type information given here is insufficient to check whether the pointer cast is valid + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0599]: no function or associated item named `pointer_to_metadata` found for type parameter `T` in the current scope + --> tests/ui-stable/mid_compile_pass.rs:55:10 + | +55 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ function or associated item not found in `T` +56 | #[repr(C)] +57 | struct KL13(u8, T); + | - function or associated item `pointer_to_metadata` not found for this type parameter + | + = help: items from traits can only be used if the type parameter is bounded by the trait + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +help: the following trait defines an item `pointer_to_metadata`, perhaps you need to restrict type parameter `T` with it: + | +57 | struct KL13(u8, T); + | +++++++++++++ diff --git a/zerocopy-derive/tests/ui-stable/struct.stderr b/zerocopy-derive/tests/ui-stable/struct.stderr index 789d291606..e1973658e1 100644 --- a/zerocopy-derive/tests/ui-stable/struct.stderr +++ b/zerocopy-derive/tests/ui-stable/struct.stderr @@ -136,6 +136,73 @@ error[E0277]: the trait bound `NotKnownLayoutDst: zerocopy::KnownLayout` is not = help: see issue #48214 = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +error[E0277]: the trait bound `NotKnownLayoutDst: zerocopy::KnownLayout` is not satisfied + --> tests/ui-stable/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayoutDst` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayoutDst` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `NotKnownLayoutDst: zerocopy::KnownLayout` is not satisfied + --> tests/ui-stable/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayoutDst`, which is required by `KL08: zerocopy::KnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayoutDst` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others +note: required for `KL08` to implement `zerocopy::KnownLayout` + --> tests/ui-stable/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `NotKnownLayoutDst: zerocopy::KnownLayout` is not satisfied + --> tests/ui-stable/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayoutDst`, which is required by `_::__ZerocopyKnownLayoutMaybeUninit: zerocopy::KnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayoutDst` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others +note: required for `_::__ZerocopyKnownLayoutMaybeUninit` to implement `zerocopy::KnownLayout` + --> tests/ui-stable/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not satisfied --> tests/ui-stable/struct.rs:47:10 | @@ -156,6 +223,73 @@ error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not sat = help: see issue #48214 = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) +error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not satisfied + --> tests/ui-stable/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayout` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not satisfied + --> tests/ui-stable/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayout`, which is required by `KL09: zerocopy::KnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayout` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others +note: required for `KL09` to implement `zerocopy::KnownLayout` + --> tests/ui-stable/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not satisfied + --> tests/ui-stable/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayout`, which is required by `_::__ZerocopyKnownLayoutMaybeUninit: zerocopy::KnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayout` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others +note: required for `_::__ZerocopyKnownLayoutMaybeUninit` to implement `zerocopy::KnownLayout` + --> tests/ui-stable/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + error[E0277]: the trait bound `UnsafeCell<()>: zerocopy::Immutable` is not satisfied --> tests/ui-stable/struct.rs:55:10 | @@ -335,6 +469,100 @@ error[E0587]: type has conflicting packed and align representation hints 188 | struct Unaligned3; | ^^^^^^^^^^^^^^^^^ +error[E0277]: the trait bound `NotKnownLayoutDst: zerocopy::KnownLayout` is not satisfied + --> tests/ui-stable/struct.rs:43:8 + | +43 | struct KL08(u8, NotKnownLayoutDst); + | ^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayoutDst`, which is required by `KL08: zerocopy::KnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayoutDst` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others +note: required for `KL08` to implement `zerocopy::KnownLayout` + --> tests/ui-stable/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0641]: cannot cast to a pointer of an unknown kind + --> tests/ui-stable/struct.rs:41:10 + | +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ needs more type information + | + = note: the type information given here is insufficient to check whether the pointer cast is valid + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0599]: no function or associated item named `pointer_to_metadata` found for struct `NotKnownLayoutDst` in the current scope + --> tests/ui-stable/struct.rs:41:10 + | +27 | struct NotKnownLayoutDst([u8]); + | ------------------------ function or associated item `pointer_to_metadata` not found for this struct +... +41 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ function or associated item not found in `NotKnownLayoutDst` + | + = help: items from traits can only be used if the trait is implemented and in scope + = note: the following trait defines an item `pointer_to_metadata`, perhaps you need to implement it: + candidate #1: `zerocopy::KnownLayout` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0277]: the trait bound `NotKnownLayout: zerocopy::KnownLayout` is not satisfied + --> tests/ui-stable/struct.rs:49:8 + | +49 | struct KL09(NotKnownLayout, NotKnownLayout); + | ^^^^ the trait `zerocopy::KnownLayout` is not implemented for `NotKnownLayout`, which is required by `KL09: zerocopy::KnownLayout` + | + = note: Consider adding `#[derive(KnownLayout)]` to `NotKnownLayout` + = help: the following other types implement trait `zerocopy::KnownLayout`: + () + *const T + *mut T + AU16 + AtomicBool + AtomicI16 + AtomicI32 + AtomicI64 + and $N others +note: required for `KL09` to implement `zerocopy::KnownLayout` + --> tests/ui-stable/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ unsatisfied trait bound introduced in this `derive` macro + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0641]: cannot cast to a pointer of an unknown kind + --> tests/ui-stable/struct.rs:47:10 + | +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ needs more type information + | + = note: the type information given here is insufficient to check whether the pointer cast is valid + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0599]: no function or associated item named `pointer_to_metadata` found for struct `NotKnownLayout` in the current scope + --> tests/ui-stable/struct.rs:47:10 + | +25 | struct NotKnownLayout; + | --------------------- function or associated item `pointer_to_metadata` not found for this struct +... +47 | #[derive(KnownLayout)] + | ^^^^^^^^^^^ function or associated item not found in `NotKnownLayout` + | + = help: items from traits can only be used if the trait is implemented and in scope + = note: the following trait defines an item `pointer_to_metadata`, perhaps you need to implement it: + candidate #1: `zerocopy::KnownLayout` + = note: this error originates in the derive macro `KnownLayout` (in Nightly builds, run with -Z macro-backtrace for more info) + error[E0277]: the trait bound `AU16: Unaligned` is not satisfied --> tests/ui-stable/struct.rs:161:28 |