@@ -18,7 +18,19 @@ use pin_init::{PinInit, Zeroable};
1818///
1919/// This trait is meant to be used in cases when Rust objects are stored in C objects and
2020/// eventually "freed" back to Rust.
21- pub trait ForeignOwnable : Sized {
21+ ///
22+ /// # Safety
23+ ///
24+ /// Implementers must ensure that [`into_foreign`] returns a pointer which meets the alignment
25+ /// requirements of [`PointedTo`].
26+ ///
27+ /// [`into_foreign`]: Self::into_foreign
28+ /// [`PointedTo`]: Self::PointedTo
29+ pub unsafe trait ForeignOwnable : Sized {
30+ /// Type used when the value is foreign-owned. In practical terms only defines the alignment of
31+ /// the pointer.
32+ type PointedTo ;
33+
2234 /// Type used to immutably borrow a value that is currently foreign-owned.
2335 type Borrowed < ' a > ;
2436
@@ -27,16 +39,18 @@ pub trait ForeignOwnable: Sized {
2739
2840 /// Converts a Rust-owned object to a foreign-owned one.
2941 ///
30- /// The foreign representation is a pointer to void. There are no guarantees for this pointer.
31- /// For example, it might be invalid, dangling or pointing to uninitialized memory. Using it in
32- /// any way except for [`from_foreign`], [`try_from_foreign`], [`borrow`], or [`borrow_mut`] can
33- /// result in undefined behavior.
42+ /// # Guarantees
43+ ///
44+ /// The return value is guaranteed to be well-aligned, but there are no other guarantees for
45+ /// this pointer. For example, it might be null, dangling, or point to uninitialized memory.
46+ /// Using it in any way except for [`ForeignOwnable::from_foreign`], [`ForeignOwnable::borrow`],
47+ /// [`ForeignOwnable::try_from_foreign`] can result in undefined behavior.
3448 ///
3549 /// [`from_foreign`]: Self::from_foreign
3650 /// [`try_from_foreign`]: Self::try_from_foreign
3751 /// [`borrow`]: Self::borrow
3852 /// [`borrow_mut`]: Self::borrow_mut
39- fn into_foreign ( self ) -> * mut crate :: ffi :: c_void ;
53+ fn into_foreign ( self ) -> * mut Self :: PointedTo ;
4054
4155 /// Converts a foreign-owned object back to a Rust-owned one.
4256 ///
@@ -46,7 +60,7 @@ pub trait ForeignOwnable: Sized {
4660 /// must not be passed to `from_foreign` more than once.
4761 ///
4862 /// [`into_foreign`]: Self::into_foreign
49- unsafe fn from_foreign ( ptr : * mut crate :: ffi :: c_void ) -> Self ;
63+ unsafe fn from_foreign ( ptr : * mut Self :: PointedTo ) -> Self ;
5064
5165 /// Tries to convert a foreign-owned object back to a Rust-owned one.
5266 ///
@@ -58,7 +72,7 @@ pub trait ForeignOwnable: Sized {
5872 /// `ptr` must either be null or satisfy the safety requirements for [`from_foreign`].
5973 ///
6074 /// [`from_foreign`]: Self::from_foreign
61- unsafe fn try_from_foreign ( ptr : * mut crate :: ffi :: c_void ) -> Option < Self > {
75+ unsafe fn try_from_foreign ( ptr : * mut Self :: PointedTo ) -> Option < Self > {
6276 if ptr. is_null ( ) {
6377 None
6478 } else {
@@ -81,7 +95,7 @@ pub trait ForeignOwnable: Sized {
8195 ///
8296 /// [`into_foreign`]: Self::into_foreign
8397 /// [`from_foreign`]: Self::from_foreign
84- unsafe fn borrow < ' a > ( ptr : * mut crate :: ffi :: c_void ) -> Self :: Borrowed < ' a > ;
98+ unsafe fn borrow < ' a > ( ptr : * mut Self :: PointedTo ) -> Self :: Borrowed < ' a > ;
8599
86100 /// Borrows a foreign-owned object mutably.
87101 ///
@@ -109,21 +123,23 @@ pub trait ForeignOwnable: Sized {
109123 /// [`from_foreign`]: Self::from_foreign
110124 /// [`borrow`]: Self::borrow
111125 /// [`Arc`]: crate::sync::Arc
112- unsafe fn borrow_mut < ' a > ( ptr : * mut crate :: ffi :: c_void ) -> Self :: BorrowedMut < ' a > ;
126+ unsafe fn borrow_mut < ' a > ( ptr : * mut Self :: PointedTo ) -> Self :: BorrowedMut < ' a > ;
113127}
114128
115- impl ForeignOwnable for ( ) {
129+ // SAFETY: The `into_foreign` function returns a pointer that is dangling, but well-aligned.
130+ unsafe impl ForeignOwnable for ( ) {
131+ type PointedTo = ( ) ;
116132 type Borrowed < ' a > = ( ) ;
117133 type BorrowedMut < ' a > = ( ) ;
118134
119- fn into_foreign ( self ) -> * mut crate :: ffi :: c_void {
135+ fn into_foreign ( self ) -> * mut Self :: PointedTo {
120136 core:: ptr:: NonNull :: dangling ( ) . as_ptr ( )
121137 }
122138
123- unsafe fn from_foreign ( _: * mut crate :: ffi :: c_void ) -> Self { }
139+ unsafe fn from_foreign ( _: * mut Self :: PointedTo ) -> Self { }
124140
125- unsafe fn borrow < ' a > ( _: * mut crate :: ffi :: c_void ) -> Self :: Borrowed < ' a > { }
126- unsafe fn borrow_mut < ' a > ( _: * mut crate :: ffi :: c_void ) -> Self :: BorrowedMut < ' a > { }
141+ unsafe fn borrow < ' a > ( _: * mut Self :: PointedTo ) -> Self :: Borrowed < ' a > { }
142+ unsafe fn borrow_mut < ' a > ( _: * mut Self :: PointedTo ) -> Self :: BorrowedMut < ' a > { }
127143}
128144
129145/// Runs a cleanup function/closure when dropped.
0 commit comments