pub unsafe trait Class {
type Factory;
fn dec_ref_count(&self) -> u32;
}
#[repr(transparent)]
pub struct ClassAllocation<T: Class> {
inner: std::mem::ManuallyDrop<std::pin::Pin<Box<T>>>,
}
impl<T: Class> ClassAllocation<T> {
pub fn new(inner: std::pin::Pin<Box<T>>) -> Self {
Self {
inner: std::mem::ManuallyDrop::new(inner),
}
}
pub unsafe fn from_raw(raw: *mut T) -> Self {
let inner = std::mem::ManuallyDrop::new(Box::from_raw(raw).into());
Self { inner }
}
}
impl<T: Class> std::ops::Deref for ClassAllocation<T> {
type Target = std::pin::Pin<Box<T>>;
fn deref(&self) -> &Self::Target {
&self.inner
}
}
impl<T: Class> Drop for ClassAllocation<T> {
fn drop(&mut self) {
if self.inner.dec_ref_count() == 0 {
unsafe {
std::mem::ManuallyDrop::drop(&mut self.inner);
}
}
}
}
impl<T: Class + std::fmt::Debug> std::fmt::Debug for ClassAllocation<T> {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
let inner = self.inner.as_ref().get_ref();
write!(f, "{:?}", inner)
}
}