Struct abi_stable::sabi_types::StaticRef
source · #[repr(transparent)]pub struct StaticRef<T> { /* private fields */ }
Expand description
A wrapper type for vtable static references,
and other constants that have non-'static
generic parameters
but are safe to reference for the lifetime of T
.
Purpose
This type is necessary because Rust doesn’t understand that vtables live for 'static
,
even though they have non-'static
type parameters.
Example
This defines a non-extensible vtable,using a StaticRef as the pointer to the vtable.
use abi_stable::{
marker_type::ErasedObject,
prefix_type::{PrefixTypeTrait, WithMetadata},
sabi_extern_fn,
sabi_types::StaticRef,
staticref, StableAbi,
};
use std::{marker::PhantomData, ops::Deref};
fn main() {
let boxed = BoxLike::new("foo".to_string());
assert_eq!(boxed.as_str(), "foo");
}
/// An ffi-safe `Box<T>`
#[repr(C)]
#[derive(StableAbi)]
pub struct BoxLike<T> {
data: *mut T,
vtable: StaticRef<VTable<T>>,
_marker: PhantomData<T>,
}
impl<T> BoxLike<T> {
pub fn new(value: T) -> Self {
Self {
data: Box::into_raw(Box::new(value)),
vtable: VTable::<T>::VTABLE,
_marker: PhantomData,
}
}
}
impl<T> Drop for BoxLike<T> {
fn drop(&mut self) {
unsafe {
(self.vtable.drop_)(self.data);
}
}
}
impl<T> Deref for BoxLike<T> {
type Target = T;
fn deref(&self) -> &T {
unsafe { &*self.data }
}
}
#[repr(C)]
#[derive(StableAbi)]
pub struct VTable<T> {
drop_: unsafe extern "C" fn(*mut T),
}
impl<T> VTable<T> {
// The `staticref` macro declares a `StaticRef<VTable<T>>` constant.
staticref!(const VTABLE: Self = Self{
drop_: drop_box::<T>,
});
}
#[sabi_extern_fn]
unsafe fn drop_box<T>(object: *mut T) {
drop(Box::from_raw(object));
}
Implementations
sourceimpl<T, P> StaticRef<WithMetadata_<T, P>>
impl<T, P> StaticRef<WithMetadata_<T, P>>
sourcepub const fn as_prefix(self) -> PrefixRef<P>
pub const fn as_prefix(self) -> PrefixRef<P>
Constructs a PrefixRef<P>
from self.
This is most useful when you have a generic type that isn’t 'static
for type system reasons, but lives for the entire program.
Example
use abi_stable::{
for_examples::{PhantModule, PhantModule_Ref},
prefix_type::{PrefixRef, PrefixTypeTrait, WithMetadata},
std_types::{RNone, RStr},
staticref,
};
struct Foo<T>(T);
impl<T: Copy> Foo<T> {
// The `staticref` invocation here declares a
// `StaticRef<WithMetadata<PhantModule<T>>>` constant.
staticref!(const WITH_META: WithMetadata<PhantModule<T>> = WithMetadata::new(
PrefixTypeTrait::METADATA,
PhantModule {
first: RNone,
second: RStr::from_str("hello"),
third: 100,
phantom: std::marker::PhantomData,
},
));
}
const MOD: PhantModule_Ref<()> = PhantModule_Ref(Foo::WITH_META.as_prefix());
assert_eq!(MOD.first(), RNone);
assert_eq!(MOD.second().as_str(), "hello");
sourceimpl<T> StaticRef<T>
impl<T> StaticRef<T>
sourcepub const unsafe fn from_raw(ref_: *const T) -> Self
pub const unsafe fn from_raw(ref_: *const T) -> Self
Constructs this StaticRef from a raw pointer.
Safety
You must ensure that the raw pointer is valid for the entire program’s lifetime.
Example
use abi_stable::sabi_types::StaticRef;
struct GetPtr<T>(T);
impl<T> GetPtr<T> {
const PTR: *const Option<T> = &None;
const STATIC: StaticRef<Option<T>> = unsafe { StaticRef::from_raw(Self::PTR) };
}
{}
sourcepub const fn new(ref_: &'static T) -> Self
pub const fn new(ref_: &'static T) -> Self
Constructs this StaticRef from a static reference
This implicitly requires that T:'static
.
Example
use abi_stable::sabi_types::StaticRef;
struct GetPtr<T>(T);
impl<T> GetPtr<T>
where
T: 'static,
{
const REF: &'static Option<T> = &None;
const STATIC: StaticRef<Option<T>> = StaticRef::new(Self::REF);
}
sourcepub fn leak_value(val: T) -> Self
pub fn leak_value(val: T) -> Self
Creates a StaticRef by heap allocating and leaking val
.
sourcepub fn get<'a>(self) -> &'a T
pub fn get<'a>(self) -> &'a T
Gets access to the reference.
This returns &'a T
instead of &'static T
to support vtables of non-'static
types.
Example
use abi_stable::sabi_types::StaticRef;
struct GetPtr<T>(T);
impl<T> GetPtr<T> {
const PTR: *const Option<T> = &None;
const STATIC: StaticRef<Option<T>> = unsafe { StaticRef::from_raw(Self::PTR) };
}
let reference: &'static Option<String> = GetPtr::<String>::STATIC.get();
sourcepub const fn as_ptr(self) -> *const T
pub const fn as_ptr(self) -> *const T
Gets access to the referenced value,as a raw pointer.
Example
use abi_stable::sabi_types::StaticRef;
use std::convert::Infallible;
struct GetPtr<T>(T);
impl<T> GetPtr<T> {
const PTR: *const Option<T> = &None;
const STATIC: StaticRef<Option<T>> = unsafe { StaticRef::from_raw(Self::PTR) };
}
let reference: *const Option<Infallible> = GetPtr::<Infallible>::STATIC.as_ptr();
sourcepub const unsafe fn transmute<U>(self) -> StaticRef<U>
pub const unsafe fn transmute<U>(self) -> StaticRef<U>
Transmutes this StaticRef<T>
to a StaticRef<U>
.
Safety
StaticRef has the same rules that references have regarding transmuting from one type to another:
Example
use abi_stable::sabi_types::StaticRef;
struct GetPtr<T>(T);
impl<T> GetPtr<T> {
const PTR: *const Option<T> = &None;
const STATIC: StaticRef<Option<T>> = unsafe { StaticRef::from_raw(Self::PTR) };
}
let reference: StaticRef<Option<[(); 0xFFF_FFFF]>> =
unsafe { GetPtr::<()>::STATIC.transmute::<Option<[(); 0xFFF_FFFF]>>() };
Trait Implementations
sourceimpl<T, U> CanTransmuteElement<U> for StaticRef<T>
impl<T, U> CanTransmuteElement<U> for StaticRef<T>
type TransmutedPtr = StaticRef<U>
type TransmutedPtr = StaticRef<U>
sourceunsafe fn transmute_element_(self) -> StaticRef<U>
unsafe fn transmute_element_(self) -> StaticRef<U>
sourceimpl<T> GetPointerKind for StaticRef<T>
impl<T> GetPointerKind for StaticRef<T>
type Kind = PK_Reference
type Kind = PK_Reference
sourceconst KIND: PointerKind = <Self::Kind as PointerKindVariant>::VALUE
const KIND: PointerKind = <Self::Kind as PointerKindVariant>::VALUE
sourceimpl<T> GetStaticEquivalent_ for StaticRef<T>where
T: __StableAbi,
impl<T> GetStaticEquivalent_ for StaticRef<T>where
T: __StableAbi,
type StaticEquivalent = _static_StaticRef<<T as GetStaticEquivalent_>::StaticEquivalent>
sourceimpl<T> Ord for StaticRef<T>where
T: Ord,
impl<T> Ord for StaticRef<T>where
T: Ord,
1.21.0 · sourcefn max(self, other: Self) -> Selfwhere
Self: Sized,
fn max(self, other: Self) -> Selfwhere
Self: Sized,
1.21.0 · sourcefn min(self, other: Self) -> Selfwhere
Self: Sized,
fn min(self, other: Self) -> Selfwhere
Self: Sized,
1.50.0 · sourcefn clamp(self, min: Self, max: Self) -> Selfwhere
Self: Sized + PartialOrd<Self>,
fn clamp(self, min: Self, max: Self) -> Selfwhere
Self: Sized + PartialOrd<Self>,
sourceimpl<T> PartialEq<StaticRef<T>> for StaticRef<T>where
T: PartialEq,
impl<T> PartialEq<StaticRef<T>> for StaticRef<T>where
T: PartialEq,
sourceimpl<T> PartialOrd<StaticRef<T>> for StaticRef<T>where
T: PartialOrd,
impl<T> PartialOrd<StaticRef<T>> for StaticRef<T>where
T: PartialOrd,
sourcefn partial_cmp(&self, other: &Self) -> Option<Ordering>
fn partial_cmp(&self, other: &Self) -> Option<Ordering>
1.0.0 · sourcefn le(&self, other: &Rhs) -> bool
fn le(&self, other: &Rhs) -> bool
self
and other
) and is used by the <=
operator. Read moresourceimpl<T> StableAbi for StaticRef<T>where
T: __StableAbi,
impl<T> StableAbi for StaticRef<T>where
T: __StableAbi,
type IsNonZeroType = <NonNull<T> as StableAbi>::IsNonZeroType
type IsNonZeroType = <NonNull<T> as StableAbi>::IsNonZeroType
sourceconst LAYOUT: &'static TypeLayout = _
const LAYOUT: &'static TypeLayout = _
sourceconst ABI_CONSTS: AbiConsts = _
const ABI_CONSTS: AbiConsts = _
const
-equivalents of the associated types.impl<T> Copy for StaticRef<T>
impl<T> Eq for StaticRef<T>where
T: Eq,
impl<'a, T: 'a> Send for StaticRef<T>where
&'a T: Send,
impl<'a, T: 'a> Sync for StaticRef<T>where
&'a T: Sync,
Auto Trait Implementations
impl<T> RefUnwindSafe for StaticRef<T>where
T: RefUnwindSafe,
impl<T> Unpin for StaticRef<T>
impl<T> UnwindSafe for StaticRef<T>where
T: RefUnwindSafe,
Blanket Implementations
sourceimpl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
const: unstable · sourcefn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
sourceimpl<'a, T> BorrowOwned<'a> for Twhere
T: 'a + Clone,
impl<'a, T> BorrowOwned<'a> for Twhere
T: 'a + Clone,
type ROwned = T
type ROwned = T
RCow::Owned
fn r_borrow(
this: &'a <T as BorrowOwned<'a>>::ROwned
) -> <T as BorrowOwned<'a>>::RBorrowed
fn r_to_owned(
this: <T as BorrowOwned<'a>>::RBorrowed
) -> <T as BorrowOwned<'a>>::ROwned
fn deref_borrowed(this: &<T as BorrowOwned<'a>>::RBorrowed) -> &T
fn deref_owned(this: &<T as BorrowOwned<'a>>::ROwned) -> &T
fn from_cow_borrow(this: &'a T) -> <T as BorrowOwned<'a>>::RBorrowed
fn from_cow_owned(this: <T as ToOwned>::Owned) -> <T as BorrowOwned<'a>>::ROwned
fn into_cow_borrow(this: <T as BorrowOwned<'a>>::RBorrowed) -> &'a T
fn into_cow_owned(this: <T as BorrowOwned<'a>>::ROwned) -> <T as ToOwned>::Owned
sourceimpl<T> GetWithMetadata for T
impl<T> GetWithMetadata for T
type ForSelf = WithMetadata_<T, T>
type ForSelf = WithMetadata_<T, T>
WithMetadata_<Self, Self>
sourceimpl<S> ROExtAcc for S
impl<S> ROExtAcc for S
sourcefn f_get<F>(&self, offset: FieldOffset<S, F, Aligned>) -> &F
fn f_get<F>(&self, offset: FieldOffset<S, F, Aligned>) -> &F
offset
. Read moresourcefn f_get_mut<F>(&mut self, offset: FieldOffset<S, F, Aligned>) -> &mut F
fn f_get_mut<F>(&mut self, offset: FieldOffset<S, F, Aligned>) -> &mut F
offset
. Read moresourcefn f_get_ptr<F, A>(&self, offset: FieldOffset<S, F, A>) -> *const F
fn f_get_ptr<F, A>(&self, offset: FieldOffset<S, F, A>) -> *const F
offset
. Read moresourcefn f_get_mut_ptr<F, A>(&mut self, offset: FieldOffset<S, F, A>) -> *mut F
fn f_get_mut_ptr<F, A>(&mut self, offset: FieldOffset<S, F, A>) -> *mut F
offset
. Read moresourceimpl<S> ROExtOps<Aligned> for S
impl<S> ROExtOps<Aligned> for S
sourcefn f_replace<F>(&mut self, offset: FieldOffset<S, F, Aligned>, value: F) -> F
fn f_replace<F>(&mut self, offset: FieldOffset<S, F, Aligned>, value: F) -> F
offset
) with value
,
returning the previous value of the field. Read moresourcefn f_swap<F>(&mut self, offset: FieldOffset<S, F, Aligned>, right: &mut S)
fn f_swap<F>(&mut self, offset: FieldOffset<S, F, Aligned>, right: &mut S)
sourcefn f_get_copy<F>(&self, offset: FieldOffset<S, F, Aligned>) -> Fwhere
F: Copy,
fn f_get_copy<F>(&self, offset: FieldOffset<S, F, Aligned>) -> Fwhere
F: Copy,
sourceimpl<S> ROExtOps<Unaligned> for S
impl<S> ROExtOps<Unaligned> for S
sourcefn f_replace<F>(&mut self, offset: FieldOffset<S, F, Unaligned>, value: F) -> F
fn f_replace<F>(&mut self, offset: FieldOffset<S, F, Unaligned>, value: F) -> F
offset
) with value
,
returning the previous value of the field. Read moresourcefn f_swap<F>(&mut self, offset: FieldOffset<S, F, Unaligned>, right: &mut S)
fn f_swap<F>(&mut self, offset: FieldOffset<S, F, Unaligned>, right: &mut S)
sourcefn f_get_copy<F>(&self, offset: FieldOffset<S, F, Unaligned>) -> Fwhere
F: Copy,
fn f_get_copy<F>(&self, offset: FieldOffset<S, F, Unaligned>) -> Fwhere
F: Copy,
sourceimpl<T> SelfOps for Twhere
T: ?Sized,
impl<T> SelfOps for Twhere
T: ?Sized,
sourcefn piped<F, U>(self, f: F) -> Uwhere
F: FnOnce(Self) -> U,
Self: Sized,
fn piped<F, U>(self, f: F) -> Uwhere
F: FnOnce(Self) -> U,
Self: Sized,
sourcefn piped_ref<'a, F, U>(&'a self, f: F) -> Uwhere
F: FnOnce(&'a Self) -> U,
fn piped_ref<'a, F, U>(&'a self, f: F) -> Uwhere
F: FnOnce(&'a Self) -> U,
piped
except that the function takes &Self
Useful for functions that take &Self
instead of Self
. Read moresourcefn piped_mut<'a, F, U>(&'a mut self, f: F) -> Uwhere
F: FnOnce(&'a mut Self) -> U,
fn piped_mut<'a, F, U>(&'a mut self, f: F) -> Uwhere
F: FnOnce(&'a mut Self) -> U,
piped
, except that the function takes &mut Self
.
Useful for functions that take &mut Self
instead of Self
. Read moresourcefn mutated<F>(self, f: F) -> Selfwhere
F: FnOnce(&mut Self),
Self: Sized,
fn mutated<F>(self, f: F) -> Selfwhere
F: FnOnce(&mut Self),
Self: Sized,
sourcefn observe<F>(self, f: F) -> Selfwhere
F: FnOnce(&Self),
Self: Sized,
fn observe<F>(self, f: F) -> Selfwhere
F: FnOnce(&Self),
Self: Sized,
sourcefn as_ref_<T>(&self) -> &Twhere
Self: AsRef<T>,
T: ?Sized,
fn as_ref_<T>(&self) -> &Twhere
Self: AsRef<T>,
T: ?Sized,
AsRef
,
using the turbofish .as_ref_::<_>()
syntax. Read moresourceimpl<This> TransmuteElement for Thiswhere
This: ?Sized,
impl<This> TransmuteElement for Thiswhere
This: ?Sized,
sourceunsafe fn transmute_element<T>(
self
) -> <Self as CanTransmuteElement<T>>::TransmutedPtrwhere
Self: CanTransmuteElement<T>,
unsafe fn transmute_element<T>(
self
) -> <Self as CanTransmuteElement<T>>::TransmutedPtrwhere
Self: CanTransmuteElement<T>,
sourceimpl<T> TypeIdentity for Twhere
T: ?Sized,
impl<T> TypeIdentity for Twhere
T: ?Sized,
type Type = T
type Type = T
Self
.