use super::*;
use crate::{
erased_types::{FormattingMode,InterfaceBound,VTableDT},
marker_type::NonOwningPhantom,
prefix_type::PrefixRef,
type_level::{
unerasability::{GetUTID},
impl_enum::{Implemented,Unimplemented},
trait_marker,
},
sabi_types::Constructor,
std_types::{UTypeId,RResult,RString,Tuple3},
};
pub unsafe trait GetRObjectVTable<IA,_Self,ErasedPtr,OrigPtr>:Sized+InterfaceType{
const ROBJECT_VTABLE:RObjectVtable_Ref<_Self,ErasedPtr,Self>;
}
unsafe impl<IA,_Self,ErasedPtr,OrigPtr,I>
GetRObjectVTable<IA,_Self,ErasedPtr,OrigPtr> for I
where
I:AreTraitsImpld<IA,_Self,ErasedPtr,OrigPtr>+InterfaceType,
{
const ROBJECT_VTABLE:RObjectVtable_Ref<_Self,ErasedPtr,Self>={
GetRObjectVTableHelper::<IA,_Self,ErasedPtr,OrigPtr,I>::TMP_VTABLE
};
}
#[allow(non_camel_case_types)]
pub type VTableTO_RO<T,OrigPtr,Unerasability,V>=VTableTO<T,OrigPtr,Unerasability,V,()>;
#[allow(non_camel_case_types)]
pub type VTableTO_DT<'borr,_Self,ErasedPtr,OrigPtr,I,Unerasability,V>=
VTableTO<
_Self,
OrigPtr,
Unerasability,
V,
VTableDT<'borr,_Self,ErasedPtr,OrigPtr,I,Unerasability>
>;
pub struct VTableTO<_Self,OrigPtr,Unerasability,V,DT>{
vtable:PrefixRef<V>,
for_dyn_trait:DT,
_for:PhantomData<Constructor<Tuple3<_Self,OrigPtr,Unerasability>>>,
}
impl<_Self,OrigPtr,Unerasability,V,DT> Copy for VTableTO<_Self,OrigPtr,Unerasability,V,DT>
where DT:Copy
{}
impl<_Self,OrigPtr,Unerasability,V,DT> Clone for VTableTO<_Self,OrigPtr,Unerasability,V,DT>
where DT:Copy
{
fn clone(&self)->Self{
*self
}
}
impl<_Self,OrigPtr,Unerasability,V> VTableTO<_Self,OrigPtr,Unerasability,V,()>{
pub const unsafe fn for_robject(vtable:PrefixRef<V>)->Self{
Self{
vtable,
for_dyn_trait:(),
_for:PhantomData
}
}
}
impl<_Self,OrigPtr,Unerasability,V,DT> VTableTO<_Self,OrigPtr,Unerasability,V,DT>{
pub const fn robject_vtable(&self)->PrefixRef<V>{
self.vtable
}
}
impl<'borr,_Self,ErasedPtr,OrigPtr,I,Unerasability,V>
VTableTO_DT<'borr,_Self,ErasedPtr,OrigPtr,I,Unerasability,V>
{
pub const fn dyntrait_vtable(
&self
)->VTableDT<'borr,_Self,ErasedPtr,OrigPtr,I,Unerasability>{
self.for_dyn_trait
}
}
impl<'borr,_Self,ErasedPtr,OrigPtr,I,Unerasability,V>
VTableTO_DT<'borr,_Self,ErasedPtr,OrigPtr,I,Unerasability,V>
{
pub const unsafe fn for_dyntrait(
vtable:PrefixRef<V>,
for_dyn_trait:VTableDT<'borr,_Self,ErasedPtr,OrigPtr,I,Unerasability>,
)->Self{
Self{
vtable,
for_dyn_trait,
_for:PhantomData
}
}
}
#[doc(hidden)]
pub trait AreTraitsImpld<IA,_Self,ErasedPtr,OrigPtr>:Sized {
const VTABLE_VAL:RObjectVtable<_Self,ErasedPtr,Self>;
}
impl<IA,_Self,ErasedPtr,OrigPtr,I> AreTraitsImpld<IA,_Self,ErasedPtr,OrigPtr> for I
where
I:InterfaceType,
I::Sync:RequiresSync<_Self,ErasedPtr,OrigPtr>,
I::Send:RequiresSend<_Self,ErasedPtr,OrigPtr>,
I::Clone:InitCloneField<_Self,ErasedPtr,OrigPtr>,
I::Debug:InitDebugField<_Self,ErasedPtr,OrigPtr>,
I::Display:InitDisplayField<_Self,ErasedPtr,OrigPtr>,
IA:GetUTID<_Self>,
{
const VTABLE_VAL:RObjectVtable<_Self,ErasedPtr,I>=
RObjectVtable{
_sabi_tys:NonOwningPhantom::NEW,
_sabi_type_id:<IA as GetUTID<_Self>>::UID,
_sabi_drop:c_functions::drop_pointer_impl::<OrigPtr,ErasedPtr>,
_sabi_clone:<I::Clone as InitCloneField<_Self,ErasedPtr,OrigPtr>>::VALUE,
_sabi_debug:<I::Debug as InitDebugField<_Self,ErasedPtr,OrigPtr>>::VALUE,
_sabi_display:<I::Display as InitDisplayField<_Self,ErasedPtr,OrigPtr>>::VALUE,
};
}
#[doc(hidden)]
struct GetRObjectVTableHelper<IA,_Self,ErasedPtr,OrigPtr,I>(IA,_Self,ErasedPtr,OrigPtr,I);
impl<IA,_Self,ErasedPtr,OrigPtr,I>
GetRObjectVTableHelper<IA,_Self,ErasedPtr,OrigPtr,I>
where
I:AreTraitsImpld<IA,_Self,ErasedPtr,OrigPtr>,
{
const TMP_VTABLE: RObjectVtable_Ref<_Self,ErasedPtr,I> = unsafe{
RObjectVtable_Ref(
WithMetadata::new(PrefixTypeTrait::METADATA, I::VTABLE_VAL)
.as_prefix()
)
};
}
#[repr(C)]
#[derive(StableAbi)]
#[sabi(kind(Prefix))]
#[sabi(missing_field(default))]
pub struct RObjectVtable<_Self,ErasedPtr,I>{
pub _sabi_tys:NonOwningPhantom<(_Self,ErasedPtr,I)>,
pub _sabi_type_id:Constructor<MaybeCmp<UTypeId>>,
pub _sabi_drop :unsafe extern "C" fn(this:&mut ErasedPtr),
pub _sabi_clone:Option<unsafe extern "C" fn(this:&ErasedPtr)->ErasedPtr>,
pub _sabi_debug:Option<
unsafe extern "C" fn(&ErasedObject,FormattingMode,&mut RString)->RResult<(),()>
>,
#[sabi(last_prefix_field)]
pub _sabi_display:Option<
unsafe extern "C" fn(&ErasedObject,FormattingMode,&mut RString)->RResult<(),()>
>,
}
#[repr(C)]
#[derive(StableAbi)]
#[sabi(
bound="I:InterfaceBound",
extra_checks="<I as InterfaceBound>::EXTRA_CHECKS",
kind(Prefix),
)]
pub(super)struct BaseVtable<_Self,ErasedPtr,I>{
pub _sabi_tys:NonOwningPhantom<(_Self,ErasedPtr,I)>,
#[sabi(last_prefix_field)]
pub _sabi_vtable: RObjectVtable_Ref<_Self,ErasedPtr,I>,
}
use self::trait_bounds::*;
pub mod trait_bounds{
use super::*;
macro_rules! declare_conditional_marker {
(
type $selector:ident;
trait $trait_name:ident[$self_:ident,$ErasedPtr:ident,$OrigPtr:ident]
where [ $($where_preds:tt)* ]
) => (
pub trait $trait_name<$self_,$ErasedPtr,$OrigPtr>{}
impl<$self_,$ErasedPtr,$OrigPtr> $trait_name<$self_,$ErasedPtr,$OrigPtr>
for Unimplemented<trait_marker::$selector>
{}
impl<$self_,$ErasedPtr,$OrigPtr> $trait_name<$self_,ErasedPtr,$OrigPtr>
for Implemented<trait_marker::$selector>
where
$($where_preds)*
{}
)
}
macro_rules! declare_field_initalizer {
(
type $selector:ident;
trait $trait_name:ident[$self_:ident,$ErasedPtr:ident,$OrigPtr:ident]
where [ $($where_preds:tt)* ]
type=$field_ty:ty,
value=$field_value:expr,
) => (
pub trait $trait_name<$self_,$ErasedPtr,$OrigPtr>{
const VALUE:Option<$field_ty>;
}
impl<$self_,$ErasedPtr,$OrigPtr> $trait_name<$self_,$ErasedPtr,$OrigPtr>
for Unimplemented<trait_marker::$selector>
{
const VALUE:Option<$field_ty>=None;
}
impl<$self_,$ErasedPtr,$OrigPtr> $trait_name<$self_,ErasedPtr,$OrigPtr>
for Implemented<trait_marker::$selector>
where
$($where_preds)*
{
const VALUE:Option<$field_ty>=Some($field_value);
}
)
}
declare_conditional_marker!{
type Send;
trait RequiresSend[_Self,ErasedPtr,OrigPtr]
where [ _Self:Send,OrigPtr:Send ]
}
declare_conditional_marker!{
type Sync;
trait RequiresSync[_Self,ErasedPtr,OrigPtr]
where [ _Self:Sync,OrigPtr:Sync ]
}
declare_field_initalizer!{
type Clone;
trait InitCloneField[_Self,ErasedPtr,OrigPtr]
where [ OrigPtr:Clone ]
type=unsafe extern "C" fn(this:&ErasedPtr)->ErasedPtr,
value=c_functions::clone_pointer_impl::<OrigPtr,ErasedPtr>,
}
declare_field_initalizer!{
type Debug;
trait InitDebugField[_Self,ErasedPtr,OrigPtr]
where [ _Self:Debug ]
type=unsafe extern "C" fn(&ErasedObject,FormattingMode,&mut RString)->RResult<(),()>,
value=c_functions::debug_impl::<_Self>,
}
declare_field_initalizer!{
type Display;
trait InitDisplayField[_Self,ErasedPtr,OrigPtr]
where [ _Self:Display ]
type=unsafe extern "C" fn(&ErasedObject,FormattingMode,&mut RString)->RResult<(),()>,
value=c_functions::display_impl::<_Self>,
}
}