rust: add derive macro for Zeroable
Add a derive proc-macro for the `Zeroable` trait. The macro supports structs where every field implements the `Zeroable` trait. This way `unsafe` implementations can be avoided. The macro is split into two parts: - a proc-macro to parse generics into impl and ty generics, - a declarative macro that expands to the impl block. Suggested-by: Asahi Lina <lina@asahilina.net> Signed-off-by: Benno Lossin <benno.lossin@proton.me> Reviewed-by: Gary Guo <gary@garyguo.net> Reviewed-by: Martin Rodriguez Reboredo <yakoyoku@gmail.com> Link: https://lore.kernel.org/r/20230814084602.25699-4-benno.lossin@proton.me [ Added `ignore` to the `lib.rs` example and cleaned trivial nit. ] Signed-off-by: Miguel Ojeda <ojeda@kernel.org>
This commit is contained in:
committed by
Miguel Ojeda
parent
f8badd1507
commit
071cedc84e
@@ -1215,3 +1215,38 @@ macro_rules! __init_internal {
|
||||
);
|
||||
};
|
||||
}
|
||||
|
||||
#[doc(hidden)]
|
||||
#[macro_export]
|
||||
macro_rules! __derive_zeroable {
|
||||
(parse_input:
|
||||
@sig(
|
||||
$(#[$($struct_attr:tt)*])*
|
||||
$vis:vis struct $name:ident
|
||||
$(where $($whr:tt)*)?
|
||||
),
|
||||
@impl_generics($($impl_generics:tt)*),
|
||||
@ty_generics($($ty_generics:tt)*),
|
||||
@body({
|
||||
$(
|
||||
$(#[$($field_attr:tt)*])*
|
||||
$field:ident : $field_ty:ty
|
||||
),* $(,)?
|
||||
}),
|
||||
) => {
|
||||
// SAFETY: Every field type implements `Zeroable` and padding bytes may be zero.
|
||||
#[automatically_derived]
|
||||
unsafe impl<$($impl_generics)*> $crate::init::Zeroable for $name<$($ty_generics)*>
|
||||
where
|
||||
$($($whr)*)?
|
||||
{}
|
||||
const _: () = {
|
||||
fn assert_zeroable<T: ?::core::marker::Sized + $crate::init::Zeroable>() {}
|
||||
fn ensure_zeroable<$($impl_generics)*>()
|
||||
where $($($whr)*)?
|
||||
{
|
||||
$(assert_zeroable::<$field_ty>();)*
|
||||
}
|
||||
};
|
||||
};
|
||||
}
|
||||
|
||||
@@ -18,7 +18,7 @@ pub use core::pin::Pin;
|
||||
pub use alloc::{boxed::Box, vec::Vec};
|
||||
|
||||
#[doc(no_inline)]
|
||||
pub use macros::{module, pin_data, pinned_drop, vtable};
|
||||
pub use macros::{module, pin_data, pinned_drop, vtable, Zeroable};
|
||||
|
||||
pub use super::build_assert;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user