1 // SPDX-License-Identifier: Apache-2.0 OR MIT
3 //! API to safely and fallibly initialize pinned `struct`s using in-place constructors.
5 //! It also allows in-place initialization of big `struct`s that would otherwise produce a stack
8 //! Most `struct`s from the [`sync`] module need to be pinned, because they contain self-referential
9 //! `struct`s from C. [Pinning][pinning] is Rust's way of ensuring data does not move.
13 //! To initialize a `struct` with an in-place constructor you will need two things:
14 //! - an in-place constructor,
15 //! - a memory location that can hold your `struct` (this can be the [stack], an [`Arc<T>`],
16 //! [`UniqueArc<T>`], [`Box<T>`] or any other smart pointer that implements [`InPlaceInit`]).
18 //! To get an in-place constructor there are generally three options:
19 //! - directly creating an in-place constructor using the [`pin_init!`] macro,
20 //! - a custom function/macro returning an in-place constructor provided by someone else,
21 //! - using the unsafe function [`pin_init_from_closure()`] to manually create an initializer.
23 //! Aside from pinned initialization, this API also supports in-place construction without pinning,
24 //! the macros/types/functions are generally named like the pinned variants without the `pin`
29 //! ## Using the [`pin_init!`] macro
31 //! If you want to use [`PinInit`], then you will have to annotate your `struct` with
32 //! `#[`[`pin_data`]`]`. It is a macro that uses `#[pin]` as a marker for
33 //! [structurally pinned fields]. After doing this, you can then create an in-place constructor via
34 //! [`pin_init!`]. The syntax is almost the same as normal `struct` initializers. The difference is
35 //! that you need to write `<-` instead of `:` for fields that you want to initialize in-place.
38 //! # #![allow(clippy::disallowed_names)]
39 //! use kernel::sync::{new_mutex, Mutex};
40 //! # use core::pin::Pin;
48 //! let foo = pin_init!(Foo {
49 //! a <- new_mutex!(42, "Foo::a"),
54 //! `foo` now is of the type [`impl PinInit<Foo>`]. We can now use any smart pointer that we like
55 //! (or just the stack) to actually initialize a `Foo`:
58 //! # #![allow(clippy::disallowed_names)]
59 //! # use kernel::sync::{new_mutex, Mutex};
60 //! # use core::pin::Pin;
64 //! # a: Mutex<usize>,
67 //! # let foo = pin_init!(Foo {
68 //! # a <- new_mutex!(42, "Foo::a"),
71 //! let foo: Result<Pin<Box<Foo>>> = Box::pin_init(foo, GFP_KERNEL);
74 //! For more information see the [`pin_init!`] macro.
76 //! ## Using a custom function/macro that returns an initializer
78 //! Many types from the kernel supply a function/macro that returns an initializer, because the
79 //! above method only works for types where you can access the fields.
82 //! # use kernel::sync::{new_mutex, Arc, Mutex};
83 //! let mtx: Result<Arc<Mutex<usize>>> =
84 //! Arc::pin_init(new_mutex!(42, "example::mtx"), GFP_KERNEL);
87 //! To declare an init macro/function you just return an [`impl PinInit<T, E>`]:
90 //! # #![allow(clippy::disallowed_names)]
91 //! # use kernel::{sync::Mutex, new_mutex, init::PinInit, try_pin_init};
93 //! struct DriverData {
95 //! status: Mutex<i32>,
96 //! buffer: Box<[u8; 1_000_000]>,
100 //! fn new() -> impl PinInit<Self, Error> {
101 //! try_pin_init!(Self {
102 //! status <- new_mutex!(0, "DriverData::status"),
103 //! buffer: Box::init(kernel::init::zeroed(), GFP_KERNEL)?,
109 //! ## Manual creation of an initializer
111 //! Often when working with primitives the previous approaches are not sufficient. That is where
112 //! [`pin_init_from_closure()`] comes in. This `unsafe` function allows you to create a
113 //! [`impl PinInit<T, E>`] directly from a closure. Of course you have to ensure that the closure
114 //! actually does the initialization in the correct way. Here are the things to look out for
115 //! (we are calling the parameter to the closure `slot`):
116 //! - when the closure returns `Ok(())`, then it has completed the initialization successfully, so
117 //! `slot` now contains a valid bit pattern for the type `T`,
118 //! - when the closure returns `Err(e)`, then the caller may deallocate the memory at `slot`, so
119 //! you need to take care to clean up anything if your initialization fails mid-way,
120 //! - you may assume that `slot` will stay pinned even after the closure returns until `drop` of
121 //! `slot` gets called.
124 //! # #![allow(unreachable_pub, clippy::disallowed_names)]
125 //! use kernel::{init, types::Opaque};
126 //! use core::{ptr::addr_of_mut, marker::PhantomPinned, pin::Pin};
128 //! # #![allow(non_camel_case_types)]
129 //! # pub struct foo;
130 //! # pub unsafe fn init_foo(_ptr: *mut foo) {}
131 //! # pub unsafe fn destroy_foo(_ptr: *mut foo) {}
132 //! # pub unsafe fn enable_foo(_ptr: *mut foo, _flags: u32) -> i32 { 0 }
134 //! # // `Error::from_errno` is `pub(crate)` in the `kernel` crate, thus provide a workaround.
135 //! # trait FromErrno {
136 //! # fn from_errno(errno: core::ffi::c_int) -> Error {
137 //! # // Dummy error that can be constructed outside the `kernel` crate.
138 //! # Error::from(core::fmt::Error)
141 //! # impl FromErrno for Error {}
144 //! /// `foo` is always initialized
145 //! #[pin_data(PinnedDrop)]
146 //! pub struct RawFoo {
148 //! foo: Opaque<bindings::foo>,
150 //! _p: PhantomPinned,
154 //! pub fn new(flags: u32) -> impl PinInit<Self, Error> {
156 //! // - when the closure returns `Ok(())`, then it has successfully initialized and
157 //! // enabled `foo`,
158 //! // - when it returns `Err(e)`, then it has cleaned up before
160 //! init::pin_init_from_closure(move |slot: *mut Self| {
161 //! // `slot` contains uninit memory, avoid creating a reference.
162 //! let foo = addr_of_mut!((*slot).foo);
164 //! // Initialize the `foo`
165 //! bindings::init_foo(Opaque::raw_get(foo));
167 //! // Try to enable it.
168 //! let err = bindings::enable_foo(Opaque::raw_get(foo), flags);
170 //! // Enabling has failed, first clean up the foo and then return the error.
171 //! bindings::destroy_foo(Opaque::raw_get(foo));
172 //! return Err(Error::from_errno(err));
175 //! // All fields of `RawFoo` have been initialized, since `_p` is a ZST.
183 //! impl PinnedDrop for RawFoo {
184 //! fn drop(self: Pin<&mut Self>) {
185 //! // SAFETY: Since `foo` is initialized, destroying is safe.
186 //! unsafe { bindings::destroy_foo(self.foo.get()) };
191 //! For the special case where initializing a field is a single FFI-function call that cannot fail,
192 //! there exist the helper function [`Opaque::ffi_init`]. This function initialize a single
193 //! [`Opaque`] field by just delegating to the supplied closure. You can use these in combination
194 //! with [`pin_init!`].
196 //! For more information on how to use [`pin_init_from_closure()`], take a look at the uses inside
197 //! the `kernel` crate. The [`sync`] module is a good starting point.
199 //! [`sync`]: kernel::sync
200 //! [pinning]: https://doc.rust-lang.org/std/pin/index.html
201 //! [structurally pinned fields]:
202 //! https://doc.rust-lang.org/std/pin/index.html#pinning-is-structural-for-field
203 //! [stack]: crate::stack_pin_init
204 //! [`Arc<T>`]: crate::sync::Arc
205 //! [`impl PinInit<Foo>`]: PinInit
206 //! [`impl PinInit<T, E>`]: PinInit
207 //! [`impl Init<T, E>`]: Init
208 //! [`Opaque`]: kernel::types::Opaque
209 //! [`Opaque::ffi_init`]: kernel::types::Opaque::ffi_init
210 //! [`pin_data`]: ::macros::pin_data
211 //! [`pin_init!`]: crate::pin_init!
214 alloc::{box_ext::BoxExt, AllocError, Flags},
215 error::{self, Error},
217 types::{Opaque, ScopeGuard},
219 use alloc::boxed::Box;
227 ptr::{self, NonNull},
235 /// Initialize and pin a type directly on the stack.
240 /// # #![allow(clippy::disallowed_names)]
241 /// # use kernel::{init, macros::pin_data, pin_init, stack_pin_init, init::*, sync::Mutex, new_mutex};
242 /// # use core::pin::Pin;
255 /// stack_pin_init!(let foo = pin_init!(Foo {
256 /// a <- new_mutex!(42),
261 /// let foo: Pin<&mut Foo> = foo;
262 /// pr_info!("a: {}", &*foo.a.lock());
267 /// A normal `let` binding with optional type annotation. The expression is expected to implement
268 /// [`PinInit`]/[`Init`] with the error type [`Infallible`]. If you want to use a different error
269 /// type, then use [`stack_try_pin_init!`].
271 /// [`stack_try_pin_init!`]: crate::stack_try_pin_init!
273 macro_rules! stack_pin_init {
274 (let $var:ident $(: $t:ty)? = $val:expr) => {
276 let mut $var = ::core::pin::pin!($crate::init::__internal::StackInit$(::<$t>)?::uninit());
277 let mut $var = match $crate::init::__internal::StackInit::init($var, val) {
280 let x: ::core::convert::Infallible = x;
287 /// Initialize and pin a type directly on the stack.
292 /// # #![allow(clippy::disallowed_names)]
293 /// # use kernel::{init, pin_init, stack_try_pin_init, init::*, sync::Mutex, new_mutex};
294 /// # use macros::pin_data;
295 /// # use core::{alloc::AllocError, pin::Pin};
307 /// stack_try_pin_init!(let foo: Result<Pin<&mut Foo>, AllocError> = pin_init!(Foo {
308 /// a <- new_mutex!(42),
309 /// b: Box::new(Bar {
313 /// let foo = foo.unwrap();
314 /// pr_info!("a: {}", &*foo.a.lock());
318 /// # #![allow(clippy::disallowed_names)]
319 /// # use kernel::{init, pin_init, stack_try_pin_init, init::*, sync::Mutex, new_mutex};
320 /// # use macros::pin_data;
321 /// # use core::{alloc::AllocError, pin::Pin};
333 /// stack_try_pin_init!(let foo: Pin<&mut Foo> =? pin_init!(Foo {
334 /// a <- new_mutex!(42),
335 /// b: Box::new(Bar {
339 /// pr_info!("a: {}", &*foo.a.lock());
340 /// # Ok::<_, AllocError>(())
345 /// A normal `let` binding with optional type annotation. The expression is expected to implement
346 /// [`PinInit`]/[`Init`]. This macro assigns a result to the given variable, adding a `?` after the
347 /// `=` will propagate this error.
349 macro_rules! stack_try_pin_init {
350 (let $var:ident $(: $t:ty)? = $val:expr) => {
352 let mut $var = ::core::pin::pin!($crate::init::__internal::StackInit$(::<$t>)?::uninit());
353 let mut $var = $crate::init::__internal::StackInit::init($var, val);
355 (let $var:ident $(: $t:ty)? =? $val:expr) => {
357 let mut $var = ::core::pin::pin!($crate::init::__internal::StackInit$(::<$t>)?::uninit());
358 let mut $var = $crate::init::__internal::StackInit::init($var, val)?;
362 /// Construct an in-place, pinned initializer for `struct`s.
364 /// This macro defaults the error to [`Infallible`]. If you need [`Error`], then use
365 /// [`try_pin_init!`].
367 /// The syntax is almost identical to that of a normal `struct` initializer:
370 /// # #![allow(clippy::disallowed_names)]
371 /// # use kernel::{init, pin_init, macros::pin_data, init::*};
372 /// # use core::pin::Pin;
384 /// # fn demo() -> impl PinInit<Foo> {
387 /// let initializer = pin_init!(Foo {
394 /// # Box::pin_init(demo(), GFP_KERNEL).unwrap();
397 /// Arbitrary Rust expressions can be used to set the value of a variable.
399 /// The fields are initialized in the order that they appear in the initializer. So it is possible
400 /// to read already initialized fields using raw pointers.
402 /// IMPORTANT: You are not allowed to create references to fields of the struct inside of the
407 /// When working with this API it is often desired to let others construct your types without
408 /// giving access to all fields. This is where you would normally write a plain function `new`
409 /// that would return a new instance of your type. With this API that is also possible.
410 /// However, there are a few extra things to keep in mind.
412 /// To create an initializer function, simply declare it like this:
415 /// # #![allow(clippy::disallowed_names)]
416 /// # use kernel::{init, pin_init, init::*};
417 /// # use core::pin::Pin;
428 /// fn new() -> impl PinInit<Self> {
439 /// Users of `Foo` can now create it like this:
442 /// # #![allow(clippy::disallowed_names)]
443 /// # use kernel::{init, pin_init, macros::pin_data, init::*};
444 /// # use core::pin::Pin;
455 /// # fn new() -> impl PinInit<Self> {
456 /// # pin_init!(Self {
464 /// let foo = Box::pin_init(Foo::new(), GFP_KERNEL);
467 /// They can also easily embed it into their own `struct`s:
470 /// # #![allow(clippy::disallowed_names)]
471 /// # use kernel::{init, pin_init, macros::pin_data, init::*};
472 /// # use core::pin::Pin;
483 /// # fn new() -> impl PinInit<Self> {
484 /// # pin_init!(Self {
493 /// struct FooContainer {
501 /// impl FooContainer {
502 /// fn new(other: u32) -> impl PinInit<Self> {
504 /// foo1 <- Foo::new(),
505 /// foo2 <- Foo::new(),
512 /// Here we see that when using `pin_init!` with `PinInit`, one needs to write `<-` instead of `:`.
513 /// This signifies that the given field is initialized in-place. As with `struct` initializers, just
514 /// writing the field (in this case `other`) without `:` or `<-` means `other: other,`.
518 /// As already mentioned in the examples above, inside of `pin_init!` a `struct` initializer with
519 /// the following modifications is expected:
520 /// - Fields that you want to initialize in-place have to use `<-` instead of `:`.
521 /// - In front of the initializer you can write `&this in` to have access to a [`NonNull<Self>`]
522 /// pointer named `this` inside of the initializer.
523 /// - Using struct update syntax one can place `..Zeroable::zeroed()` at the very end of the
524 /// struct, this initializes every field with 0 and then runs all initializers specified in the
525 /// body. This can only be done if [`Zeroable`] is implemented for the struct.
530 /// # use kernel::{macros::{Zeroable, pin_data}, pin_init};
531 /// # use core::{ptr::addr_of_mut, marker::PhantomPinned};
533 /// #[derive(Zeroable)]
535 /// // `ptr` points into `buf`.
539 /// pin: PhantomPinned,
541 /// pin_init!(&this in Buf {
543 /// ptr: unsafe { addr_of_mut!((*this.as_ptr()).buf).cast() },
544 /// pin: PhantomPinned,
548 /// ..Zeroable::zeroed()
552 /// [`try_pin_init!`]: kernel::try_pin_init
553 /// [`NonNull<Self>`]: core::ptr::NonNull
554 // For a detailed example of how this macro works, see the module documentation of the hidden
555 // module `__internal` inside of `init/__internal.rs`.
557 macro_rules! pin_init {
558 ($(&$this:ident in)? $t:ident $(::<$($generics:ty),* $(,)?>)? {
561 $crate::__init_internal!(
563 @typ($t $(::<$($generics),*>)?),
564 @fields($($fields)*),
565 @error(::core::convert::Infallible),
566 @data(PinData, use_data),
567 @has_data(HasPinData, __pin_data),
568 @construct_closure(pin_init_from_closure),
569 @munch_fields($($fields)*),
574 /// Construct an in-place, fallible pinned initializer for `struct`s.
576 /// If the initialization can complete without error (or [`Infallible`]), then use [`pin_init!`].
578 /// You can use the `?` operator or use `return Err(err)` inside the initializer to stop
579 /// initialization and return the error.
581 /// IMPORTANT: if you have `unsafe` code inside of the initializer you have to ensure that when
582 /// initialization fails, the memory can be safely deallocated without any further modifications.
584 /// This macro defaults the error to [`Error`].
586 /// The syntax is identical to [`pin_init!`] with the following exception: you can append `? $type`
587 /// after the `struct` initializer to specify the error type you want to use.
592 /// # #![feature(new_uninit)]
593 /// use kernel::{init::{self, PinInit}, error::Error};
596 /// big: Box<[u8; 1024 * 1024 * 1024]>,
597 /// small: [u8; 1024 * 1024],
602 /// fn new() -> impl PinInit<Self, Error> {
603 /// try_pin_init!(Self {
604 /// big: Box::init(init::zeroed(), GFP_KERNEL)?,
605 /// small: [0; 1024 * 1024],
606 /// ptr: core::ptr::null_mut(),
611 // For a detailed example of how this macro works, see the module documentation of the hidden
612 // module `__internal` inside of `init/__internal.rs`.
614 macro_rules! try_pin_init {
615 ($(&$this:ident in)? $t:ident $(::<$($generics:ty),* $(,)?>)? {
618 $crate::__init_internal!(
620 @typ($t $(::<$($generics),*>)? ),
621 @fields($($fields)*),
622 @error($crate::error::Error),
623 @data(PinData, use_data),
624 @has_data(HasPinData, __pin_data),
625 @construct_closure(pin_init_from_closure),
626 @munch_fields($($fields)*),
629 ($(&$this:ident in)? $t:ident $(::<$($generics:ty),* $(,)?>)? {
632 $crate::__init_internal!(
634 @typ($t $(::<$($generics),*>)? ),
635 @fields($($fields)*),
637 @data(PinData, use_data),
638 @has_data(HasPinData, __pin_data),
639 @construct_closure(pin_init_from_closure),
640 @munch_fields($($fields)*),
645 /// Construct an in-place initializer for `struct`s.
647 /// This macro defaults the error to [`Infallible`]. If you need [`Error`], then use
650 /// The syntax is identical to [`pin_init!`] and its safety caveats also apply:
651 /// - `unsafe` code must guarantee either full initialization or return an error and allow
652 /// deallocation of the memory.
653 /// - the fields are initialized in the order given in the initializer.
654 /// - no references to fields are allowed to be created inside of the initializer.
656 /// This initializer is for initializing data in-place that might later be moved. If you want to
657 /// pin-initialize, use [`pin_init!`].
659 /// [`try_init!`]: crate::try_init!
660 // For a detailed example of how this macro works, see the module documentation of the hidden
661 // module `__internal` inside of `init/__internal.rs`.
664 ($(&$this:ident in)? $t:ident $(::<$($generics:ty),* $(,)?>)? {
667 $crate::__init_internal!(
669 @typ($t $(::<$($generics),*>)?),
670 @fields($($fields)*),
671 @error(::core::convert::Infallible),
672 @data(InitData, /*no use_data*/),
673 @has_data(HasInitData, __init_data),
674 @construct_closure(init_from_closure),
675 @munch_fields($($fields)*),
680 /// Construct an in-place fallible initializer for `struct`s.
682 /// This macro defaults the error to [`Error`]. If you need [`Infallible`], then use
685 /// The syntax is identical to [`try_pin_init!`]. If you want to specify a custom error,
686 /// append `? $type` after the `struct` initializer.
687 /// The safety caveats from [`try_pin_init!`] also apply:
688 /// - `unsafe` code must guarantee either full initialization or return an error and allow
689 /// deallocation of the memory.
690 /// - the fields are initialized in the order given in the initializer.
691 /// - no references to fields are allowed to be created inside of the initializer.
696 /// use kernel::{init::{PinInit, zeroed}, error::Error};
698 /// big: Box<[u8; 1024 * 1024 * 1024]>,
699 /// small: [u8; 1024 * 1024],
703 /// fn new() -> impl Init<Self, Error> {
705 /// big: Box::init(zeroed(), GFP_KERNEL)?,
706 /// small: [0; 1024 * 1024],
711 // For a detailed example of how this macro works, see the module documentation of the hidden
712 // module `__internal` inside of `init/__internal.rs`.
714 macro_rules! try_init {
715 ($(&$this:ident in)? $t:ident $(::<$($generics:ty),* $(,)?>)? {
718 $crate::__init_internal!(
720 @typ($t $(::<$($generics),*>)?),
721 @fields($($fields)*),
722 @error($crate::error::Error),
723 @data(InitData, /*no use_data*/),
724 @has_data(HasInitData, __init_data),
725 @construct_closure(init_from_closure),
726 @munch_fields($($fields)*),
729 ($(&$this:ident in)? $t:ident $(::<$($generics:ty),* $(,)?>)? {
732 $crate::__init_internal!(
734 @typ($t $(::<$($generics),*>)?),
735 @fields($($fields)*),
737 @data(InitData, /*no use_data*/),
738 @has_data(HasInitData, __init_data),
739 @construct_closure(init_from_closure),
740 @munch_fields($($fields)*),
745 /// A pin-initializer for the type `T`.
747 /// To use this initializer, you will need a suitable memory location that can hold a `T`. This can
748 /// be [`Box<T>`], [`Arc<T>`], [`UniqueArc<T>`] or even the stack (see [`stack_pin_init!`]). Use the
749 /// [`InPlaceInit::pin_init`] function of a smart pointer like [`Arc<T>`] on this.
751 /// Also see the [module description](self).
755 /// When implementing this trait you will need to take great care. Also there are probably very few
756 /// cases where a manual implementation is necessary. Use [`pin_init_from_closure`] where possible.
758 /// The [`PinInit::__pinned_init`] function:
759 /// - returns `Ok(())` if it initialized every field of `slot`,
760 /// - returns `Err(err)` if it encountered an error and then cleaned `slot`, this means:
761 /// - `slot` can be deallocated without UB occurring,
762 /// - `slot` does not need to be dropped,
763 /// - `slot` is not partially initialized.
764 /// - while constructing the `T` at `slot` it upholds the pinning invariants of `T`.
766 /// [`Arc<T>`]: crate::sync::Arc
767 /// [`Arc::pin_init`]: crate::sync::Arc::pin_init
768 #[must_use = "An initializer must be used in order to create its value."]
769 pub unsafe trait PinInit<T: ?Sized, E = Infallible>: Sized {
770 /// Initializes `slot`.
774 /// - `slot` is a valid pointer to uninitialized memory.
775 /// - the caller does not touch `slot` when `Err` is returned, they are only permitted to
777 /// - `slot` will not move until it is dropped, i.e. it will be pinned.
778 unsafe fn __pinned_init(self, slot: *mut T) -> Result<(), E>;
780 /// First initializes the value using `self` then calls the function `f` with the initialized
783 /// If `f` returns an error the value is dropped and the initializer will forward the error.
788 /// # #![allow(clippy::disallowed_names)]
789 /// use kernel::{types::Opaque, init::pin_init_from_closure};
791 /// struct RawFoo([u8; 16]);
793 /// fn init_foo(_: *mut RawFoo);
799 /// raw: Opaque<RawFoo>,
803 /// fn setup(self: Pin<&mut Self>) {
804 /// pr_info!("Setting up foo");
808 /// let foo = pin_init!(Foo {
810 /// Opaque::ffi_init(|s| {
814 /// }).pin_chain(|foo| {
819 fn pin_chain<F>(self, f: F) -> ChainPinInit<Self, F, T, E>
821 F: FnOnce(Pin<&mut T>) -> Result<(), E>,
823 ChainPinInit(self, f, PhantomData)
827 /// An initializer returned by [`PinInit::pin_chain`].
828 pub struct ChainPinInit<I, F, T: ?Sized, E>(I, F, __internal::Invariant<(E, Box<T>)>);
830 // SAFETY: The `__pinned_init` function is implemented such that it
831 // - returns `Ok(())` on successful initialization,
832 // - returns `Err(err)` on error and in this case `slot` will be dropped.
833 // - considers `slot` pinned.
834 unsafe impl<T: ?Sized, E, I, F> PinInit<T, E> for ChainPinInit<I, F, T, E>
837 F: FnOnce(Pin<&mut T>) -> Result<(), E>,
839 unsafe fn __pinned_init(self, slot: *mut T) -> Result<(), E> {
840 // SAFETY: All requirements fulfilled since this function is `__pinned_init`.
841 unsafe { self.0.__pinned_init(slot)? };
842 // SAFETY: The above call initialized `slot` and we still have unique access.
843 let val = unsafe { &mut *slot };
844 // SAFETY: `slot` is considered pinned.
845 let val = unsafe { Pin::new_unchecked(val) };
846 // SAFETY: `slot` was initialized above.
847 (self.1)(val).inspect_err(|_| unsafe { core::ptr::drop_in_place(slot) })
851 /// An initializer for `T`.
853 /// To use this initializer, you will need a suitable memory location that can hold a `T`. This can
854 /// be [`Box<T>`], [`Arc<T>`], [`UniqueArc<T>`] or even the stack (see [`stack_pin_init!`]). Use the
855 /// [`InPlaceInit::init`] function of a smart pointer like [`Arc<T>`] on this. Because
856 /// [`PinInit<T, E>`] is a super trait, you can use every function that takes it as well.
858 /// Also see the [module description](self).
862 /// When implementing this trait you will need to take great care. Also there are probably very few
863 /// cases where a manual implementation is necessary. Use [`init_from_closure`] where possible.
865 /// The [`Init::__init`] function:
866 /// - returns `Ok(())` if it initialized every field of `slot`,
867 /// - returns `Err(err)` if it encountered an error and then cleaned `slot`, this means:
868 /// - `slot` can be deallocated without UB occurring,
869 /// - `slot` does not need to be dropped,
870 /// - `slot` is not partially initialized.
871 /// - while constructing the `T` at `slot` it upholds the pinning invariants of `T`.
873 /// The `__pinned_init` function from the supertrait [`PinInit`] needs to execute the exact same
874 /// code as `__init`.
876 /// Contrary to its supertype [`PinInit<T, E>`] the caller is allowed to
877 /// move the pointee after initialization.
879 /// [`Arc<T>`]: crate::sync::Arc
880 #[must_use = "An initializer must be used in order to create its value."]
881 pub unsafe trait Init<T: ?Sized, E = Infallible>: PinInit<T, E> {
882 /// Initializes `slot`.
886 /// - `slot` is a valid pointer to uninitialized memory.
887 /// - the caller does not touch `slot` when `Err` is returned, they are only permitted to
889 unsafe fn __init(self, slot: *mut T) -> Result<(), E>;
891 /// First initializes the value using `self` then calls the function `f` with the initialized
894 /// If `f` returns an error the value is dropped and the initializer will forward the error.
899 /// # #![allow(clippy::disallowed_names)]
900 /// use kernel::{types::Opaque, init::{self, init_from_closure}};
902 /// buf: [u8; 1_000_000],
906 /// fn setup(&mut self) {
907 /// pr_info!("Setting up foo");
911 /// let foo = init!(Foo {
912 /// buf <- init::zeroed()
918 fn chain<F>(self, f: F) -> ChainInit<Self, F, T, E>
920 F: FnOnce(&mut T) -> Result<(), E>,
922 ChainInit(self, f, PhantomData)
926 /// An initializer returned by [`Init::chain`].
927 pub struct ChainInit<I, F, T: ?Sized, E>(I, F, __internal::Invariant<(E, Box<T>)>);
929 // SAFETY: The `__init` function is implemented such that it
930 // - returns `Ok(())` on successful initialization,
931 // - returns `Err(err)` on error and in this case `slot` will be dropped.
932 unsafe impl<T: ?Sized, E, I, F> Init<T, E> for ChainInit<I, F, T, E>
935 F: FnOnce(&mut T) -> Result<(), E>,
937 unsafe fn __init(self, slot: *mut T) -> Result<(), E> {
938 // SAFETY: All requirements fulfilled since this function is `__init`.
939 unsafe { self.0.__pinned_init(slot)? };
940 // SAFETY: The above call initialized `slot` and we still have unique access.
941 (self.1)(unsafe { &mut *slot }).inspect_err(|_|
942 // SAFETY: `slot` was initialized above.
943 unsafe { core::ptr::drop_in_place(slot) })
947 // SAFETY: `__pinned_init` behaves exactly the same as `__init`.
948 unsafe impl<T: ?Sized, E, I, F> PinInit<T, E> for ChainInit<I, F, T, E>
951 F: FnOnce(&mut T) -> Result<(), E>,
953 unsafe fn __pinned_init(self, slot: *mut T) -> Result<(), E> {
954 // SAFETY: `__init` has less strict requirements compared to `__pinned_init`.
955 unsafe { self.__init(slot) }
959 /// Creates a new [`PinInit<T, E>`] from the given closure.
964 /// - returns `Ok(())` if it initialized every field of `slot`,
965 /// - returns `Err(err)` if it encountered an error and then cleaned `slot`, this means:
966 /// - `slot` can be deallocated without UB occurring,
967 /// - `slot` does not need to be dropped,
968 /// - `slot` is not partially initialized.
969 /// - may assume that the `slot` does not move if `T: !Unpin`,
970 /// - while constructing the `T` at `slot` it upholds the pinning invariants of `T`.
972 pub const unsafe fn pin_init_from_closure<T: ?Sized, E>(
973 f: impl FnOnce(*mut T) -> Result<(), E>,
974 ) -> impl PinInit<T, E> {
975 __internal::InitClosure(f, PhantomData)
978 /// Creates a new [`Init<T, E>`] from the given closure.
983 /// - returns `Ok(())` if it initialized every field of `slot`,
984 /// - returns `Err(err)` if it encountered an error and then cleaned `slot`, this means:
985 /// - `slot` can be deallocated without UB occurring,
986 /// - `slot` does not need to be dropped,
987 /// - `slot` is not partially initialized.
988 /// - the `slot` may move after initialization.
989 /// - while constructing the `T` at `slot` it upholds the pinning invariants of `T`.
991 pub const unsafe fn init_from_closure<T: ?Sized, E>(
992 f: impl FnOnce(*mut T) -> Result<(), E>,
993 ) -> impl Init<T, E> {
994 __internal::InitClosure(f, PhantomData)
997 /// An initializer that leaves the memory uninitialized.
999 /// The initializer is a no-op. The `slot` memory is not changed.
1001 pub fn uninit<T, E>() -> impl Init<MaybeUninit<T>, E> {
1002 // SAFETY: The memory is allowed to be uninitialized.
1003 unsafe { init_from_closure(|_| Ok(())) }
1006 /// Initializes an array by initializing each element via the provided initializer.
1011 /// use kernel::{error::Error, init::init_array_from_fn};
1012 /// let array: Box<[usize; 1_000]> = Box::init::<Error>(init_array_from_fn(|i| i), GFP_KERNEL).unwrap();
1013 /// assert_eq!(array.len(), 1_000);
1015 pub fn init_array_from_fn<I, const N: usize, T, E>(
1016 mut make_init: impl FnMut(usize) -> I,
1017 ) -> impl Init<[T; N], E>
1021 let init = move |slot: *mut [T; N]| {
1022 let slot = slot.cast::<T>();
1023 // Counts the number of initialized elements and when dropped drops that many elements from
1025 let mut init_count = ScopeGuard::new_with_data(0, |i| {
1026 // We now free every element that has been initialized before.
1027 // SAFETY: The loop initialized exactly the values from 0..i and since we
1028 // return `Err` below, the caller will consider the memory at `slot` as
1030 unsafe { ptr::drop_in_place(ptr::slice_from_raw_parts_mut(slot, i)) };
1033 let init = make_init(i);
1034 // SAFETY: Since 0 <= `i` < N, it is still in bounds of `[T; N]`.
1035 let ptr = unsafe { slot.add(i) };
1036 // SAFETY: The pointer is derived from `slot` and thus satisfies the `__init`
1038 unsafe { init.__init(ptr) }?;
1041 init_count.dismiss();
1044 // SAFETY: The initializer above initializes every element of the array. On failure it drops
1045 // any initialized elements and returns `Err`.
1046 unsafe { init_from_closure(init) }
1049 /// Initializes an array by initializing each element via the provided initializer.
1054 /// use kernel::{sync::{Arc, Mutex}, init::pin_init_array_from_fn, new_mutex};
1055 /// let array: Arc<[Mutex<usize>; 1_000]> =
1056 /// Arc::pin_init(pin_init_array_from_fn(|i| new_mutex!(i)), GFP_KERNEL).unwrap();
1057 /// assert_eq!(array.len(), 1_000);
1059 pub fn pin_init_array_from_fn<I, const N: usize, T, E>(
1060 mut make_init: impl FnMut(usize) -> I,
1061 ) -> impl PinInit<[T; N], E>
1065 let init = move |slot: *mut [T; N]| {
1066 let slot = slot.cast::<T>();
1067 // Counts the number of initialized elements and when dropped drops that many elements from
1069 let mut init_count = ScopeGuard::new_with_data(0, |i| {
1070 // We now free every element that has been initialized before.
1071 // SAFETY: The loop initialized exactly the values from 0..i and since we
1072 // return `Err` below, the caller will consider the memory at `slot` as
1074 unsafe { ptr::drop_in_place(ptr::slice_from_raw_parts_mut(slot, i)) };
1077 let init = make_init(i);
1078 // SAFETY: Since 0 <= `i` < N, it is still in bounds of `[T; N]`.
1079 let ptr = unsafe { slot.add(i) };
1080 // SAFETY: The pointer is derived from `slot` and thus satisfies the `__init`
1082 unsafe { init.__pinned_init(ptr) }?;
1085 init_count.dismiss();
1088 // SAFETY: The initializer above initializes every element of the array. On failure it drops
1089 // any initialized elements and returns `Err`.
1090 unsafe { pin_init_from_closure(init) }
1093 // SAFETY: Every type can be initialized by-value.
1094 unsafe impl<T, E> Init<T, E> for T {
1095 unsafe fn __init(self, slot: *mut T) -> Result<(), E> {
1096 unsafe { slot.write(self) };
1101 // SAFETY: Every type can be initialized by-value. `__pinned_init` calls `__init`.
1102 unsafe impl<T, E> PinInit<T, E> for T {
1103 unsafe fn __pinned_init(self, slot: *mut T) -> Result<(), E> {
1104 unsafe { self.__init(slot) }
1108 /// Smart pointer that can initialize memory in-place.
1109 pub trait InPlaceInit<T>: Sized {
1110 /// Use the given pin-initializer to pin-initialize a `T` inside of a new smart pointer of this
1113 /// If `T: !Unpin` it will not be able to move afterwards.
1114 fn try_pin_init<E>(init: impl PinInit<T, E>, flags: Flags) -> Result<Pin<Self>, E>
1116 E: From<AllocError>;
1118 /// Use the given pin-initializer to pin-initialize a `T` inside of a new smart pointer of this
1121 /// If `T: !Unpin` it will not be able to move afterwards.
1122 fn pin_init<E>(init: impl PinInit<T, E>, flags: Flags) -> error::Result<Pin<Self>>
1126 // SAFETY: We delegate to `init` and only change the error type.
1128 pin_init_from_closure(|slot| init.__pinned_init(slot).map_err(|e| Error::from(e)))
1130 Self::try_pin_init(init, flags)
1133 /// Use the given initializer to in-place initialize a `T`.
1134 fn try_init<E>(init: impl Init<T, E>, flags: Flags) -> Result<Self, E>
1136 E: From<AllocError>;
1138 /// Use the given initializer to in-place initialize a `T`.
1139 fn init<E>(init: impl Init<T, E>, flags: Flags) -> error::Result<Self>
1143 // SAFETY: We delegate to `init` and only change the error type.
1145 init_from_closure(|slot| init.__pinned_init(slot).map_err(|e| Error::from(e)))
1147 Self::try_init(init, flags)
1151 impl<T> InPlaceInit<T> for Box<T> {
1153 fn try_pin_init<E>(init: impl PinInit<T, E>, flags: Flags) -> Result<Pin<Self>, E>
1155 E: From<AllocError>,
1157 let mut this = <Box<_> as BoxExt<_>>::new_uninit(flags)?;
1158 let slot = this.as_mut_ptr();
1159 // SAFETY: When init errors/panics, slot will get deallocated but not dropped,
1160 // slot is valid and will not be moved, because we pin it later.
1161 unsafe { init.__pinned_init(slot)? };
1162 // SAFETY: All fields have been initialized.
1163 Ok(unsafe { this.assume_init() }.into())
1167 fn try_init<E>(init: impl Init<T, E>, flags: Flags) -> Result<Self, E>
1169 E: From<AllocError>,
1171 let mut this = <Box<_> as BoxExt<_>>::new_uninit(flags)?;
1172 let slot = this.as_mut_ptr();
1173 // SAFETY: When init errors/panics, slot will get deallocated but not dropped,
1175 unsafe { init.__init(slot)? };
1176 // SAFETY: All fields have been initialized.
1177 Ok(unsafe { this.assume_init() })
1181 impl<T> InPlaceInit<T> for UniqueArc<T> {
1183 fn try_pin_init<E>(init: impl PinInit<T, E>, flags: Flags) -> Result<Pin<Self>, E>
1185 E: From<AllocError>,
1187 let mut this = UniqueArc::new_uninit(flags)?;
1188 let slot = this.as_mut_ptr();
1189 // SAFETY: When init errors/panics, slot will get deallocated but not dropped,
1190 // slot is valid and will not be moved, because we pin it later.
1191 unsafe { init.__pinned_init(slot)? };
1192 // SAFETY: All fields have been initialized.
1193 Ok(unsafe { this.assume_init() }.into())
1197 fn try_init<E>(init: impl Init<T, E>, flags: Flags) -> Result<Self, E>
1199 E: From<AllocError>,
1201 let mut this = UniqueArc::new_uninit(flags)?;
1202 let slot = this.as_mut_ptr();
1203 // SAFETY: When init errors/panics, slot will get deallocated but not dropped,
1205 unsafe { init.__init(slot)? };
1206 // SAFETY: All fields have been initialized.
1207 Ok(unsafe { this.assume_init() })
1211 /// Trait facilitating pinned destruction.
1213 /// Use [`pinned_drop`] to implement this trait safely:
1216 /// # use kernel::sync::Mutex;
1217 /// use kernel::macros::pinned_drop;
1218 /// use core::pin::Pin;
1219 /// #[pin_data(PinnedDrop)]
1222 /// mtx: Mutex<usize>,
1226 /// impl PinnedDrop for Foo {
1227 /// fn drop(self: Pin<&mut Self>) {
1228 /// pr_info!("Foo is being dropped!");
1235 /// This trait must be implemented via the [`pinned_drop`] proc-macro attribute on the impl.
1237 /// [`pinned_drop`]: kernel::macros::pinned_drop
1238 pub unsafe trait PinnedDrop: __internal::HasPinData {
1239 /// Executes the pinned destructor of this type.
1241 /// While this function is marked safe, it is actually unsafe to call it manually. For this
1242 /// reason it takes an additional parameter. This type can only be constructed by `unsafe` code
1243 /// and thus prevents this function from being called where it should not.
1245 /// This extra parameter will be generated by the `#[pinned_drop]` proc-macro attribute
1247 fn drop(self: Pin<&mut Self>, only_call_from_drop: __internal::OnlyCallFromDrop);
1250 /// Marker trait for types that can be initialized by writing just zeroes.
1254 /// The bit pattern consisting of only zeroes is a valid bit pattern for this type. In other words,
1258 /// let val: Self = unsafe { core::mem::zeroed() };
1260 pub unsafe trait Zeroable {}
1262 /// Create a new zeroed T.
1264 /// The returned initializer will write `0x00` to every byte of the given `slot`.
1266 pub fn zeroed<T: Zeroable>() -> impl Init<T> {
1267 // SAFETY: Because `T: Zeroable`, all bytes zero is a valid bit pattern for `T`
1268 // and because we write all zeroes, the memory is initialized.
1270 init_from_closure(|slot: *mut T| {
1271 slot.write_bytes(0, 1);
1277 macro_rules! impl_zeroable {
1278 ($($({$($generics:tt)*})? $t:ty, )*) => {
1279 $(unsafe impl$($($generics)*)? Zeroable for $t {})*
1284 // SAFETY: All primitives that are allowed to be zero.
1287 u8, u16, u32, u64, u128, usize,
1288 i8, i16, i32, i64, i128, isize,
1291 // Note: do not add uninhabited types (such as `!` or `core::convert::Infallible`) to this list;
1292 // creating an instance of an uninhabited type is immediate undefined behavior. For more on
1293 // uninhabited/empty types, consult The Rustonomicon:
1294 // <https://doc.rust-lang.org/stable/nomicon/exotic-sizes.html#empty-types>. The Rust Reference
1295 // also has information on undefined behavior:
1296 // <https://doc.rust-lang.org/stable/reference/behavior-considered-undefined.html>.
1298 // SAFETY: These are inhabited ZSTs; there is nothing to zero and a valid value exists.
1299 {<T: ?Sized>} PhantomData<T>, core::marker::PhantomPinned, (),
1301 // SAFETY: Type is allowed to take any value, including all zeros.
1302 {<T>} MaybeUninit<T>,
1303 // SAFETY: Type is allowed to take any value, including all zeros.
1306 // SAFETY: `T: Zeroable` and `UnsafeCell` is `repr(transparent)`.
1307 {<T: ?Sized + Zeroable>} UnsafeCell<T>,
1309 // SAFETY: All zeros is equivalent to `None` (option layout optimization guarantee).
1310 Option<NonZeroU8>, Option<NonZeroU16>, Option<NonZeroU32>, Option<NonZeroU64>,
1311 Option<NonZeroU128>, Option<NonZeroUsize>,
1312 Option<NonZeroI8>, Option<NonZeroI16>, Option<NonZeroI32>, Option<NonZeroI64>,
1313 Option<NonZeroI128>, Option<NonZeroIsize>,
1315 // SAFETY: All zeros is equivalent to `None` (option layout optimization guarantee).
1317 // In this case we are allowed to use `T: ?Sized`, since all zeros is the `None` variant.
1318 {<T: ?Sized>} Option<NonNull<T>>,
1319 {<T: ?Sized>} Option<Box<T>>,
1321 // SAFETY: `null` pointer is valid.
1323 // We cannot use `T: ?Sized`, since the VTABLE pointer part of fat pointers is not allowed to be
1326 // When `Pointee` gets stabilized, we could use
1327 // `T: ?Sized where <T as Pointee>::Metadata: Zeroable`
1328 {<T>} *mut T, {<T>} *const T,
1330 // SAFETY: `null` pointer is valid and the metadata part of these fat pointers is allowed to be
1332 {<T>} *mut [T], {<T>} *const [T], *mut str, *const str,
1334 // SAFETY: `T` is `Zeroable`.
1335 {<const N: usize, T: Zeroable>} [T; N], {<T: Zeroable>} Wrapping<T>,
1338 macro_rules! impl_tuple_zeroable {
1340 ($first:ident, $($t:ident),* $(,)?) => {
1341 // SAFETY: All elements are zeroable and padding can be zero.
1342 unsafe impl<$first: Zeroable, $($t: Zeroable),*> Zeroable for ($first, $($t),*) {}
1343 impl_tuple_zeroable!($($t),* ,);
1347 impl_tuple_zeroable!(A, B, C, D, E, F, G, H, I, J);