// SPDX-License-Identifier: Apache-2.0 OR MIT12//! This module provides the macros that actually implement the proc-macros `pin_data` and3//! `pinned_drop`. It also contains `__init_internal`, the implementation of the4//! `{try_}{pin_}init!` macros.5//!6//! These macros should never be called directly, since they expect their input to be7//! in a certain format which is internal. If used incorrectly, these macros can lead to UB even in8//! safe code! Use the public facing macros instead.9//!10//! This architecture has been chosen because the kernel does not yet have access to `syn` which11//! would make matters a lot easier for implementing these as proc-macros.12//!13//! Since this library and the kernel implementation should diverge as little as possible, the same14//! approach has been taken here.15//!16//! # Macro expansion example17//!18//! This section is intended for readers trying to understand the macros in this module and the19//! `[try_][pin_]init!` macros from `lib.rs`.20//!21//! We will look at the following example:22//!23//! ```rust,ignore24//! #[pin_data]25//! #[repr(C)]26//! struct Bar<T> {27//! #[pin]28//! t: T,29//! pub x: usize,30//! }31//!32//! impl<T> Bar<T> {33//! fn new(t: T) -> impl PinInit<Self> {34//! pin_init!(Self { t, x: 0 })35//! }36//! }37//!38//! #[pin_data(PinnedDrop)]39//! struct Foo {40//! a: usize,41//! #[pin]42//! b: Bar<u32>,43//! }44//!45//! #[pinned_drop]46//! impl PinnedDrop for Foo {47//! fn drop(self: Pin<&mut Self>) {48//! println!("{self:p} is getting dropped.");49//! }50//! }51//!52//! let a = 42;53//! let initializer = pin_init!(Foo {54//! a,55//! b <- Bar::new(36),56//! });57//! ```58//!59//! This example includes the most common and important features of the pin-init API.60//!61//! Below you can find individual section about the different macro invocations. Here are some62//! general things we need to take into account when designing macros:63//! - use global paths, similarly to file paths, these start with the separator: `::core::panic!()`64//! this ensures that the correct item is used, since users could define their own `mod core {}`65//! and then their own `panic!` inside to execute arbitrary code inside of our macro.66//! - macro `unsafe` hygiene: we need to ensure that we do not expand arbitrary, user-supplied67//! expressions inside of an `unsafe` block in the macro, because this would allow users to do68//! `unsafe` operations without an associated `unsafe` block.69//!70//! ## `#[pin_data]` on `Bar`71//!72//! This macro is used to specify which fields are structurally pinned and which fields are not. It73//! is placed on the struct definition and allows `#[pin]` to be placed on the fields.74//!75//! Here is the definition of `Bar` from our example:76//!77//! ```rust,ignore78//! #[pin_data]79//! #[repr(C)]80//! struct Bar<T> {81//! #[pin]82//! t: T,83//! pub x: usize,84//! }85//! ```86//!87//! This expands to the following code:88//!89//! ```rust,ignore90//! // Firstly the normal definition of the struct, attributes are preserved:91//! #[repr(C)]92//! struct Bar<T> {93//! t: T,94//! pub x: usize,95//! }96//! // Then an anonymous constant is defined, this is because we do not want any code to access the97//! // types that we define inside:98//! const _: () = {99//! // We define the pin-data carrying struct, it is a ZST and needs to have the same generics,100//! // since we need to implement access functions for each field and thus need to know its101//! // type.102//! struct __ThePinData<T> {103//! __phantom: ::core::marker::PhantomData<fn(Bar<T>) -> Bar<T>>,104//! }105//! // We implement `Copy` for the pin-data struct, since all functions it defines will take106//! // `self` by value.107//! impl<T> ::core::clone::Clone for __ThePinData<T> {108//! fn clone(&self) -> Self {109//! *self110//! }111//! }112//! impl<T> ::core::marker::Copy for __ThePinData<T> {}113//! // For every field of `Bar`, the pin-data struct will define a function with the same name114//! // and accessor (`pub` or `pub(crate)` etc.). This function will take a pointer to the115//! // field (`slot`) and a `PinInit` or `Init` depending on the projection kind of the field116//! // (if pinning is structural for the field, then `PinInit` otherwise `Init`).117//! #[allow(dead_code)]118//! impl<T> __ThePinData<T> {119//! unsafe fn t<E>(120//! self,121//! slot: *mut T,122//! // Since `t` is `#[pin]`, this is `PinInit`.123//! init: impl ::pin_init::PinInit<T, E>,124//! ) -> ::core::result::Result<(), E> {125//! unsafe { ::pin_init::PinInit::__pinned_init(init, slot) }126//! }127//! pub unsafe fn x<E>(128//! self,129//! slot: *mut usize,130//! // Since `x` is not `#[pin]`, this is `Init`.131//! init: impl ::pin_init::Init<usize, E>,132//! ) -> ::core::result::Result<(), E> {133//! unsafe { ::pin_init::Init::__init(init, slot) }134//! }135//! }136//! // Implement the internal `HasPinData` trait that associates `Bar` with the pin-data struct137//! // that we constructed above.138//! unsafe impl<T> ::pin_init::__internal::HasPinData for Bar<T> {139//! type PinData = __ThePinData<T>;140//! unsafe fn __pin_data() -> Self::PinData {141//! __ThePinData {142//! __phantom: ::core::marker::PhantomData,143//! }144//! }145//! }146//! // Implement the internal `PinData` trait that marks the pin-data struct as a pin-data147//! // struct. This is important to ensure that no user can implement a rogue `__pin_data`148//! // function without using `unsafe`.149//! unsafe impl<T> ::pin_init::__internal::PinData for __ThePinData<T> {150//! type Datee = Bar<T>;151//! }152//! // Now we only want to implement `Unpin` for `Bar` when every structurally pinned field is153//! // `Unpin`. In other words, whether `Bar` is `Unpin` only depends on structurally pinned154//! // fields (those marked with `#[pin]`). These fields will be listed in this struct, in our155//! // case no such fields exist, hence this is almost empty. The two phantomdata fields exist156//! // for two reasons:157//! // - `__phantom`: every generic must be used, since we cannot really know which generics158//! // are used, we declare all and then use everything here once.159//! // - `__phantom_pin`: uses the `'__pin` lifetime and ensures that this struct is invariant160//! // over it. The lifetime is needed to work around the limitation that trait bounds must161//! // not be trivial, e.g. the user has a `#[pin] PhantomPinned` field -- this is162//! // unconditionally `!Unpin` and results in an error. The lifetime tricks the compiler163//! // into accepting these bounds regardless.164//! #[allow(dead_code)]165//! struct __Unpin<'__pin, T> {166//! __phantom_pin: ::core::marker::PhantomData<fn(&'__pin ()) -> &'__pin ()>,167//! __phantom: ::core::marker::PhantomData<fn(Bar<T>) -> Bar<T>>,168//! // Our only `#[pin]` field is `t`.169//! t: T,170//! }171//! #[doc(hidden)]172//! impl<'__pin, T> ::core::marker::Unpin for Bar<T>173//! where174//! __Unpin<'__pin, T>: ::core::marker::Unpin,175//! {}176//! // Now we need to ensure that `Bar` does not implement `Drop`, since that would give users177//! // access to `&mut self` inside of `drop` even if the struct was pinned. This could lead to178//! // UB with only safe code, so we disallow this by giving a trait implementation error using179//! // a direct impl and a blanket implementation.180//! trait MustNotImplDrop {}181//! // Normally `Drop` bounds do not have the correct semantics, but for this purpose they do182//! // (normally people want to know if a type has any kind of drop glue at all, here we want183//! // to know if it has any kind of custom drop glue, which is exactly what this bound does).184//! #[expect(drop_bounds)]185//! impl<T: ::core::ops::Drop> MustNotImplDrop for T {}186//! impl<T> MustNotImplDrop for Bar<T> {}187//! // Here comes a convenience check, if one implemented `PinnedDrop`, but forgot to add it to188//! // `#[pin_data]`, then this will error with the same mechanic as above, this is not needed189//! // for safety, but a good sanity check, since no normal code calls `PinnedDrop::drop`.190//! #[expect(non_camel_case_types)]191//! trait UselessPinnedDropImpl_you_need_to_specify_PinnedDrop {}192//! impl<193//! T: ::pin_init::PinnedDrop,194//! > UselessPinnedDropImpl_you_need_to_specify_PinnedDrop for T {}195//! impl<T> UselessPinnedDropImpl_you_need_to_specify_PinnedDrop for Bar<T> {}196//! };197//! ```198//!199//! ## `pin_init!` in `impl Bar`200//!201//! This macro creates an pin-initializer for the given struct. It requires that the struct is202//! annotated by `#[pin_data]`.203//!204//! Here is the impl on `Bar` defining the new function:205//!206//! ```rust,ignore207//! impl<T> Bar<T> {208//! fn new(t: T) -> impl PinInit<Self> {209//! pin_init!(Self { t, x: 0 })210//! }211//! }212//! ```213//!214//! This expands to the following code:215//!216//! ```rust,ignore217//! impl<T> Bar<T> {218//! fn new(t: T) -> impl PinInit<Self> {219//! {220//! // We do not want to allow arbitrary returns, so we declare this type as the `Ok`221//! // return type and shadow it later when we insert the arbitrary user code. That way222//! // there will be no possibility of returning without `unsafe`.223//! struct __InitOk;224//! // Get the data about fields from the supplied type.225//! // - the function is unsafe, hence the unsafe block226//! // - we `use` the `HasPinData` trait in the block, it is only available in that227//! // scope.228//! let data = unsafe {229//! use ::pin_init::__internal::HasPinData;230//! Self::__pin_data()231//! };232//! // Ensure that `data` really is of type `PinData` and help with type inference:233//! let init = ::pin_init::__internal::PinData::make_closure::<234//! _,235//! __InitOk,236//! ::core::convert::Infallible,237//! >(data, move |slot| {238//! {239//! // Shadow the structure so it cannot be used to return early. If a user240//! // tries to write `return Ok(__InitOk)`, then they get a type error,241//! // since that will refer to this struct instead of the one defined242//! // above.243//! struct __InitOk;244//! // This is the expansion of `t,`, which is syntactic sugar for `t: t,`.245//! {246//! unsafe { ::core::ptr::write(::core::addr_of_mut!((*slot).t), t) };247//! }248//! // Since initialization could fail later (not in this case, since the249//! // error type is `Infallible`) we will need to drop this field if there250//! // is an error later. This `DropGuard` will drop the field when it gets251//! // dropped and has not yet been forgotten.252//! let __t_guard = unsafe {253//! ::pin_init::__internal::DropGuard::new(::core::addr_of_mut!((*slot).t))254//! };255//! // Expansion of `x: 0,`:256//! // Since this can be an arbitrary expression we cannot place it inside257//! // of the `unsafe` block, so we bind it here.258//! {259//! let x = 0;260//! unsafe { ::core::ptr::write(::core::addr_of_mut!((*slot).x), x) };261//! }262//! // We again create a `DropGuard`.263//! let __x_guard = unsafe {264//! ::pin_init::__internal::DropGuard::new(::core::addr_of_mut!((*slot).x))265//! };266//! // Since initialization has successfully completed, we can now forget267//! // the guards. This is not `mem::forget`, since we only have268//! // `&DropGuard`.269//! ::core::mem::forget(__x_guard);270//! ::core::mem::forget(__t_guard);271//! // Here we use the type checker to ensure that every field has been272//! // initialized exactly once, since this is `if false` it will never get273//! // executed, but still type-checked.274//! // Additionally we abuse `slot` to automatically infer the correct type275//! // for the struct. This is also another check that every field is276//! // accessible from this scope.277//! #[allow(unreachable_code, clippy::diverging_sub_expression)]278//! let _ = || {279//! unsafe {280//! ::core::ptr::write(281//! slot,282//! Self {283//! // We only care about typecheck finding every field284//! // here, the expression does not matter, just conjure285//! // one using `panic!()`:286//! t: ::core::panic!(),287//! x: ::core::panic!(),288//! },289//! );290//! };291//! };292//! }293//! // We leave the scope above and gain access to the previously shadowed294//! // `__InitOk` that we need to return.295//! Ok(__InitOk)296//! });297//! // Change the return type from `__InitOk` to `()`.298//! let init = move |299//! slot,300//! | -> ::core::result::Result<(), ::core::convert::Infallible> {301//! init(slot).map(|__InitOk| ())302//! };303//! // Construct the initializer.304//! let init = unsafe {305//! ::pin_init::pin_init_from_closure::<306//! _,307//! ::core::convert::Infallible,308//! >(init)309//! };310//! init311//! }312//! }313//! }314//! ```315//!316//! ## `#[pin_data]` on `Foo`317//!318//! Since we already took a look at `#[pin_data]` on `Bar`, this section will only explain the319//! differences/new things in the expansion of the `Foo` definition:320//!321//! ```rust,ignore322//! #[pin_data(PinnedDrop)]323//! struct Foo {324//! a: usize,325//! #[pin]326//! b: Bar<u32>,327//! }328//! ```329//!330//! This expands to the following code:331//!332//! ```rust,ignore333//! struct Foo {334//! a: usize,335//! b: Bar<u32>,336//! }337//! const _: () = {338//! struct __ThePinData {339//! __phantom: ::core::marker::PhantomData<fn(Foo) -> Foo>,340//! }341//! impl ::core::clone::Clone for __ThePinData {342//! fn clone(&self) -> Self {343//! *self344//! }345//! }346//! impl ::core::marker::Copy for __ThePinData {}347//! #[allow(dead_code)]348//! impl __ThePinData {349//! unsafe fn b<E>(350//! self,351//! slot: *mut Bar<u32>,352//! init: impl ::pin_init::PinInit<Bar<u32>, E>,353//! ) -> ::core::result::Result<(), E> {354//! unsafe { ::pin_init::PinInit::__pinned_init(init, slot) }355//! }356//! unsafe fn a<E>(357//! self,358//! slot: *mut usize,359//! init: impl ::pin_init::Init<usize, E>,360//! ) -> ::core::result::Result<(), E> {361//! unsafe { ::pin_init::Init::__init(init, slot) }362//! }363//! }364//! unsafe impl ::pin_init::__internal::HasPinData for Foo {365//! type PinData = __ThePinData;366//! unsafe fn __pin_data() -> Self::PinData {367//! __ThePinData {368//! __phantom: ::core::marker::PhantomData,369//! }370//! }371//! }372//! unsafe impl ::pin_init::__internal::PinData for __ThePinData {373//! type Datee = Foo;374//! }375//! #[allow(dead_code)]376//! struct __Unpin<'__pin> {377//! __phantom_pin: ::core::marker::PhantomData<fn(&'__pin ()) -> &'__pin ()>,378//! __phantom: ::core::marker::PhantomData<fn(Foo) -> Foo>,379//! b: Bar<u32>,380//! }381//! #[doc(hidden)]382//! impl<'__pin> ::core::marker::Unpin for Foo383//! where384//! __Unpin<'__pin>: ::core::marker::Unpin,385//! {}386//! // Since we specified `PinnedDrop` as the argument to `#[pin_data]`, we expect `Foo` to387//! // implement `PinnedDrop`. Thus we do not need to prevent `Drop` implementations like388//! // before, instead we implement `Drop` here and delegate to `PinnedDrop`.389//! impl ::core::ops::Drop for Foo {390//! fn drop(&mut self) {391//! // Since we are getting dropped, no one else has a reference to `self` and thus we392//! // can assume that we never move.393//! let pinned = unsafe { ::core::pin::Pin::new_unchecked(self) };394//! // Create the unsafe token that proves that we are inside of a destructor, this395//! // type is only allowed to be created in a destructor.396//! let token = unsafe { ::pin_init::__internal::OnlyCallFromDrop::new() };397//! ::pin_init::PinnedDrop::drop(pinned, token);398//! }399//! }400//! };401//! ```402//!403//! ## `#[pinned_drop]` on `impl PinnedDrop for Foo`404//!405//! This macro is used to implement the `PinnedDrop` trait, since that trait is `unsafe` and has an406//! extra parameter that should not be used at all. The macro hides that parameter.407//!408//! Here is the `PinnedDrop` impl for `Foo`:409//!410//! ```rust,ignore411//! #[pinned_drop]412//! impl PinnedDrop for Foo {413//! fn drop(self: Pin<&mut Self>) {414//! println!("{self:p} is getting dropped.");415//! }416//! }417//! ```418//!419//! This expands to the following code:420//!421//! ```rust,ignore422//! // `unsafe`, full path and the token parameter are added, everything else stays the same.423//! unsafe impl ::pin_init::PinnedDrop for Foo {424//! fn drop(self: Pin<&mut Self>, _: ::pin_init::__internal::OnlyCallFromDrop) {425//! println!("{self:p} is getting dropped.");426//! }427//! }428//! ```429//!430//! ## `pin_init!` on `Foo`431//!432//! Since we already took a look at `pin_init!` on `Bar`, this section will only show the expansion433//! of `pin_init!` on `Foo`:434//!435//! ```rust,ignore436//! let a = 42;437//! let initializer = pin_init!(Foo {438//! a,439//! b <- Bar::new(36),440//! });441//! ```442//!443//! This expands to the following code:444//!445//! ```rust,ignore446//! let a = 42;447//! let initializer = {448//! struct __InitOk;449//! let data = unsafe {450//! use ::pin_init::__internal::HasPinData;451//! Foo::__pin_data()452//! };453//! let init = ::pin_init::__internal::PinData::make_closure::<454//! _,455//! __InitOk,456//! ::core::convert::Infallible,457//! >(data, move |slot| {458//! {459//! struct __InitOk;460//! {461//! unsafe { ::core::ptr::write(::core::addr_of_mut!((*slot).a), a) };462//! }463//! let __a_guard = unsafe {464//! ::pin_init::__internal::DropGuard::new(::core::addr_of_mut!((*slot).a))465//! };466//! let init = Bar::new(36);467//! unsafe { data.b(::core::addr_of_mut!((*slot).b), b)? };468//! let __b_guard = unsafe {469//! ::pin_init::__internal::DropGuard::new(::core::addr_of_mut!((*slot).b))470//! };471//! ::core::mem::forget(__b_guard);472//! ::core::mem::forget(__a_guard);473//! #[allow(unreachable_code, clippy::diverging_sub_expression)]474//! let _ = || {475//! unsafe {476//! ::core::ptr::write(477//! slot,478//! Foo {479//! a: ::core::panic!(),480//! b: ::core::panic!(),481//! },482//! );483//! };484//! };485//! }486//! Ok(__InitOk)487//! });488//! let init = move |489//! slot,490//! | -> ::core::result::Result<(), ::core::convert::Infallible> {491//! init(slot).map(|__InitOk| ())492//! };493//! let init = unsafe {494//! ::pin_init::pin_init_from_closure::<_, ::core::convert::Infallible>(init)495//! };496//! init497//! };498//! ```499500#[cfg(kernel)]501pub use ::macros::paste;502#[cfg(not(kernel))]503pub use ::paste::paste;504505/// Creates a `unsafe impl<...> PinnedDrop for $type` block.506///507/// See [`PinnedDrop`] for more information.508#[doc(hidden)]509#[macro_export]510macro_rules! __pinned_drop {511(512@impl_sig($($impl_sig:tt)*),513@impl_body(514$(#[$($attr:tt)*])*515fn drop($($sig:tt)*) {516$($inner:tt)*517}518),519) => {520// SAFETY: TODO.521unsafe $($impl_sig)* {522// Inherit all attributes and the type/ident tokens for the signature.523$(#[$($attr)*])*524fn drop($($sig)*, _: $crate::__internal::OnlyCallFromDrop) {525$($inner)*526}527}528}529}530531/// This macro first parses the struct definition such that it separates pinned and not pinned532/// fields. Afterwards it declares the struct and implement the `PinData` trait safely.533#[doc(hidden)]534#[macro_export]535macro_rules! __pin_data {536// Proc-macro entry point, this is supplied by the proc-macro pre-parsing.537(parse_input:538@args($($pinned_drop:ident)?),539@sig(540$(#[$($struct_attr:tt)*])*541$vis:vis struct $name:ident542$(where $($whr:tt)*)?543),544@impl_generics($($impl_generics:tt)*),545@ty_generics($($ty_generics:tt)*),546@decl_generics($($decl_generics:tt)*),547@body({ $($fields:tt)* }),548) => {549// We now use token munching to iterate through all of the fields. While doing this we550// identify fields marked with `#[pin]`, these fields are the 'pinned fields'. The user551// wants these to be structurally pinned. The rest of the fields are the552// 'not pinned fields'. Additionally we collect all fields, since we need them in the right553// order to declare the struct.554//555// In this call we also put some explaining comments for the parameters.556$crate::__pin_data!(find_pinned_fields:557// Attributes on the struct itself, these will just be propagated to be put onto the558// struct definition.559@struct_attrs($(#[$($struct_attr)*])*),560// The visibility of the struct.561@vis($vis),562// The name of the struct.563@name($name),564// The 'impl generics', the generics that will need to be specified on the struct inside565// of an `impl<$ty_generics>` block.566@impl_generics($($impl_generics)*),567// The 'ty generics', the generics that will need to be specified on the impl blocks.568@ty_generics($($ty_generics)*),569// The 'decl generics', the generics that need to be specified on the struct570// definition.571@decl_generics($($decl_generics)*),572// The where clause of any impl block and the declaration.573@where($($($whr)*)?),574// The remaining fields tokens that need to be processed.575// We add a `,` at the end to ensure correct parsing.576@fields_munch($($fields)* ,),577// The pinned fields.578@pinned(),579// The not pinned fields.580@not_pinned(),581// All fields.582@fields(),583// The accumulator containing all attributes already parsed.584@accum(),585// Contains `yes` or `` to indicate if `#[pin]` was found on the current field.586@is_pinned(),587// The proc-macro argument, this should be `PinnedDrop` or ``.588@pinned_drop($($pinned_drop)?),589);590};591(find_pinned_fields:592@struct_attrs($($struct_attrs:tt)*),593@vis($vis:vis),594@name($name:ident),595@impl_generics($($impl_generics:tt)*),596@ty_generics($($ty_generics:tt)*),597@decl_generics($($decl_generics:tt)*),598@where($($whr:tt)*),599// We found a PhantomPinned field, this should generally be pinned!600@fields_munch($field:ident : $($($(::)?core::)?marker::)?PhantomPinned, $($rest:tt)*),601@pinned($($pinned:tt)*),602@not_pinned($($not_pinned:tt)*),603@fields($($fields:tt)*),604@accum($($accum:tt)*),605// This field is not pinned.606@is_pinned(),607@pinned_drop($($pinned_drop:ident)?),608) => {609::core::compile_error!(concat!(610"The field `",611stringify!($field),612"` of type `PhantomPinned` only has an effect, if it has the `#[pin]` attribute.",613));614$crate::__pin_data!(find_pinned_fields:615@struct_attrs($($struct_attrs)*),616@vis($vis),617@name($name),618@impl_generics($($impl_generics)*),619@ty_generics($($ty_generics)*),620@decl_generics($($decl_generics)*),621@where($($whr)*),622@fields_munch($($rest)*),623@pinned($($pinned)* $($accum)* $field: ::core::marker::PhantomPinned,),624@not_pinned($($not_pinned)*),625@fields($($fields)* $($accum)* $field: ::core::marker::PhantomPinned,),626@accum(),627@is_pinned(),628@pinned_drop($($pinned_drop)?),629);630};631(find_pinned_fields:632@struct_attrs($($struct_attrs:tt)*),633@vis($vis:vis),634@name($name:ident),635@impl_generics($($impl_generics:tt)*),636@ty_generics($($ty_generics:tt)*),637@decl_generics($($decl_generics:tt)*),638@where($($whr:tt)*),639// We reached the field declaration.640@fields_munch($field:ident : $type:ty, $($rest:tt)*),641@pinned($($pinned:tt)*),642@not_pinned($($not_pinned:tt)*),643@fields($($fields:tt)*),644@accum($($accum:tt)*),645// This field is pinned.646@is_pinned(yes),647@pinned_drop($($pinned_drop:ident)?),648) => {649$crate::__pin_data!(find_pinned_fields:650@struct_attrs($($struct_attrs)*),651@vis($vis),652@name($name),653@impl_generics($($impl_generics)*),654@ty_generics($($ty_generics)*),655@decl_generics($($decl_generics)*),656@where($($whr)*),657@fields_munch($($rest)*),658@pinned($($pinned)* $($accum)* $field: $type,),659@not_pinned($($not_pinned)*),660@fields($($fields)* $($accum)* $field: $type,),661@accum(),662@is_pinned(),663@pinned_drop($($pinned_drop)?),664);665};666(find_pinned_fields:667@struct_attrs($($struct_attrs:tt)*),668@vis($vis:vis),669@name($name:ident),670@impl_generics($($impl_generics:tt)*),671@ty_generics($($ty_generics:tt)*),672@decl_generics($($decl_generics:tt)*),673@where($($whr:tt)*),674// We reached the field declaration.675@fields_munch($field:ident : $type:ty, $($rest:tt)*),676@pinned($($pinned:tt)*),677@not_pinned($($not_pinned:tt)*),678@fields($($fields:tt)*),679@accum($($accum:tt)*),680// This field is not pinned.681@is_pinned(),682@pinned_drop($($pinned_drop:ident)?),683) => {684$crate::__pin_data!(find_pinned_fields:685@struct_attrs($($struct_attrs)*),686@vis($vis),687@name($name),688@impl_generics($($impl_generics)*),689@ty_generics($($ty_generics)*),690@decl_generics($($decl_generics)*),691@where($($whr)*),692@fields_munch($($rest)*),693@pinned($($pinned)*),694@not_pinned($($not_pinned)* $($accum)* $field: $type,),695@fields($($fields)* $($accum)* $field: $type,),696@accum(),697@is_pinned(),698@pinned_drop($($pinned_drop)?),699);700};701(find_pinned_fields:702@struct_attrs($($struct_attrs:tt)*),703@vis($vis:vis),704@name($name:ident),705@impl_generics($($impl_generics:tt)*),706@ty_generics($($ty_generics:tt)*),707@decl_generics($($decl_generics:tt)*),708@where($($whr:tt)*),709// We found the `#[pin]` attr.710@fields_munch(#[pin] $($rest:tt)*),711@pinned($($pinned:tt)*),712@not_pinned($($not_pinned:tt)*),713@fields($($fields:tt)*),714@accum($($accum:tt)*),715@is_pinned($($is_pinned:ident)?),716@pinned_drop($($pinned_drop:ident)?),717) => {718$crate::__pin_data!(find_pinned_fields:719@struct_attrs($($struct_attrs)*),720@vis($vis),721@name($name),722@impl_generics($($impl_generics)*),723@ty_generics($($ty_generics)*),724@decl_generics($($decl_generics)*),725@where($($whr)*),726@fields_munch($($rest)*),727// We do not include `#[pin]` in the list of attributes, since it is not actually an728// attribute that is defined somewhere.729@pinned($($pinned)*),730@not_pinned($($not_pinned)*),731@fields($($fields)*),732@accum($($accum)*),733// Set this to `yes`.734@is_pinned(yes),735@pinned_drop($($pinned_drop)?),736);737};738(find_pinned_fields:739@struct_attrs($($struct_attrs:tt)*),740@vis($vis:vis),741@name($name:ident),742@impl_generics($($impl_generics:tt)*),743@ty_generics($($ty_generics:tt)*),744@decl_generics($($decl_generics:tt)*),745@where($($whr:tt)*),746// We reached the field declaration with visibility, for simplicity we only munch the747// visibility and put it into `$accum`.748@fields_munch($fvis:vis $field:ident $($rest:tt)*),749@pinned($($pinned:tt)*),750@not_pinned($($not_pinned:tt)*),751@fields($($fields:tt)*),752@accum($($accum:tt)*),753@is_pinned($($is_pinned:ident)?),754@pinned_drop($($pinned_drop:ident)?),755) => {756$crate::__pin_data!(find_pinned_fields:757@struct_attrs($($struct_attrs)*),758@vis($vis),759@name($name),760@impl_generics($($impl_generics)*),761@ty_generics($($ty_generics)*),762@decl_generics($($decl_generics)*),763@where($($whr)*),764@fields_munch($field $($rest)*),765@pinned($($pinned)*),766@not_pinned($($not_pinned)*),767@fields($($fields)*),768@accum($($accum)* $fvis),769@is_pinned($($is_pinned)?),770@pinned_drop($($pinned_drop)?),771);772};773(find_pinned_fields:774@struct_attrs($($struct_attrs:tt)*),775@vis($vis:vis),776@name($name:ident),777@impl_generics($($impl_generics:tt)*),778@ty_generics($($ty_generics:tt)*),779@decl_generics($($decl_generics:tt)*),780@where($($whr:tt)*),781// Some other attribute, just put it into `$accum`.782@fields_munch(#[$($attr:tt)*] $($rest:tt)*),783@pinned($($pinned:tt)*),784@not_pinned($($not_pinned:tt)*),785@fields($($fields:tt)*),786@accum($($accum:tt)*),787@is_pinned($($is_pinned:ident)?),788@pinned_drop($($pinned_drop:ident)?),789) => {790$crate::__pin_data!(find_pinned_fields:791@struct_attrs($($struct_attrs)*),792@vis($vis),793@name($name),794@impl_generics($($impl_generics)*),795@ty_generics($($ty_generics)*),796@decl_generics($($decl_generics)*),797@where($($whr)*),798@fields_munch($($rest)*),799@pinned($($pinned)*),800@not_pinned($($not_pinned)*),801@fields($($fields)*),802@accum($($accum)* #[$($attr)*]),803@is_pinned($($is_pinned)?),804@pinned_drop($($pinned_drop)?),805);806};807(find_pinned_fields:808@struct_attrs($($struct_attrs:tt)*),809@vis($vis:vis),810@name($name:ident),811@impl_generics($($impl_generics:tt)*),812@ty_generics($($ty_generics:tt)*),813@decl_generics($($decl_generics:tt)*),814@where($($whr:tt)*),815// We reached the end of the fields, plus an optional additional comma, since we added one816// before and the user is also allowed to put a trailing comma.817@fields_munch($(,)?),818@pinned($($pinned:tt)*),819@not_pinned($($not_pinned:tt)*),820@fields($($fields:tt)*),821@accum(),822@is_pinned(),823@pinned_drop($($pinned_drop:ident)?),824) => {825// Declare the struct with all fields in the correct order.826$($struct_attrs)*827$vis struct $name <$($decl_generics)*>828where $($whr)*829{830$($fields)*831}832833$crate::__pin_data!(make_pin_projections:834@vis($vis),835@name($name),836@impl_generics($($impl_generics)*),837@ty_generics($($ty_generics)*),838@decl_generics($($decl_generics)*),839@where($($whr)*),840@pinned($($pinned)*),841@not_pinned($($not_pinned)*),842);843844// We put the rest into this const item, because it then will not be accessible to anything845// outside.846const _: () = {847// We declare this struct which will host all of the projection function for our type.848// it will be invariant over all generic parameters which are inherited from the849// struct.850$vis struct __ThePinData<$($impl_generics)*>851where $($whr)*852{853__phantom: ::core::marker::PhantomData<854fn($name<$($ty_generics)*>) -> $name<$($ty_generics)*>855>,856}857858impl<$($impl_generics)*> ::core::clone::Clone for __ThePinData<$($ty_generics)*>859where $($whr)*860{861fn clone(&self) -> Self { *self }862}863864impl<$($impl_generics)*> ::core::marker::Copy for __ThePinData<$($ty_generics)*>865where $($whr)*866{}867868// Make all projection functions.869$crate::__pin_data!(make_pin_data:870@pin_data(__ThePinData),871@impl_generics($($impl_generics)*),872@ty_generics($($ty_generics)*),873@where($($whr)*),874@pinned($($pinned)*),875@not_pinned($($not_pinned)*),876);877878// SAFETY: We have added the correct projection functions above to `__ThePinData` and879// we also use the least restrictive generics possible.880unsafe impl<$($impl_generics)*>881$crate::__internal::HasPinData for $name<$($ty_generics)*>882where $($whr)*883{884type PinData = __ThePinData<$($ty_generics)*>;885886unsafe fn __pin_data() -> Self::PinData {887__ThePinData { __phantom: ::core::marker::PhantomData }888}889}890891// SAFETY: TODO.892unsafe impl<$($impl_generics)*>893$crate::__internal::PinData for __ThePinData<$($ty_generics)*>894where $($whr)*895{896type Datee = $name<$($ty_generics)*>;897}898899// This struct will be used for the unpin analysis. Since only structurally pinned900// fields are relevant whether the struct should implement `Unpin`.901#[allow(dead_code)]902struct __Unpin <'__pin, $($impl_generics)*>903where $($whr)*904{905__phantom_pin: ::core::marker::PhantomData<fn(&'__pin ()) -> &'__pin ()>,906__phantom: ::core::marker::PhantomData<907fn($name<$($ty_generics)*>) -> $name<$($ty_generics)*>908>,909// Only the pinned fields.910$($pinned)*911}912913#[doc(hidden)]914impl<'__pin, $($impl_generics)*> ::core::marker::Unpin for $name<$($ty_generics)*>915where916__Unpin<'__pin, $($ty_generics)*>: ::core::marker::Unpin,917$($whr)*918{}919920// We need to disallow normal `Drop` implementation, the exact behavior depends on921// whether `PinnedDrop` was specified as the parameter.922$crate::__pin_data!(drop_prevention:923@name($name),924@impl_generics($($impl_generics)*),925@ty_generics($($ty_generics)*),926@where($($whr)*),927@pinned_drop($($pinned_drop)?),928);929};930};931// When no `PinnedDrop` was specified, then we have to prevent implementing drop.932(drop_prevention:933@name($name:ident),934@impl_generics($($impl_generics:tt)*),935@ty_generics($($ty_generics:tt)*),936@where($($whr:tt)*),937@pinned_drop(),938) => {939// We prevent this by creating a trait that will be implemented for all types implementing940// `Drop`. Additionally we will implement this trait for the struct leading to a conflict,941// if it also implements `Drop`942trait MustNotImplDrop {}943#[expect(drop_bounds)]944impl<T: ::core::ops::Drop> MustNotImplDrop for T {}945impl<$($impl_generics)*> MustNotImplDrop for $name<$($ty_generics)*>946where $($whr)* {}947// We also take care to prevent users from writing a useless `PinnedDrop` implementation.948// They might implement `PinnedDrop` correctly for the struct, but forget to give949// `PinnedDrop` as the parameter to `#[pin_data]`.950#[expect(non_camel_case_types)]951trait UselessPinnedDropImpl_you_need_to_specify_PinnedDrop {}952impl<T: $crate::PinnedDrop>953UselessPinnedDropImpl_you_need_to_specify_PinnedDrop for T {}954impl<$($impl_generics)*>955UselessPinnedDropImpl_you_need_to_specify_PinnedDrop for $name<$($ty_generics)*>956where $($whr)* {}957};958// When `PinnedDrop` was specified we just implement `Drop` and delegate.959(drop_prevention:960@name($name:ident),961@impl_generics($($impl_generics:tt)*),962@ty_generics($($ty_generics:tt)*),963@where($($whr:tt)*),964@pinned_drop(PinnedDrop),965) => {966impl<$($impl_generics)*> ::core::ops::Drop for $name<$($ty_generics)*>967where $($whr)*968{969fn drop(&mut self) {970// SAFETY: Since this is a destructor, `self` will not move after this function971// terminates, since it is inaccessible.972let pinned = unsafe { ::core::pin::Pin::new_unchecked(self) };973// SAFETY: Since this is a drop function, we can create this token to call the974// pinned destructor of this type.975let token = unsafe { $crate::__internal::OnlyCallFromDrop::new() };976$crate::PinnedDrop::drop(pinned, token);977}978}979};980// If some other parameter was specified, we emit a readable error.981(drop_prevention:982@name($name:ident),983@impl_generics($($impl_generics:tt)*),984@ty_generics($($ty_generics:tt)*),985@where($($whr:tt)*),986@pinned_drop($($rest:tt)*),987) => {988compile_error!(989"Wrong parameters to `#[pin_data]`, expected nothing or `PinnedDrop`, got '{}'.",990stringify!($($rest)*),991);992};993(make_pin_projections:994@vis($vis:vis),995@name($name:ident),996@impl_generics($($impl_generics:tt)*),997@ty_generics($($ty_generics:tt)*),998@decl_generics($($decl_generics:tt)*),999@where($($whr:tt)*),1000@pinned($($(#[$($p_attr:tt)*])* $pvis:vis $p_field:ident : $p_type:ty),* $(,)?),1001@not_pinned($($(#[$($attr:tt)*])* $fvis:vis $field:ident : $type:ty),* $(,)?),1002) => {1003$crate::macros::paste! {1004#[doc(hidden)]1005$vis struct [< $name Projection >] <'__pin, $($decl_generics)*> {1006$($(#[$($p_attr)*])* $pvis $p_field : ::core::pin::Pin<&'__pin mut $p_type>,)*1007$($(#[$($attr)*])* $fvis $field : &'__pin mut $type,)*1008___pin_phantom_data: ::core::marker::PhantomData<&'__pin mut ()>,1009}10101011impl<$($impl_generics)*> $name<$($ty_generics)*>1012where $($whr)*1013{1014/// Pin-projects all fields of `Self`.1015///1016/// These fields are structurally pinned:1017$(#[doc = ::core::concat!(" - `", ::core::stringify!($p_field), "`")])*1018///1019/// These fields are **not** structurally pinned:1020$(#[doc = ::core::concat!(" - `", ::core::stringify!($field), "`")])*1021#[inline]1022$vis fn project<'__pin>(1023self: ::core::pin::Pin<&'__pin mut Self>,1024) -> [< $name Projection >] <'__pin, $($ty_generics)*> {1025// SAFETY: we only give access to `&mut` for fields not structurally pinned.1026let this = unsafe { ::core::pin::Pin::get_unchecked_mut(self) };1027[< $name Projection >] {1028$(1029// SAFETY: `$p_field` is structurally pinned.1030$(#[$($p_attr)*])*1031$p_field : unsafe { ::core::pin::Pin::new_unchecked(&mut this.$p_field) },1032)*1033$(1034$(#[$($attr)*])*1035$field : &mut this.$field,1036)*1037___pin_phantom_data: ::core::marker::PhantomData,1038}1039}1040}1041}1042};1043(make_pin_data:1044@pin_data($pin_data:ident),1045@impl_generics($($impl_generics:tt)*),1046@ty_generics($($ty_generics:tt)*),1047@where($($whr:tt)*),1048@pinned($($(#[$($p_attr:tt)*])* $pvis:vis $p_field:ident : $p_type:ty),* $(,)?),1049@not_pinned($($(#[$($attr:tt)*])* $fvis:vis $field:ident : $type:ty),* $(,)?),1050) => {1051$crate::macros::paste! {1052// For every field, we create a projection function according to its projection type. If a1053// field is structurally pinned, then it must be initialized via `PinInit`, if it is not1054// structurally pinned, then it can be initialized via `Init`.1055//1056// The functions are `unsafe` to prevent accidentally calling them.1057#[allow(dead_code)]1058#[expect(clippy::missing_safety_doc)]1059impl<$($impl_generics)*> $pin_data<$($ty_generics)*>1060where $($whr)*1061{1062$(1063$(#[$($p_attr)*])*1064$pvis unsafe fn $p_field<E>(1065self,1066slot: *mut $p_type,1067init: impl $crate::PinInit<$p_type, E>,1068) -> ::core::result::Result<(), E> {1069// SAFETY: TODO.1070unsafe { $crate::PinInit::__pinned_init(init, slot) }1071}10721073$(#[$($p_attr)*])*1074$pvis unsafe fn [<__project_ $p_field>]<'__slot>(1075self,1076slot: &'__slot mut $p_type,1077) -> ::core::pin::Pin<&'__slot mut $p_type> {1078::core::pin::Pin::new_unchecked(slot)1079}1080)*1081$(1082$(#[$($attr)*])*1083$fvis unsafe fn $field<E>(1084self,1085slot: *mut $type,1086init: impl $crate::Init<$type, E>,1087) -> ::core::result::Result<(), E> {1088// SAFETY: TODO.1089unsafe { $crate::Init::__init(init, slot) }1090}10911092$(#[$($attr)*])*1093$fvis unsafe fn [<__project_ $field>]<'__slot>(1094self,1095slot: &'__slot mut $type,1096) -> &'__slot mut $type {1097slot1098}1099)*1100}1101}1102};1103}11041105/// The internal init macro. Do not call manually!1106///1107/// This is called by the `{try_}{pin_}init!` macros with various inputs.1108///1109/// This macro has multiple internal call configurations, these are always the very first ident:1110/// - nothing: this is the base case and called by the `{try_}{pin_}init!` macros.1111/// - `with_update_parsed`: when the `..Zeroable::init_zeroed()` syntax has been handled.1112/// - `init_slot`: recursively creates the code that initializes all fields in `slot`.1113/// - `make_initializer`: recursively create the struct initializer that guarantees that every1114/// field has been initialized exactly once.1115#[doc(hidden)]1116#[macro_export]1117macro_rules! __init_internal {1118(1119@this($($this:ident)?),1120@typ($t:path),1121@fields($($fields:tt)*),1122@error($err:ty),1123// Either `PinData` or `InitData`, `$use_data` should only be present in the `PinData`1124// case.1125@data($data:ident, $($use_data:ident)?),1126// `HasPinData` or `HasInitData`.1127@has_data($has_data:ident, $get_data:ident),1128// `pin_init_from_closure` or `init_from_closure`.1129@construct_closure($construct_closure:ident),1130@munch_fields(),1131) => {1132$crate::__init_internal!(with_update_parsed:1133@this($($this)?),1134@typ($t),1135@fields($($fields)*),1136@error($err),1137@data($data, $($use_data)?),1138@has_data($has_data, $get_data),1139@construct_closure($construct_closure),1140@init_zeroed(), // Nothing means default behavior.1141)1142};1143(1144@this($($this:ident)?),1145@typ($t:path),1146@fields($($fields:tt)*),1147@error($err:ty),1148// Either `PinData` or `InitData`, `$use_data` should only be present in the `PinData`1149// case.1150@data($data:ident, $($use_data:ident)?),1151// `HasPinData` or `HasInitData`.1152@has_data($has_data:ident, $get_data:ident),1153// `pin_init_from_closure` or `init_from_closure`.1154@construct_closure($construct_closure:ident),1155@munch_fields(..Zeroable::init_zeroed()),1156) => {1157$crate::__init_internal!(with_update_parsed:1158@this($($this)?),1159@typ($t),1160@fields($($fields)*),1161@error($err),1162@data($data, $($use_data)?),1163@has_data($has_data, $get_data),1164@construct_closure($construct_closure),1165@init_zeroed(()), // `()` means zero all fields not mentioned.1166)1167};1168(1169@this($($this:ident)?),1170@typ($t:path),1171@fields($($fields:tt)*),1172@error($err:ty),1173// Either `PinData` or `InitData`, `$use_data` should only be present in the `PinData`1174// case.1175@data($data:ident, $($use_data:ident)?),1176// `HasPinData` or `HasInitData`.1177@has_data($has_data:ident, $get_data:ident),1178// `pin_init_from_closure` or `init_from_closure`.1179@construct_closure($construct_closure:ident),1180@munch_fields($ignore:tt $($rest:tt)*),1181) => {1182$crate::__init_internal!(1183@this($($this)?),1184@typ($t),1185@fields($($fields)*),1186@error($err),1187@data($data, $($use_data)?),1188@has_data($has_data, $get_data),1189@construct_closure($construct_closure),1190@munch_fields($($rest)*),1191)1192};1193(with_update_parsed:1194@this($($this:ident)?),1195@typ($t:path),1196@fields($($fields:tt)*),1197@error($err:ty),1198// Either `PinData` or `InitData`, `$use_data` should only be present in the `PinData`1199// case.1200@data($data:ident, $($use_data:ident)?),1201// `HasPinData` or `HasInitData`.1202@has_data($has_data:ident, $get_data:ident),1203// `pin_init_from_closure` or `init_from_closure`.1204@construct_closure($construct_closure:ident),1205@init_zeroed($($init_zeroed:expr)?),1206) => {{1207// We do not want to allow arbitrary returns, so we declare this type as the `Ok` return1208// type and shadow it later when we insert the arbitrary user code. That way there will be1209// no possibility of returning without `unsafe`.1210struct __InitOk;1211// Get the data about fields from the supplied type.1212//1213// SAFETY: TODO.1214let data = unsafe {1215use $crate::__internal::$has_data;1216// Here we abuse `paste!` to retokenize `$t`. Declarative macros have some internal1217// information that is associated to already parsed fragments, so a path fragment1218// cannot be used in this position. Doing the retokenization results in valid rust1219// code.1220$crate::macros::paste!($t::$get_data())1221};1222// Ensure that `data` really is of type `$data` and help with type inference:1223let init = $crate::__internal::$data::make_closure::<_, __InitOk, $err>(1224data,1225move |slot| {1226{1227// Shadow the structure so it cannot be used to return early.1228struct __InitOk;1229// If `$init_zeroed` is present we should zero the slot now and not emit an1230// error when fields are missing (since they will be zeroed). We also have to1231// check that the type actually implements `Zeroable`.1232$({1233fn assert_zeroable<T: $crate::Zeroable>(_: *mut T) {}1234// Ensure that the struct is indeed `Zeroable`.1235assert_zeroable(slot);1236// SAFETY: The type implements `Zeroable` by the check above.1237unsafe { ::core::ptr::write_bytes(slot, 0, 1) };1238$init_zeroed // This will be `()` if set.1239})?1240// Create the `this` so it can be referenced by the user inside of the1241// expressions creating the individual fields.1242$(let $this = unsafe { ::core::ptr::NonNull::new_unchecked(slot) };)?1243// Initialize every field.1244$crate::__init_internal!(init_slot($($use_data)?):1245@data(data),1246@slot(slot),1247@guards(),1248@munch_fields($($fields)*,),1249);1250// We use unreachable code to ensure that all fields have been mentioned exactly1251// once, this struct initializer will still be type-checked and complain with a1252// very natural error message if a field is forgotten/mentioned more than once.1253#[allow(unreachable_code, clippy::diverging_sub_expression)]1254let _ = || {1255$crate::__init_internal!(make_initializer:1256@slot(slot),1257@type_name($t),1258@munch_fields($($fields)*,),1259@acc(),1260);1261};1262}1263Ok(__InitOk)1264}1265);1266let init = move |slot| -> ::core::result::Result<(), $err> {1267init(slot).map(|__InitOk| ())1268};1269// SAFETY: TODO.1270let init = unsafe { $crate::$construct_closure::<_, $err>(init) };1271init1272}};1273(init_slot($($use_data:ident)?):1274@data($data:ident),1275@slot($slot:ident),1276@guards($($guards:ident,)*),1277@munch_fields($(..Zeroable::init_zeroed())? $(,)?),1278) => {1279// Endpoint of munching, no fields are left. If execution reaches this point, all fields1280// have been initialized. Therefore we can now dismiss the guards by forgetting them.1281$(::core::mem::forget($guards);)*1282};1283(init_slot($($use_data:ident)?):1284@data($data:ident),1285@slot($slot:ident),1286@guards($($guards:ident,)*),1287// arbitrary code block1288@munch_fields(_: { $($code:tt)* }, $($rest:tt)*),1289) => {1290{ $($code)* }1291$crate::__init_internal!(init_slot($($use_data)?):1292@data($data),1293@slot($slot),1294@guards($($guards,)*),1295@munch_fields($($rest)*),1296);1297};1298(init_slot($use_data:ident): // `use_data` is present, so we use the `data` to init fields.1299@data($data:ident),1300@slot($slot:ident),1301@guards($($guards:ident,)*),1302// In-place initialization syntax.1303@munch_fields($field:ident <- $val:expr, $($rest:tt)*),1304) => {1305let init = $val;1306// Call the initializer.1307//1308// SAFETY: `slot` is valid, because we are inside of an initializer closure, we1309// return when an error/panic occurs.1310// We also use the `data` to require the correct trait (`Init` or `PinInit`) for `$field`.1311unsafe { $data.$field(::core::ptr::addr_of_mut!((*$slot).$field), init)? };1312// SAFETY:1313// - the project function does the correct field projection,1314// - the field has been initialized,1315// - the reference is only valid until the end of the initializer.1316#[allow(unused_variables)]1317let $field = $crate::macros::paste!(unsafe { $data.[< __project_ $field >](&mut (*$slot).$field) });13181319// Create the drop guard:1320//1321// We rely on macro hygiene to make it impossible for users to access this local variable.1322// We use `paste!` to create new hygiene for `$field`.1323$crate::macros::paste! {1324// SAFETY: We forget the guard later when initialization has succeeded.1325let [< __ $field _guard >] = unsafe {1326$crate::__internal::DropGuard::new(::core::ptr::addr_of_mut!((*$slot).$field))1327};13281329$crate::__init_internal!(init_slot($use_data):1330@data($data),1331@slot($slot),1332@guards([< __ $field _guard >], $($guards,)*),1333@munch_fields($($rest)*),1334);1335}1336};1337(init_slot(): // No `use_data`, so we use `Init::__init` directly.1338@data($data:ident),1339@slot($slot:ident),1340@guards($($guards:ident,)*),1341// In-place initialization syntax.1342@munch_fields($field:ident <- $val:expr, $($rest:tt)*),1343) => {1344let init = $val;1345// Call the initializer.1346//1347// SAFETY: `slot` is valid, because we are inside of an initializer closure, we1348// return when an error/panic occurs.1349unsafe { $crate::Init::__init(init, ::core::ptr::addr_of_mut!((*$slot).$field))? };13501351// SAFETY:1352// - the field is not structurally pinned, since the line above must compile,1353// - the field has been initialized,1354// - the reference is only valid until the end of the initializer.1355#[allow(unused_variables)]1356let $field = unsafe { &mut (*$slot).$field };13571358// Create the drop guard:1359//1360// We rely on macro hygiene to make it impossible for users to access this local variable.1361// We use `paste!` to create new hygiene for `$field`.1362$crate::macros::paste! {1363// SAFETY: We forget the guard later when initialization has succeeded.1364let [< __ $field _guard >] = unsafe {1365$crate::__internal::DropGuard::new(::core::ptr::addr_of_mut!((*$slot).$field))1366};13671368$crate::__init_internal!(init_slot():1369@data($data),1370@slot($slot),1371@guards([< __ $field _guard >], $($guards,)*),1372@munch_fields($($rest)*),1373);1374}1375};1376(init_slot(): // No `use_data`, so all fields are not structurally pinned1377@data($data:ident),1378@slot($slot:ident),1379@guards($($guards:ident,)*),1380// Init by-value.1381@munch_fields($field:ident $(: $val:expr)?, $($rest:tt)*),1382) => {1383{1384$(let $field = $val;)?1385// Initialize the field.1386//1387// SAFETY: The memory at `slot` is uninitialized.1388unsafe { ::core::ptr::write(::core::ptr::addr_of_mut!((*$slot).$field), $field) };1389}13901391#[allow(unused_variables)]1392// SAFETY:1393// - the field is not structurally pinned, since no `use_data` was required to create this1394// initializer,1395// - the field has been initialized,1396// - the reference is only valid until the end of the initializer.1397let $field = unsafe { &mut (*$slot).$field };13981399// Create the drop guard:1400//1401// We rely on macro hygiene to make it impossible for users to access this local variable.1402// We use `paste!` to create new hygiene for `$field`.1403$crate::macros::paste! {1404// SAFETY: We forget the guard later when initialization has succeeded.1405let [< __ $field _guard >] = unsafe {1406$crate::__internal::DropGuard::new(::core::ptr::addr_of_mut!((*$slot).$field))1407};14081409$crate::__init_internal!(init_slot():1410@data($data),1411@slot($slot),1412@guards([< __ $field _guard >], $($guards,)*),1413@munch_fields($($rest)*),1414);1415}1416};1417(init_slot($use_data:ident):1418@data($data:ident),1419@slot($slot:ident),1420@guards($($guards:ident,)*),1421// Init by-value.1422@munch_fields($field:ident $(: $val:expr)?, $($rest:tt)*),1423) => {1424{1425$(let $field = $val;)?1426// Initialize the field.1427//1428// SAFETY: The memory at `slot` is uninitialized.1429unsafe { ::core::ptr::write(::core::ptr::addr_of_mut!((*$slot).$field), $field) };1430}1431// SAFETY:1432// - the project function does the correct field projection,1433// - the field has been initialized,1434// - the reference is only valid until the end of the initializer.1435#[allow(unused_variables)]1436let $field = $crate::macros::paste!(unsafe { $data.[< __project_ $field >](&mut (*$slot).$field) });14371438// Create the drop guard:1439//1440// We rely on macro hygiene to make it impossible for users to access this local variable.1441// We use `paste!` to create new hygiene for `$field`.1442$crate::macros::paste! {1443// SAFETY: We forget the guard later when initialization has succeeded.1444let [< __ $field _guard >] = unsafe {1445$crate::__internal::DropGuard::new(::core::ptr::addr_of_mut!((*$slot).$field))1446};14471448$crate::__init_internal!(init_slot($use_data):1449@data($data),1450@slot($slot),1451@guards([< __ $field _guard >], $($guards,)*),1452@munch_fields($($rest)*),1453);1454}1455};1456(make_initializer:1457@slot($slot:ident),1458@type_name($t:path),1459@munch_fields(_: { $($code:tt)* }, $($rest:tt)*),1460@acc($($acc:tt)*),1461) => {1462// code blocks are ignored for the initializer check1463$crate::__init_internal!(make_initializer:1464@slot($slot),1465@type_name($t),1466@munch_fields($($rest)*),1467@acc($($acc)*),1468);1469};1470(make_initializer:1471@slot($slot:ident),1472@type_name($t:path),1473@munch_fields(..Zeroable::init_zeroed() $(,)?),1474@acc($($acc:tt)*),1475) => {1476// Endpoint, nothing more to munch, create the initializer. Since the users specified1477// `..Zeroable::init_zeroed()`, the slot will already have been zeroed and all field that have1478// not been overwritten are thus zero and initialized. We still check that all fields are1479// actually accessible by using the struct update syntax ourselves.1480// We are inside of a closure that is never executed and thus we can abuse `slot` to1481// get the correct type inference here:1482#[allow(unused_assignments)]1483unsafe {1484let mut zeroed = ::core::mem::zeroed();1485// We have to use type inference here to make zeroed have the correct type. This does1486// not get executed, so it has no effect.1487::core::ptr::write($slot, zeroed);1488zeroed = ::core::mem::zeroed();1489// Here we abuse `paste!` to retokenize `$t`. Declarative macros have some internal1490// information that is associated to already parsed fragments, so a path fragment1491// cannot be used in this position. Doing the retokenization results in valid rust1492// code.1493$crate::macros::paste!(1494::core::ptr::write($slot, $t {1495$($acc)*1496..zeroed1497});1498);1499}1500};1501(make_initializer:1502@slot($slot:ident),1503@type_name($t:path),1504@munch_fields($(,)?),1505@acc($($acc:tt)*),1506) => {1507// Endpoint, nothing more to munch, create the initializer.1508// Since we are in the closure that is never called, this will never get executed.1509// We abuse `slot` to get the correct type inference here:1510//1511// SAFETY: TODO.1512unsafe {1513// Here we abuse `paste!` to retokenize `$t`. Declarative macros have some internal1514// information that is associated to already parsed fragments, so a path fragment1515// cannot be used in this position. Doing the retokenization results in valid rust1516// code.1517$crate::macros::paste!(1518::core::ptr::write($slot, $t {1519$($acc)*1520});1521);1522}1523};1524(make_initializer:1525@slot($slot:ident),1526@type_name($t:path),1527@munch_fields($field:ident <- $val:expr, $($rest:tt)*),1528@acc($($acc:tt)*),1529) => {1530$crate::__init_internal!(make_initializer:1531@slot($slot),1532@type_name($t),1533@munch_fields($($rest)*),1534@acc($($acc)* $field: ::core::panic!(),),1535);1536};1537(make_initializer:1538@slot($slot:ident),1539@type_name($t:path),1540@munch_fields($field:ident $(: $val:expr)?, $($rest:tt)*),1541@acc($($acc:tt)*),1542) => {1543$crate::__init_internal!(make_initializer:1544@slot($slot),1545@type_name($t),1546@munch_fields($($rest)*),1547@acc($($acc)* $field: ::core::panic!(),),1548);1549};1550}15511552#[doc(hidden)]1553#[macro_export]1554macro_rules! __derive_zeroable {1555(parse_input:1556@sig(1557$(#[$($struct_attr:tt)*])*1558$vis:vis struct $name:ident1559$(where $($whr:tt)*)?1560),1561@impl_generics($($impl_generics:tt)*),1562@ty_generics($($ty_generics:tt)*),1563@body({1564$(1565$(#[$($field_attr:tt)*])*1566$field_vis:vis $field:ident : $field_ty:ty1567),* $(,)?1568}),1569) => {1570// SAFETY: Every field type implements `Zeroable` and padding bytes may be zero.1571#[automatically_derived]1572unsafe impl<$($impl_generics)*> $crate::Zeroable for $name<$($ty_generics)*>1573where1574$($($whr)*)?1575{}1576const _: () = {1577fn assert_zeroable<T: ?::core::marker::Sized + $crate::Zeroable>() {}1578fn ensure_zeroable<$($impl_generics)*>()1579where $($($whr)*)?1580{1581$(assert_zeroable::<$field_ty>();)*1582}1583};1584};1585(parse_input:1586@sig(1587$(#[$($struct_attr:tt)*])*1588$vis:vis union $name:ident1589$(where $($whr:tt)*)?1590),1591@impl_generics($($impl_generics:tt)*),1592@ty_generics($($ty_generics:tt)*),1593@body({1594$(1595$(#[$($field_attr:tt)*])*1596$field_vis:vis $field:ident : $field_ty:ty1597),* $(,)?1598}),1599) => {1600// SAFETY: Every field type implements `Zeroable` and padding bytes may be zero.1601#[automatically_derived]1602unsafe impl<$($impl_generics)*> $crate::Zeroable for $name<$($ty_generics)*>1603where1604$($($whr)*)?1605{}1606const _: () = {1607fn assert_zeroable<T: ?::core::marker::Sized + $crate::Zeroable>() {}1608fn ensure_zeroable<$($impl_generics)*>()1609where $($($whr)*)?1610{1611$(assert_zeroable::<$field_ty>();)*1612}1613};1614};1615}16161617#[doc(hidden)]1618#[macro_export]1619macro_rules! __maybe_derive_zeroable {1620(parse_input:1621@sig(1622$(#[$($struct_attr:tt)*])*1623$vis:vis struct $name:ident1624$(where $($whr:tt)*)?1625),1626@impl_generics($($impl_generics:tt)*),1627@ty_generics($($ty_generics:tt)*),1628@body({1629$(1630$(#[$($field_attr:tt)*])*1631$field_vis:vis $field:ident : $field_ty:ty1632),* $(,)?1633}),1634) => {1635// SAFETY: Every field type implements `Zeroable` and padding bytes may be zero.1636#[automatically_derived]1637unsafe impl<$($impl_generics)*> $crate::Zeroable for $name<$($ty_generics)*>1638where1639$(1640// the `for<'__dummy>` HRTB makes this not error without the `trivial_bounds`1641// feature <https://github.com/rust-lang/rust/issues/48214#issuecomment-2557829956>.1642$field_ty: for<'__dummy> $crate::Zeroable,1643)*1644$($($whr)*)?1645{}1646};1647(parse_input:1648@sig(1649$(#[$($struct_attr:tt)*])*1650$vis:vis union $name:ident1651$(where $($whr:tt)*)?1652),1653@impl_generics($($impl_generics:tt)*),1654@ty_generics($($ty_generics:tt)*),1655@body({1656$(1657$(#[$($field_attr:tt)*])*1658$field_vis:vis $field:ident : $field_ty:ty1659),* $(,)?1660}),1661) => {1662// SAFETY: Every field type implements `Zeroable` and padding bytes may be zero.1663#[automatically_derived]1664unsafe impl<$($impl_generics)*> $crate::Zeroable for $name<$($ty_generics)*>1665where1666$(1667// the `for<'__dummy>` HRTB makes this not error without the `trivial_bounds`1668// feature <https://github.com/rust-lang/rust/issues/48214#issuecomment-2557829956>.1669$field_ty: for<'__dummy> $crate::Zeroable,1670)*1671$($($whr)*)?1672{}1673};1674}167516761677