Skip to content

Commit 031ea71

Browse files
bors[bot]CAD97
andauthored
Merge #64
64: Big picture docs r=CAD97 a=CAD97 r? @Ralith Does this cover what you were looking for? Co-authored-by: CAD97 <cad97@cad97.com>
2 parents ab2347f + a5cb0e9 commit 031ea71

File tree

1 file changed

+50
-0
lines changed

1 file changed

+50
-0
lines changed

crates/slice-dst/src/lib.rs

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,56 @@
7777
//! This is mostly useful when space optimization is very important.
7878
//! This is still useful when using an arena: it reduces the allocations in the arena
7979
//! in exchange for moving node payloads to the heap alongside the children array.
80+
//!
81+
//! # But how?
82+
//!
83+
//! This is possible because of the following key building blocks:
84+
//!
85+
//! - `Box`'s [memory layout][boxed-memory-layout] is defined and uses the
86+
//! [global allocator][std::alloc::Global], and is allowed to be manually allocated.
87+
//! - [Array layout][array-layout] and [slice layout][slice-layout] are defined.
88+
//! - [`#[repr(C)]`][repr-c-layout] allows us to make compound types with defined layout.
89+
//! - We can turn an opaque pointer into a slice fat pointer with
90+
//! [`ptr::slice_from_raw_parts`][slice_from_raw_parts].
91+
//! - We can cast a slice pointer to a pointer to our compound type
92+
//! in order to keep the correct fat pointer metadata.
93+
//!
94+
//! So with these guarantees, we can "just" manually allocate some space, initialize it
95+
//! for some custom `repr(C)` structure, and convert it into a `Box`. From that point,
96+
//! `Box` handles managing the memory, including deallocation or moving it into another
97+
//! smart pointer, such as `Arc`.
98+
//!
99+
//! [boxed-memory-layout]: <https://doc.rust-lang.org/stable/std/boxed/index.html#memory-layout>
100+
//! [array-layout]: <https://doc.rust-lang.org/stable/reference/type-layout.html#array-layout>
101+
//! [slice-layout]: <https://doc.rust-lang.org/stable/reference/type-layout.html#slice-layout>
102+
//! [repr-c-layout]: <https://doc.rust-lang.org/stable/reference/type-layout.html#reprc-structs>
103+
//! [std::alloc::Global]: <https://doc.rust-lang.org/stable/std/alloc/index.html#the-global_allocator-attribute>
104+
//!
105+
//! [`SliceDst`] defines the capabilities required of the pointee type. It must be able to
106+
//! turn a trailing slice length into a [`Layout`] for the whole pointee, and it must provide
107+
//! a way to turn a untyped slice pointer `*mut [()]` into a correctly typed pointer.
108+
//!
109+
//! The functions [`alloc_slice_dst`] and [`alloc_slice_dst_in`] provide a way
110+
//! to allocate space for a `SliceDst` type via the global allocator.
111+
//!
112+
//! [`AllocSliceDst`] types are owning heap pointers that can create a new slice DST.
113+
//! They take an initialization routine that is responsible for initializing the
114+
//! uninitialized allocated place, and do the ceremony required to allocate the place
115+
//! and turn it into the proper type by delgating to `SliceDst` and `alloc_slice_dst`.
116+
//! They also handle panic/unwind safety of the initialization routine and prevent
117+
//! leaking of the allocated place due to an initialization panic.
118+
//!
119+
//! [`TryAllocSliceDst`] is the potentially fallible initialization version.
120+
//!
121+
//! All of these pieces are the glue, but [`SliceWithHeader`] and [`StrWithHeader`]
122+
//! put the pieces together into a safe package. They take a header and an iterator
123+
//! (or copyable slice) and put together all of the pieces to allocate a dynamically
124+
//! sized custom type.
125+
//!
126+
//! Additionaly, though not strictly required, these types store the slice length inline.
127+
//! This gives them the ability to reconstruct pointers from fully type erased pointers
128+
#![cfg_attr(feature = "erasable", doc = "via the [`Erasable`] trait")]
129+
//! .
80130
81131
// All hail Chairity!
82132
// The one who saves our sanity -

0 commit comments

Comments
 (0)