From e8cd71df545a6bef741fec18a5ddf938c401a02a Mon Sep 17 00:00:00 2001 From: Edward Date: Wed, 29 Jun 2022 01:54:56 +0200 Subject: [PATCH] feat: ZeroableInOption and PodInOption traits (#114) * same as Zeroable and Pod but for types which are Zeroable and Pod when wrapped in Option * allows downstream users to implement Zeroable and Pod for their own Option types without running into orphan rules --- src/pod.rs | 34 +++++++++++++++++++++------------- src/zeroable.rs | 34 +++++++++++++++++++++------------- 2 files changed, 42 insertions(+), 26 deletions(-) diff --git a/src/pod.rs b/src/pod.rs index a612f0f..a7bbf9f 100644 --- a/src/pod.rs +++ b/src/pod.rs @@ -52,25 +52,33 @@ unsafe impl Pod for f32 {} unsafe impl Pod for f64 {} unsafe impl Pod for Wrapping {} -unsafe impl Pod for Option {} -unsafe impl Pod for Option {} -unsafe impl Pod for Option {} -unsafe impl Pod for Option {} -unsafe impl Pod for Option {} -unsafe impl Pod for Option {} -unsafe impl Pod for Option {} -unsafe impl Pod for Option {} -unsafe impl Pod for Option {} -unsafe impl Pod for Option {} -unsafe impl Pod for Option {} -unsafe impl Pod for Option {} +/// Trait for types which are [Pod](Pod) when wrapped in [Option](core::option::Option). +/// +/// ## Safety +/// +/// * `Option` must uphold the same invariants as [Pod](Pod). +pub unsafe trait PodInOption: ZeroableInOption + Copy + 'static {} +unsafe impl Pod for Option {} + +unsafe impl PodInOption for NonZeroI8 {} +unsafe impl PodInOption for NonZeroI16 {} +unsafe impl PodInOption for NonZeroI32 {} +unsafe impl PodInOption for NonZeroI64 {} +unsafe impl PodInOption for NonZeroI128 {} +unsafe impl PodInOption for NonZeroIsize {} +unsafe impl PodInOption for NonZeroU8 {} +unsafe impl PodInOption for NonZeroU16 {} +unsafe impl PodInOption for NonZeroU32 {} +unsafe impl PodInOption for NonZeroU64 {} +unsafe impl PodInOption for NonZeroU128 {} +unsafe impl PodInOption for NonZeroUsize {} #[cfg(feature = "unsound_ptr_pod_impl")] unsafe impl Pod for *mut T {} #[cfg(feature = "unsound_ptr_pod_impl")] unsafe impl Pod for *const T {} #[cfg(feature = "unsound_ptr_pod_impl")] -unsafe impl Pod for Option> {} +unsafe impl PodInOption for NonNull {} unsafe impl Pod for PhantomData {} unsafe impl Pod for PhantomPinned {} diff --git a/src/zeroable.rs b/src/zeroable.rs index 2af4f36..c35fb41 100644 --- a/src/zeroable.rs +++ b/src/zeroable.rs @@ -42,22 +42,30 @@ unsafe impl Zeroable for f32 {} unsafe impl Zeroable for f64 {} unsafe impl Zeroable for Wrapping {} -unsafe impl Zeroable for Option {} -unsafe impl Zeroable for Option {} -unsafe impl Zeroable for Option {} -unsafe impl Zeroable for Option {} -unsafe impl Zeroable for Option {} -unsafe impl Zeroable for Option {} -unsafe impl Zeroable for Option {} -unsafe impl Zeroable for Option {} -unsafe impl Zeroable for Option {} -unsafe impl Zeroable for Option {} -unsafe impl Zeroable for Option {} -unsafe impl Zeroable for Option {} +/// Trait for types which are [Zeroable](Zeroable) when wrapped in [Option](core::option::Option). +/// +/// ## Safety +/// +/// * `Option` must uphold the same invariants as [Zeroable](Zeroable). +pub unsafe trait ZeroableInOption: Sized {} +unsafe impl Zeroable for Option {} + +unsafe impl ZeroableInOption for NonZeroI8 {} +unsafe impl ZeroableInOption for NonZeroI16 {} +unsafe impl ZeroableInOption for NonZeroI32 {} +unsafe impl ZeroableInOption for NonZeroI64 {} +unsafe impl ZeroableInOption for NonZeroI128 {} +unsafe impl ZeroableInOption for NonZeroIsize {} +unsafe impl ZeroableInOption for NonZeroU8 {} +unsafe impl ZeroableInOption for NonZeroU16 {} +unsafe impl ZeroableInOption for NonZeroU32 {} +unsafe impl ZeroableInOption for NonZeroU64 {} +unsafe impl ZeroableInOption for NonZeroU128 {} +unsafe impl ZeroableInOption for NonZeroUsize {} unsafe impl Zeroable for *mut T {} unsafe impl Zeroable for *const T {} -unsafe impl Zeroable for Option> {} +unsafe impl ZeroableInOption for NonNull {} unsafe impl Zeroable for PhantomData {} unsafe impl Zeroable for PhantomPinned {} unsafe impl Zeroable for ManuallyDrop {}