use crate::map::ZeroMapKV;
use crate::ule::*;
use crate::{VarZeroVec, ZeroMap, ZeroVec};
use core::{mem, ptr};
use yoke::*;
unsafe impl<'a, T: 'static + AsULE + ?Sized> Yokeable<'a> for ZeroVec<'static, T> {
type Output = ZeroVec<'a, T>;
fn transform(&'a self) -> &'a ZeroVec<'a, T> {
self
}
fn transform_owned(self) -> ZeroVec<'a, T> {
self
}
unsafe fn make(from: ZeroVec<'a, T>) -> Self {
debug_assert!(mem::size_of::<ZeroVec<'a, T>>() == mem::size_of::<Self>());
let ptr: *const Self = (&from as *const Self::Output).cast();
mem::forget(from);
ptr::read(ptr)
}
fn transform_mut<F>(&'a mut self, f: F)
where
F: 'static + for<'b> FnOnce(&'b mut Self::Output),
{
unsafe { f(mem::transmute::<&mut Self, &mut Self::Output>(self)) }
}
}
unsafe impl<'a, T: 'static + VarULE + ?Sized> Yokeable<'a> for VarZeroVec<'static, T> {
type Output = VarZeroVec<'a, T>;
fn transform(&'a self) -> &'a VarZeroVec<'a, T> {
self
}
fn transform_owned(self) -> VarZeroVec<'a, T> {
self
}
unsafe fn make(from: VarZeroVec<'a, T>) -> Self {
debug_assert!(mem::size_of::<VarZeroVec<'a, T>>() == mem::size_of::<Self>());
let ptr: *const Self = (&from as *const Self::Output).cast();
mem::forget(from);
ptr::read(ptr)
}
fn transform_mut<F>(&'a mut self, f: F)
where
F: 'static + for<'b> FnOnce(&'b mut Self::Output),
{
unsafe { f(mem::transmute::<&mut Self, &mut Self::Output>(self)) }
}
}
#[allow(clippy::transmute_ptr_to_ptr)]
unsafe impl<'a, K, V> Yokeable<'a> for ZeroMap<'static, K, V>
where
K: 'static + for<'b> ZeroMapKV<'b> + ?Sized,
V: 'static + for<'b> ZeroMapKV<'b> + ?Sized,
{
type Output = ZeroMap<'a, K, V>;
fn transform(&'a self) -> &'a ZeroMap<'a, K, V> {
unsafe {
mem::transmute::<&Self, &Self::Output>(self)
}
}
fn transform_owned(self) -> ZeroMap<'a, K, V> {
debug_assert!(mem::size_of::<Self::Output>() == mem::size_of::<Self>());
unsafe {
let ptr: *const Self::Output = (&self as *const Self).cast();
mem::forget(self);
ptr::read(ptr)
}
}
unsafe fn make(from: ZeroMap<'a, K, V>) -> Self {
debug_assert!(mem::size_of::<ZeroMap<'a, K, V>>() == mem::size_of::<Self>());
let ptr: *const Self = (&from as *const Self::Output).cast();
mem::forget(from);
ptr::read(ptr)
}
fn transform_mut<F>(&'a mut self, f: F)
where
F: 'static + for<'b> FnOnce(&'b mut Self::Output),
{
unsafe { f(mem::transmute::<&mut Self, &mut Self::Output>(self)) }
}
}
impl<'a, T: 'static + AsULE + ?Sized> ZeroCopyFrom<ZeroVec<'a, T>> for ZeroVec<'static, T> {
fn zero_copy_from<'b>(cart: &'b ZeroVec<'a, T>) -> ZeroVec<'b, T> {
ZeroVec::Borrowed(cart.as_slice())
}
}
impl<'a, T: 'static + VarULE + ?Sized> ZeroCopyFrom<VarZeroVec<'a, T>> for VarZeroVec<'static, T> {
fn zero_copy_from<'b>(cart: &'b VarZeroVec<'a, T>) -> VarZeroVec<'b, T> {
cart.as_borrowed().into()
}
}
impl<'a, K, V> ZeroCopyFrom<ZeroMap<'a, K, V>> for ZeroMap<'static, K, V>
where
K: 'static + for<'b> ZeroMapKV<'b> + ?Sized,
V: 'static + for<'b> ZeroMapKV<'b> + ?Sized,
<K as ZeroMapKV<'static>>::Container: for<'b> ZeroCopyFrom<<K as ZeroMapKV<'b>>::Container>,
<V as ZeroMapKV<'static>>::Container: for<'b> ZeroCopyFrom<<V as ZeroMapKV<'b>>::Container>,
<K as ZeroMapKV<'static>>::Container:
for<'b> Yokeable<'b, Output = <K as ZeroMapKV<'b>>::Container>,
<V as ZeroMapKV<'static>>::Container:
for<'b> Yokeable<'b, Output = <V as ZeroMapKV<'b>>::Container>,
{
fn zero_copy_from<'b>(cart: &'b ZeroMap<'a, K, V>) -> ZeroMap<'b, K, V> {
ZeroMap {
keys: <<K as ZeroMapKV<'static>>::Container as ZeroCopyFrom<_>>::zero_copy_from(
&cart.keys,
),
values: <<V as ZeroMapKV<'static>>::Container as ZeroCopyFrom<_>>::zero_copy_from(
&cart.values,
),
}
}
}