use std::{marker, pin};
pub use value::Value;
use crate::base::cell::{Sealed, region, values};
mod value;
pub trait Brand: Sealed {}
#[derive(Clone, Copy, Debug)]
#[repr(transparent)]
pub struct Identity<'id, const ID: u8 = 0>(marker::PhantomData<*mut &'id ()>);
impl<'id, const ID: u8> Sealed for Identity<'id, ID> {}
impl<'id, const ID: u8> Brand for Identity<'id, ID> {}
impl<'id, const ID: u8> Identity<'id, ID> {
pub const fn bind<T>(self, value: T) -> region::Value<Self, T> {
values::Value::new(value)
}
}
pub use crate::base::cell::values::Token;
impl<B: Brand> Token<B> {
pub fn borrow<'a, T>(&'a self, value: &'a region::Value<B, T>) -> &'a T {
self.read(value)
}
}
impl<'id, const ID: u8> Token<Identity<'id, ID>> {
pub const fn proof(&self) -> Identity<'id, ID> {
Identity(marker::PhantomData)
}
}
impl Token<Identity<'_>> {
pub fn scope<R>(f: impl for<'id> FnOnce(Token<Identity<'id>>) -> R) -> R {
f(Token::new())
}
pub fn scope_pinned<T: ?Sized, R>(
root: pin::Pin<&mut T>,
f: impl for<'id> FnOnce(Token<Identity<'id>>, pin::Pin<&'id mut T>) -> R,
) -> R {
f(Token::new(), root)
}
}
const _: () = {
assert!(size_of::<Identity<'static>>() == 0);
assert!(size_of::<Identity<'static, 1>>() == 0);
};