use ::{
marker,
mem,
ptr
};
#[cfg(feature = "std")]
pub fn bytes<T: marker::Copy>(data: T) -> Vec<u8> {
let len = mem::size_of::<T>();
let mut result: Vec<u8> = vec![0; len];
unsafe {
ptr::copy_nonoverlapping(&data as *const _ as *const u8, result.as_mut_ptr(), len);
}
result
}
pub unsafe fn copy_bytes_lazy<T: marker::Copy>(data: T, to: &mut [u8]) {
ptr::copy_nonoverlapping(&data as *const _ as *const u8, to.as_mut_ptr(), mem::size_of::<T>());
}
pub fn copy_bytes<T: marker::Copy>(data: T, to: &mut [u8]) -> Result<(), ()> {
let len = mem::size_of::<T>();
if to.len() < len {
return Err(());
}
unsafe {
ptr::copy_nonoverlapping(&data as *const _ as *const u8, to.as_mut_ptr(), len);
}
Ok(())
}
pub unsafe trait ToBytesCast : marker::Copy {
#[cfg(feature = "std")]
fn to_bytes(&self) -> Vec<u8>;
fn copy_to_bytes(&self, to: &mut [u8]) -> Result<(), ()>;
unsafe fn copy_to_bytes_lazy(&self, to: &mut [u8]);
}
macro_rules! impl_to_traits
{
($($t:ty), +) => {
$(
unsafe impl ToBytesCast for $t {
#[cfg(feature = "std")]
#[inline]
fn to_bytes(&self) -> Vec<u8> {
bytes(*self)
}
#[inline]
fn copy_to_bytes(&self, to: &mut [u8]) -> Result<(), ()> {
copy_bytes(*self, to)
}
#[inline]
unsafe fn copy_to_bytes_lazy(&self, to: &mut [u8]) {
copy_bytes_lazy(*self, to)
}
}
)+
};
}
impl_to_traits!(u64, u32, u16, u8, usize, i64, i32, i16, i8, isize, f32, f64);