facet_core/impls_core/
smartptr.rs

1use core::alloc::Layout;
2
3use crate::{
4    ConstTypeId, Def, Facet, KnownSmartPointer, PtrConst, SmartPointerDef, SmartPointerFlags,
5    SmartPointerVTable, value_vtable,
6};
7
8unsafe impl<T: Facet> Facet for core::ptr::NonNull<T> {
9    const SHAPE: &'static crate::Shape = &const {
10        crate::Shape::builder()
11            .id(ConstTypeId::of::<Self>())
12            .layout(Layout::new::<Self>())
13            .def(Def::SmartPointer(
14                SmartPointerDef::builder()
15                    .pointee(T::SHAPE)
16                    .flags(SmartPointerFlags::EMPTY)
17                    .known(KnownSmartPointer::NonNull)
18                    .vtable(
19                        &const {
20                            SmartPointerVTable::builder()
21                                .borrow_fn(|opaque| {
22                                    let ptr = unsafe { opaque.get::<Self>().as_ptr() };
23                                    PtrConst::new(ptr)
24                                })
25                                .new_into_fn(|this, ptr| {
26                                    let ptr = unsafe { ptr.read::<*mut T>() };
27                                    let non_null =
28                                        unsafe { core::ptr::NonNull::new_unchecked(ptr) };
29                                    unsafe { this.put(non_null) }
30                                })
31                                .build()
32                        },
33                    )
34                    .build(),
35            ))
36            .vtable(value_vtable!(core::ptr::NonNull<T>, |f, _opts| write!(
37                f,
38                "NonNull"
39            )))
40            .build()
41    };
42}