Library to safely and fallibly initialize pinned structs using in-place constructors.
It also allows in-place initialization of big structs that would otherwise produce a stack overflow.
Pinning is Rust's way of ensuring data does not move.
Overview
To initialize a struct with an in-place constructor you will need two things:
- an in-place constructor,
- a memory location that can hold your struct (this can be the stack, an
Arc<T>,Box<T>or any other smart pointer [^1]).
To get an in-place constructor there are generally two options:
- directly creating an in-place constructor,
- a function/macro returning an in-place constructor.
Examples
Directly creating an in-place constructor
If you want to use PinInit, then you will have to annotate your struct with #[pin_project].
It is a macro that uses #[pin] as a marker for structurally pinned fields.
let foo = pin_init!;
foo now is of the type impl PinInit<Foo>. We can now use any smart pointer that we like
(or just the stack) to actually initialize a Foo:
let foo: = Box;
Using a function/macro that returns an initializer
Many types using this library supply a function/macro that returns an initializer, because the above method only works for types where you can access the fields.
let mtx: = pin_init;
To declare an init macro/function you just return an impl PinInit<T, E>:
[^1]: That is not entirely true, only smart pointers that implement InPlaceInit.