Conditionally compile in Arc (#140)

Apparently the latest release of `bytemuck` doesn't compile on some of
the targets that it used to because it uses `Arc`. `Arc` is not a type
that exists on every target, because not every targets supports atomics.
This commit is contained in:
Christopher Serr 2022-11-05 14:00:40 +01:00 committed by GitHub
parent 518baf9c0b
commit 02021fba24
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 19 additions and 7 deletions

View File

@ -10,11 +10,12 @@
//! ["extern_crate_alloc"]}` //! ["extern_crate_alloc"]}`
use super::*; use super::*;
#[cfg(target_has_atomic = "ptr")]
use alloc::sync::Arc;
use alloc::{ use alloc::{
alloc::{alloc_zeroed, Layout}, alloc::{alloc_zeroed, Layout},
boxed::Box, boxed::Box,
rc::Rc, rc::Rc,
sync::Arc,
vec, vec,
vec::Vec, vec::Vec,
}; };
@ -355,6 +356,7 @@ pub fn try_cast_rc<A: NoUninit + AnyBitPattern, B: NoUninit + AnyBitPattern>(
/// As [`try_cast_arc`](try_cast_arc), but unwraps for you. /// As [`try_cast_arc`](try_cast_arc), but unwraps for you.
#[inline] #[inline]
#[cfg(target_has_atomic = "ptr")]
pub fn cast_arc<A: NoUninit + AnyBitPattern, B: NoUninit + AnyBitPattern>( pub fn cast_arc<A: NoUninit + AnyBitPattern, B: NoUninit + AnyBitPattern>(
input: Arc<A>, input: Arc<A>,
) -> Arc<B> { ) -> Arc<B> {
@ -375,6 +377,7 @@ pub fn cast_arc<A: NoUninit + AnyBitPattern, B: NoUninit + AnyBitPattern>(
/// alignment. /// alignment.
/// * The start and end size of the `Arc` must have the exact same size. /// * The start and end size of the `Arc` must have the exact same size.
#[inline] #[inline]
#[cfg(target_has_atomic = "ptr")]
pub fn try_cast_arc< pub fn try_cast_arc<
A: NoUninit + AnyBitPattern, A: NoUninit + AnyBitPattern,
B: NoUninit + AnyBitPattern, B: NoUninit + AnyBitPattern,
@ -456,6 +459,7 @@ pub fn try_cast_slice_rc<
/// As [`try_cast_slice_arc`](try_cast_slice_arc), but unwraps for you. /// As [`try_cast_slice_arc`](try_cast_slice_arc), but unwraps for you.
#[inline] #[inline]
#[cfg(target_has_atomic = "ptr")]
pub fn cast_slice_arc< pub fn cast_slice_arc<
A: NoUninit + AnyBitPattern, A: NoUninit + AnyBitPattern,
B: NoUninit + AnyBitPattern, B: NoUninit + AnyBitPattern,
@ -480,6 +484,7 @@ pub fn cast_slice_arc<
/// * The start and end content size in bytes of the `Arc<[T]>` must be the /// * The start and end content size in bytes of the `Arc<[T]>` must be the
/// exact same. /// exact same.
#[inline] #[inline]
#[cfg(target_has_atomic = "ptr")]
pub fn try_cast_slice_arc< pub fn try_cast_slice_arc<
A: NoUninit + AnyBitPattern, A: NoUninit + AnyBitPattern,
B: NoUninit + AnyBitPattern, B: NoUninit + AnyBitPattern,
@ -590,6 +595,7 @@ pub trait TransparentWrapperAlloc<Inner: ?Sized>:
/// Convert an [`Arc`](alloc::sync::Arc) to the inner type into an `Arc` to /// Convert an [`Arc`](alloc::sync::Arc) to the inner type into an `Arc` to
/// the wrapper type. /// the wrapper type.
#[inline] #[inline]
#[cfg(target_has_atomic = "ptr")]
fn wrap_arc(s: Arc<Inner>) -> Arc<Self> { fn wrap_arc(s: Arc<Inner>) -> Arc<Self> {
assert!(size_of::<*mut Inner>() == size_of::<*mut Self>()); assert!(size_of::<*mut Inner>() == size_of::<*mut Self>());
@ -679,6 +685,7 @@ pub trait TransparentWrapperAlloc<Inner: ?Sized>:
/// Convert an [`Arc`](alloc::sync::Arc) to the wrapper type into an `Arc` to /// Convert an [`Arc`](alloc::sync::Arc) to the wrapper type into an `Arc` to
/// the inner type. /// the inner type.
#[inline] #[inline]
#[cfg(target_has_atomic = "ptr")]
fn peel_arc(s: Arc<Self>) -> Arc<Inner> { fn peel_arc(s: Arc<Self>) -> Arc<Inner> {
assert!(size_of::<*mut Inner>() == size_of::<*mut Self>()); assert!(size_of::<*mut Inner>() == size_of::<*mut Self>());

View File

@ -77,7 +77,7 @@ fn test_transparent_wrapper() {
#[cfg(feature = "extern_crate_alloc")] #[cfg(feature = "extern_crate_alloc")]
{ {
use bytemuck::allocation::TransparentWrapperAlloc; use bytemuck::allocation::TransparentWrapperAlloc;
use std::{rc::Rc, sync::Arc}; use std::rc::Rc;
let a: Vec<Foreign> = vec![Foreign::default(); 2]; let a: Vec<Foreign> = vec![Foreign::default(); 2];
@ -101,11 +101,16 @@ fn test_transparent_wrapper() {
let i: Rc<Foreign> = Wrapper::peel_rc(h); let i: Rc<Foreign> = Wrapper::peel_rc(h);
assert_eq!(&*i, &0); assert_eq!(&*i, &0);
let j: Arc<Foreign> = Arc::new(Foreign::default()); #[cfg(target_has_atomic = "ptr")]
{
use std::sync::Arc;
let k: Arc<Wrapper> = Wrapper::wrap_arc(j); let j: Arc<Foreign> = Arc::new(Foreign::default());
assert_eq!(&*k, &0);
let l: Arc<Foreign> = Wrapper::peel_arc(k); let k: Arc<Wrapper> = Wrapper::wrap_arc(j);
assert_eq!(&*l, &0); assert_eq!(&*k, &0);
let l: Arc<Foreign> = Wrapper::peel_arc(k);
assert_eq!(&*l, &0);
}
} }
} }