diff --git a/Makefile b/Makefile index 11539c3fd405..b86c0d7ed0e5 100644 --- a/Makefile +++ b/Makefile @@ -475,6 +475,10 @@ KBUILD_USERLDFLAGS := $(USERLDFLAGS) # These flags apply to all Rust code in the tree, including the kernel and # host programs. +# +# `-Aclippy::unwrap_or_default`: the lint is buggy [1] and ignores our +# MSRV. It can trigger depending on the optimization level. +# [1] https://github.com/rust-lang/rust-clippy/issues/17379 export rust_common_flags := --edition=2021 \ -Zbinary_dep_depinfo=y \ -Astable_features \ @@ -503,6 +507,7 @@ export rust_common_flags := --edition=2021 \ -Aclippy::uninlined_format_args \ -Wclippy::unnecessary_safety_comment \ -Wclippy::unnecessary_safety_doc \ + -Aclippy::unwrap_or_default \ -Wrustdoc::missing_crate_level_docs \ -Wrustdoc::unescaped_backticks diff --git a/init/Kconfig b/init/Kconfig index 5230d4879b1c..10f2013b5321 100644 --- a/init/Kconfig +++ b/init/Kconfig @@ -190,6 +190,9 @@ config RUSTC_HAS_FILE_WITH_NUL config RUSTC_HAS_FILE_AS_C_STR def_bool RUSTC_VERSION >= 109100 +config RUSTC_HAS_SUSPICIOUS_RUNTIME_SYMBOL_DEFINITIONS + def_bool RUSTC_VERSION >= 109800 + config PAHOLE_VERSION int default "$(PAHOLE_VERSION)" diff --git a/rust/Makefile b/rust/Makefile index a870d1616c71..627ed79dc6f5 100644 --- a/rust/Makefile +++ b/rust/Makefile @@ -84,11 +84,15 @@ core-flags := \ --edition=$(core-edition) \ $(call cfgs-to-flags,$(core-cfgs)) +zerocopy-cfgs := \ + no_fp_fmt_parse + zerocopy-flags := \ - --cap-lints=allow + --cap-lints=allow \ + $(call cfgs-to-flags,$(zerocopy-cfgs)) zerocopy-envs := \ - CARGO_PKG_VERSION=0.8.50 + CARGO_PKG_VERSION=0.8.54 proc_macro2-cfgs := \ feature="proc-macro" \ @@ -128,11 +132,15 @@ syn-flags := \ --extern quote \ $(call cfgs-to-flags,$(syn-cfgs)) +zerocopy_derive-cfgs := \ + zerocopy_unstable_linux + zerocopy_derive-flags := \ --cap-lints=allow \ --extern proc_macro2 \ --extern quote \ - --extern syn + --extern syn \ + $(call cfgs-to-flags,$(zerocopy_derive-cfgs)) pin_init_internal-cfgs := \ kernel USE_RUSTC_FEATURES @@ -644,9 +652,11 @@ quiet_cmd_rustc_library = $(if $(skip_clippy),RUSTC,$(RUSTC_OR_CLIPPY_QUIET)) L rust-analyzer: $(Q)MAKEFLAGS= $(srctree)/scripts/generate_rust_analyzer.py \ --cfgs='core=$(core-cfgs)' $(core-edition) \ + --cfgs='zerocopy=$(zerocopy-cfgs)' \ --cfgs='proc_macro2=$(proc_macro2-cfgs)' \ --cfgs='quote=$(quote-cfgs)' \ --cfgs='syn=$(syn-cfgs)' \ + --cfgs='zerocopy_derive=$(zerocopy_derive-cfgs)' \ --cfgs='pin_init_internal=$(pin_init_internal-cfgs)' \ --cfgs='pin_init=$(pin_init-cfgs)' \ --envs='zerocopy=$(zerocopy-envs)' \ diff --git a/rust/bindings/lib.rs b/rust/bindings/lib.rs index 854e7c471434..812f8e5a08d5 100644 --- a/rust/bindings/lib.rs +++ b/rust/bindings/lib.rs @@ -27,6 +27,10 @@ #[allow(clippy::ref_as_ptr)] #[allow(clippy::undocumented_unsafe_blocks)] #[cfg_attr(CONFIG_RUSTC_HAS_UNNECESSARY_TRANSMUTES, allow(unnecessary_transmutes))] +#[cfg_attr( + CONFIG_RUSTC_HAS_SUSPICIOUS_RUNTIME_SYMBOL_DEFINITIONS, + allow(suspicious_runtime_symbol_definitions) +)] mod bindings_raw { use pin_init::{MaybeZeroable, Zeroable}; diff --git a/rust/kernel/device.rs b/rust/kernel/device.rs index 645afc49a27d..1a38b3bbdfb7 100644 --- a/rust/kernel/device.rs +++ b/rust/kernel/device.rs @@ -708,9 +708,7 @@ macro_rules! impl_device_context_into_aref { #[macro_export] macro_rules! dev_printk { ($method:ident, $dev:expr, $($f:tt)*) => { - { - $crate::device::Device::$method($dev.as_ref(), $crate::prelude::fmt!($($f)*)) - } + $crate::device::Device::$method($dev.as_ref(), $crate::prelude::fmt!($($f)*)) } } @@ -737,7 +735,7 @@ macro_rules! dev_printk { /// ``` #[macro_export] macro_rules! dev_emerg { - ($($f:tt)*) => { $crate::dev_printk!(pr_emerg, $($f)*); } + ($($f:tt)*) => { $crate::dev_printk!(pr_emerg, $($f)*) } } /// Prints an alert-level message (level 1) prefixed with device information. @@ -763,7 +761,7 @@ macro_rules! dev_emerg { /// ``` #[macro_export] macro_rules! dev_alert { - ($($f:tt)*) => { $crate::dev_printk!(pr_alert, $($f)*); } + ($($f:tt)*) => { $crate::dev_printk!(pr_alert, $($f)*) } } /// Prints a critical-level message (level 2) prefixed with device information. @@ -789,7 +787,7 @@ macro_rules! dev_alert { /// ``` #[macro_export] macro_rules! dev_crit { - ($($f:tt)*) => { $crate::dev_printk!(pr_crit, $($f)*); } + ($($f:tt)*) => { $crate::dev_printk!(pr_crit, $($f)*) } } /// Prints an error-level message (level 3) prefixed with device information. @@ -815,7 +813,7 @@ macro_rules! dev_crit { /// ``` #[macro_export] macro_rules! dev_err { - ($($f:tt)*) => { $crate::dev_printk!(pr_err, $($f)*); } + ($($f:tt)*) => { $crate::dev_printk!(pr_err, $($f)*) } } /// Prints a warning-level message (level 4) prefixed with device information. @@ -841,7 +839,7 @@ macro_rules! dev_err { /// ``` #[macro_export] macro_rules! dev_warn { - ($($f:tt)*) => { $crate::dev_printk!(pr_warn, $($f)*); } + ($($f:tt)*) => { $crate::dev_printk!(pr_warn, $($f)*) } } /// Prints a notice-level message (level 5) prefixed with device information. @@ -867,7 +865,7 @@ macro_rules! dev_warn { /// ``` #[macro_export] macro_rules! dev_notice { - ($($f:tt)*) => { $crate::dev_printk!(pr_notice, $($f)*); } + ($($f:tt)*) => { $crate::dev_printk!(pr_notice, $($f)*) } } /// Prints an info-level message (level 6) prefixed with device information. @@ -893,7 +891,7 @@ macro_rules! dev_notice { /// ``` #[macro_export] macro_rules! dev_info { - ($($f:tt)*) => { $crate::dev_printk!(pr_info, $($f)*); } + ($($f:tt)*) => { $crate::dev_printk!(pr_info, $($f)*) } } /// Prints a debug-level message (level 7) prefixed with device information. @@ -919,5 +917,5 @@ macro_rules! dev_info { /// ``` #[macro_export] macro_rules! dev_dbg { - ($($f:tt)*) => { $crate::dev_printk!(pr_dbg, $($f)*); } + ($($f:tt)*) => { $crate::dev_printk!(pr_dbg, $($f)*) } } diff --git a/rust/kernel/time.rs b/rust/kernel/time.rs index 363e93cbb139..b8463823aed9 100644 --- a/rust/kernel/time.rs +++ b/rust/kernel/time.rs @@ -441,15 +441,22 @@ pub const fn as_nanos(self) -> i64 { /// to the value in the [`Delta`]. #[inline] pub fn as_micros_ceil(self) -> i64 { + let n = self.as_nanos(); + let n = if n >= 0 { + n.saturating_add(NSEC_PER_USEC - 1) + } else { + n + }; + #[cfg(CONFIG_64BIT)] { - self.as_nanos().saturating_add(NSEC_PER_USEC - 1) / NSEC_PER_USEC + n / NSEC_PER_USEC } #[cfg(not(CONFIG_64BIT))] // SAFETY: It is always safe to call `ktime_to_us()` with any value. unsafe { - bindings::ktime_to_us(self.as_nanos().saturating_add(NSEC_PER_USEC - 1)) + bindings::ktime_to_us(n) } } diff --git a/rust/uapi/lib.rs b/rust/uapi/lib.rs index b8a515de31ca..797ead5b5626 100644 --- a/rust/uapi/lib.rs +++ b/rust/uapi/lib.rs @@ -24,6 +24,10 @@ unsafe_op_in_unsafe_fn )] #![cfg_attr(CONFIG_RUSTC_HAS_UNNECESSARY_TRANSMUTES, allow(unnecessary_transmutes))] +#![cfg_attr( + CONFIG_RUSTC_HAS_SUSPICIOUS_RUNTIME_SYMBOL_DEFINITIONS, + allow(suspicious_runtime_symbol_definitions) +)] #![feature(cfi_encoding)] // Manual definition of blocklisted types. diff --git a/rust/zerocopy-derive/README.md b/rust/zerocopy-derive/README.md index 110f4a401778..d62c79804342 100644 --- a/rust/zerocopy-derive/README.md +++ b/rust/zerocopy-derive/README.md @@ -1,14 +1,14 @@ # `zerocopy-derive` -These source files come from the Rust `zerocopy-derive` crate, version v0.8.50 -(released 2026-05-31), hosted in the +These source files come from the Rust `zerocopy-derive` crate, version v0.8.54 +(released 2026-07-08), hosted in the repository, licensed under "BSD-2-Clause OR Apache-2.0 OR MIT" and only -modified to add the SPDX license identifiers and to remove the generation of +modified to tweak the SPDX license identifiers and to remove the generation of non-ASCII identifiers. For copyright details, please see: - https://github.com/google/zerocopy/blob/v0.8.50/README.md?plain=1 - https://github.com/google/zerocopy/blob/v0.8.50/LICENSE-BSD - https://github.com/google/zerocopy/blob/v0.8.50/LICENSE-APACHE - https://github.com/google/zerocopy/blob/v0.8.50/LICENSE-MIT + https://github.com/google/zerocopy/blob/v0.8.54/README.md?plain=1 + https://github.com/google/zerocopy/blob/v0.8.54/LICENSE-BSD + https://github.com/google/zerocopy/blob/v0.8.54/LICENSE-APACHE + https://github.com/google/zerocopy/blob/v0.8.54/LICENSE-MIT diff --git a/rust/zerocopy-derive/derive/from_bytes.rs b/rust/zerocopy-derive/derive/from_bytes.rs index d693a63b7645..66d820f6ad4c 100644 --- a/rust/zerocopy-derive/derive/from_bytes.rs +++ b/rust/zerocopy-derive/derive/from_bytes.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// use proc_macro2::{Span, TokenStream}; use syn::{ parse_quote, Data, DataEnum, DataStruct, DataUnion, Error, Expr, ExprLit, ExprUnary, Lit, UnOp, diff --git a/rust/zerocopy-derive/derive/into_bytes.rs b/rust/zerocopy-derive/derive/into_bytes.rs index ad52a6b45d28..0103a78d087f 100644 --- a/rust/zerocopy-derive/derive/into_bytes.rs +++ b/rust/zerocopy-derive/derive/into_bytes.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// use proc_macro2::{Span, TokenStream}; use quote::quote; use syn::{Data, DataEnum, DataStruct, DataUnion, Error, Type}; diff --git a/rust/zerocopy-derive/derive/known_layout.rs b/rust/zerocopy-derive/derive/known_layout.rs index fddffd167c82..d0c4cecfff15 100644 --- a/rust/zerocopy-derive/derive/known_layout.rs +++ b/rust/zerocopy-derive/derive/known_layout.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// use proc_macro2::TokenStream; use quote::quote; use syn::{parse_quote, Data, Error, Type}; @@ -87,7 +87,6 @@ fn pointer_to_metadata(ptr: *mut Self) -> }; let inner_extras = { - let leading_fields_tys = leading_fields_tys.clone(); let methods = make_methods(*trailing_field_ty); let (_, ty_generics, _) = ctx.ast.generics.split_for_impl(); diff --git a/rust/zerocopy-derive/derive/mod.rs b/rust/zerocopy-derive/derive/mod.rs index 665ba7da55a8..b3839fcf73c9 100644 --- a/rust/zerocopy-derive/derive/mod.rs +++ b/rust/zerocopy-derive/derive/mod.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// pub mod from_bytes; pub mod into_bytes; pub mod known_layout; @@ -15,8 +15,8 @@ util::{Ctx, DataExt, FieldBounds, ImplBlockBuilder, Trait}, }; -pub(crate) fn derive_immutable(ctx: &Ctx, _top_level: Trait) -> TokenStream { - match &ctx.ast.data { +pub(crate) fn derive_immutable(ctx: &Ctx, _top_level: Trait) -> Result { + Ok(match &ctx.ast.data { Data::Struct(strct) => { ImplBlockBuilder::new(ctx, strct, Trait::Immutable, FieldBounds::ALL_SELF).build() } @@ -26,7 +26,7 @@ pub(crate) fn derive_immutable(ctx: &Ctx, _top_level: Trait) -> TokenStream { Data::Union(unn) => { ImplBlockBuilder::new(ctx, unn, Trait::Immutable, FieldBounds::ALL_SELF).build() } - } + }) } pub(crate) fn derive_hash(ctx: &Ctx, _top_level: Trait) -> Result { @@ -97,16 +97,20 @@ pub(crate) fn derive_split_at(ctx: &Ctx, _top_level: Trait) -> Result {} Data::Enum(_) | Data::Union(_) => { - return Err(Error::new(Span::call_site(), "can only be applied to structs")); + return ctx + .error_or_skip(Error::new(Span::call_site(), "can only be applied to structs")); } }; if repr.get_packed().is_some() { - return Err(Error::new(Span::call_site(), "must not have #[repr(packed)] attribute")); + return ctx.error_or_skip(Error::new( + Span::call_site(), + "must not have #[repr(packed)] attribute", + )); } if !(repr.is_c() || repr.is_transparent()) { - return Err(Error::new( + return ctx.error_or_skip(Error::new( Span::call_site(), "must have #[repr(C)] or #[repr(transparent)] in order to guarantee this type's layout is splitable", )); @@ -116,7 +120,7 @@ pub(crate) fn derive_split_at(ctx: &Ctx, _top_level: Trait) -> Result) -> *mut , Apache License, Version 2.0 @@ -129,6 +129,40 @@ fn into_ts(self) -> proc_macro2::TokenStream { derive!(ByteEq => derive_eq => crate::derive::derive_eq); derive!(SplitAt => derive_split_at => crate::derive::derive_split_at); +#[cfg_attr(not(zerocopy_unstable_linux), doc(hidden))] +#[proc_macro_derive(most_traits, attributes(zerocopy))] +pub fn most_traits(ts: proc_macro::TokenStream) -> proc_macro::TokenStream { + let ast = syn::parse_macro_input!(ts as DeriveInput); + let ctx = match Ctx::try_from_derive_input(ast) { + Ok(ctx) => ctx, + Err(e) => return e.into_compile_error().into(), + } + .skip_on_error(); + + // top-level traits for which to attempt a derive + let derives: [(fn(&Ctx, Trait) -> _, _); 6] = [ + (crate::derive::known_layout::derive, Trait::KnownLayout), + (crate::derive::derive_immutable, Trait::Immutable), + (crate::derive::from_bytes::derive_from_bytes, Trait::FromBytes), + (crate::derive::into_bytes::derive_into_bytes, Trait::IntoBytes), + (crate::derive::derive_split_at, Trait::SplitAt), + (crate::derive::unaligned::derive_unaligned, Trait::Unaligned), + ]; + + let mut tokens = proc_macro2::TokenStream::new(); + for (derive, t) in derives { + tokens.extend(derive(&ctx, t)) + } + + // We wrap in `const_block` as a backstop in case any derive fails + // to wrap its output in `const_block` (and thus fails to annotate) + // with the full set of `#[allow(...)]` attributes). + let ts = const_block([Some(tokens)]); + #[cfg(test)] + crate::util::testutil::check_hygiene(ts.clone()); + ts.into() +} + /// Deprecated: prefer [`FromZeros`] instead. #[deprecated(since = "0.8.0", note = "`FromZeroes` was renamed to `FromZeros`")] #[doc(hidden)] diff --git a/rust/zerocopy-derive/repr.rs b/rust/zerocopy-derive/repr.rs index 74fd376d9fda..1525e94302d1 100644 --- a/rust/zerocopy-derive/repr.rs +++ b/rust/zerocopy-derive/repr.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// // Copyright 2019 The Fuchsia Authors // // Licensed under a BSD-style license , Apache License, Version 2.0 diff --git a/rust/zerocopy-derive/util.rs b/rust/zerocopy-derive/util.rs index 5ba5228e2a44..5c5e9d3bdcb8 100644 --- a/rust/zerocopy-derive/util.rs +++ b/rust/zerocopy-derive/util.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// // Copyright 2019 The Fuchsia Authors // // Licensed under a BSD-style license , Apache License, Version 2.0 @@ -98,6 +98,11 @@ pub(crate) fn with_input(&self, input: &DeriveInput) -> Self { } } + pub(crate) fn skip_on_error(mut self) -> Self { + self.skip_on_error = true; + self + } + pub(crate) fn core_path(&self) -> TokenStream { let zerocopy_crate = &self.zerocopy_crate; quote!(#zerocopy_crate::util::macro_util::core_reexport) @@ -106,20 +111,21 @@ pub(crate) fn core_path(&self) -> TokenStream { pub(crate) fn cfg_compile_error(&self) -> TokenStream { // By checking both during the compilation of the proc macro *and* in // the generated code, we ensure that `--cfg - // zerocopy_unstable_derive_on_error` need only be passed *either* when + // zerocopy_unstable_linux` need only be passed *either* when // compiling this crate *or* when compiling the user's crate. The former // is preferable, but in some situations (such as when cross-compiling // using `cargo build --target`), it doesn't get propagated to this // crate's build by default. - if cfg!(zerocopy_unstable_derive_on_error) { + if cfg!(zerocopy_unstable_linux) { quote!() } else if let Some(span) = self.on_error_span { let core = self.core_path(); - let error_message = "`on_error` is experimental; pass '--cfg zerocopy_unstable_derive_on_error' to enable"; + let error_message = + "`on_error` is experimental; pass '--cfg zerocopy_unstable_linux' to enable"; quote::quote_spanned! {span=> #[allow(unused_attributes, unexpected_cfgs)] const _: () = { - #[cfg(not(zerocopy_unstable_derive_on_error))] + #[cfg(not(zerocopy_unstable_linux))] #core::compile_error!(#error_message); }; } @@ -612,6 +618,20 @@ fn bound_tt(ty: &Type, traits: impl Iterator, ctx: &Ctx) -> WhereP } }; + let zerocopy_bounds = + field_type_bounds + .into_iter() + .chain(padding_check_bound) + .chain(self_bounds) + .map(|bound| { + if self.ctx.skip_on_error { + parse_quote!(for<'zc> #bound) + } else { + bound.clone() + } + }) + .collect::>(); + let bounds = self .ctx .ast @@ -621,9 +641,7 @@ fn bound_tt(ty: &Type, traits: impl Iterator, ctx: &Ctx) -> WhereP .map(|where_clause| where_clause.predicates.iter()) .into_iter() .flatten() - .chain(field_type_bounds.iter()) - .chain(padding_check_bound.iter()) - .chain(self_bounds.iter()); + .chain(zerocopy_bounds.iter()); // The parameters with trait bounds, but without type defaults. let mut params: Vec<_> = self diff --git a/rust/zerocopy/README.md b/rust/zerocopy/README.md index 99e6cad0e26c..3d11a6502cf0 100644 --- a/rust/zerocopy/README.md +++ b/rust/zerocopy/README.md @@ -1,14 +1,13 @@ # `zerocopy` -These source files come from the Rust `zerocopy` crate, version v0.8.50 -(released 2026-05-31), hosted in the +These source files come from the Rust `zerocopy` crate, version v0.8.54 +(released 2026-07-08), hosted in the repository, licensed under "BSD-2-Clause OR Apache-2.0 OR MIT" and only -modified to add the SPDX license identifiers and to remove `Display` -for `f32` and `f64`. +modified to tweak the SPDX license identifiers. For copyright details, please see: - https://github.com/google/zerocopy/blob/v0.8.50/README.md?plain=1 - https://github.com/google/zerocopy/blob/v0.8.50/LICENSE-BSD - https://github.com/google/zerocopy/blob/v0.8.50/LICENSE-APACHE - https://github.com/google/zerocopy/blob/v0.8.50/LICENSE-MIT + https://github.com/google/zerocopy/blob/v0.8.54/README.md?plain=1 + https://github.com/google/zerocopy/blob/v0.8.54/LICENSE-BSD + https://github.com/google/zerocopy/blob/v0.8.54/LICENSE-APACHE + https://github.com/google/zerocopy/blob/v0.8.54/LICENSE-MIT diff --git a/rust/zerocopy/rustdoc/style.css b/rust/zerocopy/rustdoc/style.css index 414348964af2..d2d55ad2e689 100644 --- a/rust/zerocopy/rustdoc/style.css +++ b/rust/zerocopy/rustdoc/style.css @@ -1,5 +1,4 @@ /* SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT */ - /* Copyright 2026 The Fuchsia Authors diff --git a/rust/zerocopy/src/byte_slice.rs b/rust/zerocopy/src/byte_slice.rs index a5ded4a18b39..b7f85098dbc4 100644 --- a/rust/zerocopy/src/byte_slice.rs +++ b/rust/zerocopy/src/byte_slice.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// // Copyright 2024 The Fuchsia Authors // // Licensed under a BSD-style license , Apache License, Version 2.0 diff --git a/rust/zerocopy/src/byteorder.rs b/rust/zerocopy/src/byteorder.rs index 8f70048f1eb0..c761d5728320 100644 --- a/rust/zerocopy/src/byteorder.rs +++ b/rust/zerocopy/src/byteorder.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// // Copyright 2019 The Fuchsia Authors // // Licensed under a BSD-style license , Apache License, Version 2.0 @@ -100,6 +100,7 @@ impl Sealed for super::LittleEndian {} #[allow(missing_copy_implementations, missing_debug_implementations)] #[doc(hidden)] +#[derive(PartialEq)] pub enum Order { BigEndian, LittleEndian, @@ -164,6 +165,42 @@ fn fmt(&self, _: &mut Formatter<'_>) -> fmt::Result { /// A type alias for [`LittleEndian`]. pub type LE = LittleEndian; +macro_rules! impl_dbg_trait { + ($name:ident, $native:ident) => { + impl Debug for $name { + #[inline] + fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result { + // This results in a format like "U16(42)". + f.debug_tuple(stringify!($name)).field(&self.get()).finish() + } + } + }; +} + +macro_rules! impl_dbg_traits { + ($name:ident, $native:ident, "floating point number") => { + #[cfg(not(no_fp_fmt_parse))] + impl_dbg_trait!($name, $native); + + #[cfg(no_fp_fmt_parse)] + impl Debug for $name { + #[inline] + fn fmt(&self, _f: &mut Formatter<'_>) -> fmt::Result { + panic!("floating point support is turned off"); + } + } + }; + ($name:ident, $native:ident, "unsigned integer") => { + impl_dbg_traits!($name, $native, @all_types); + }; + ($name:ident, $native:ident, "signed integer") => { + impl_dbg_traits!($name, $native, @all_types); + }; + ($name:ident, $native:ident, @all_types) => { + impl_dbg_trait!($name, $native); + }; +} + macro_rules! impl_fmt_trait { ($name:ident, $native:ident, $trait:ident) => { impl $trait for $name { @@ -177,6 +214,8 @@ fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result { macro_rules! impl_fmt_traits { ($name:ident, $native:ident, "floating point number") => { + #[cfg(not(no_fp_fmt_parse))] + impl_fmt_trait!($name, $native, Display); }; ($name:ident, $native:ident, "unsigned integer") => { impl_fmt_traits!($name, $native, @all_types); @@ -687,16 +726,9 @@ fn eq(&self, other: &$native) -> bool { } } + impl_dbg_traits!($name, $native, $number_kind); impl_fmt_traits!($name, $native, $number_kind); impl_ops_traits!($name, $native, $number_kind); - - impl Debug for $name { - #[inline] - fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result { - // This results in a format like "U16(42)". - f.debug_tuple(stringify!($name)).field(&self.get()).finish() - } - } }; } diff --git a/rust/zerocopy/src/deprecated.rs b/rust/zerocopy/src/deprecated.rs index 24bafbf9adeb..59ddd35c77c6 100644 --- a/rust/zerocopy/src/deprecated.rs +++ b/rust/zerocopy/src/deprecated.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// // Copyright 2024 The Fuchsia Authors // // Licensed under the 2-Clause BSD License Option> { Some(match *self { SizeInfo::Sized { size } => SizeInfo::Sized { size }, diff --git a/rust/zerocopy/src/lib.rs b/rust/zerocopy/src/lib.rs index 3302d67602ab..572f0563fe2f 100644 --- a/rust/zerocopy/src/lib.rs +++ b/rust/zerocopy/src/lib.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// // Copyright 2018 The Fuchsia Authors // // Licensed under the 2-Clause BSD License README.md +// (cd .. && cargo -q run --manifest-path tools/Cargo.toml -p generate-readme) > README.md //! ***Fast, safe, compile error. Pick two.*** @@ -174,7 +174,7 @@ //! //! [Miri]: https://github.com/rust-lang/miri //! [Kani]: https://github.com/model-checking/kani -//! [soundness policy]: https://github.com/google/zerocopy/blob/main/POLICIES.md#soundness +//! [soundness policy]: https://github.com/google/zerocopy/blob/main/zerocopy/POLICIES.md#soundness //! //! # Relationship to Project Safe Transmute //! @@ -203,7 +203,7 @@ //! //! See our [MSRV policy]. //! -//! [MSRV policy]: https://github.com/google/zerocopy/blob/main/POLICIES.md#msrv +//! [MSRV policy]: https://github.com/google/zerocopy/blob/main/zerocopy/POLICIES.md#msrv //! //! # Changelog //! @@ -435,6 +435,8 @@ WARNING }; +#[cfg(all(any(feature = "derive", test), zerocopy_unstable_linux))] +pub use zerocopy_derive::most_traits; /// Implements [`KnownLayout`]. /// /// This derive analyzes various aspects of a type's layout that are needed for @@ -2832,7 +2834,7 @@ fn try_ref_from_suffix_with_elems( /// ``` /// /// [`try_mut_from_bytes`]: TryFromBytes::try_mut_from_bytes - /// + /// #[doc = codegen_header!("h5", "try_mut_from_bytes_with_elems")] /// /// See [`TryFromBytes::try_ref_from_bytes_with_elems`](#method.try_ref_from_bytes_with_elems.codegen). diff --git a/rust/zerocopy/src/macros.rs b/rust/zerocopy/src/macros.rs index b801d86a8fa6..ec67c03a44fc 100644 --- a/rust/zerocopy/src/macros.rs +++ b/rust/zerocopy/src/macros.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// // Copyright 2024 The Fuchsia Authors // // Licensed under the 2-Clause BSD License , Apache License, Version 2.0 diff --git a/rust/zerocopy/src/pointer/invariant.rs b/rust/zerocopy/src/pointer/invariant.rs index 1802d23563db..7ff0d43dad5e 100644 --- a/rust/zerocopy/src/pointer/invariant.rs +++ b/rust/zerocopy/src/pointer/invariant.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// // Copyright 2024 The Fuchsia Authors // // Licensed under a BSD-style license , Apache License, Version 2.0 diff --git a/rust/zerocopy/src/pointer/mod.rs b/rust/zerocopy/src/pointer/mod.rs index 3461f7f5ca80..d6eacc52febe 100644 --- a/rust/zerocopy/src/pointer/mod.rs +++ b/rust/zerocopy/src/pointer/mod.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// // Copyright 2023 The Fuchsia Authors // // Licensed under a BSD-style license , Apache License, Version 2.0 diff --git a/rust/zerocopy/src/pointer/ptr.rs b/rust/zerocopy/src/pointer/ptr.rs index b7c4ea56d2b2..7213f6f4a04e 100644 --- a/rust/zerocopy/src/pointer/ptr.rs +++ b/rust/zerocopy/src/pointer/ptr.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// // Copyright 2023 The Fuchsia Authors // // Licensed under a BSD-style license , Apache License, Version 2.0 diff --git a/rust/zerocopy/src/pointer/transmute.rs b/rust/zerocopy/src/pointer/transmute.rs index a534984b70d3..ef9836698203 100644 --- a/rust/zerocopy/src/pointer/transmute.rs +++ b/rust/zerocopy/src/pointer/transmute.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// // Copyright 2025 The Fuchsia Authors // // Licensed under a BSD-style license , Apache License, Version 2.0 diff --git a/rust/zerocopy/src/ref.rs b/rust/zerocopy/src/ref.rs index 860066d75196..e49f2a887ffa 100644 --- a/rust/zerocopy/src/ref.rs +++ b/rust/zerocopy/src/ref.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// // Copyright 2024 The Fuchsia Authors // // Licensed under the 2-Clause BSD License , Apache License, Version 2.0 diff --git a/rust/zerocopy/src/util/macros.rs b/rust/zerocopy/src/util/macros.rs index 43e4fd64ee15..7e63e3a54fc4 100644 --- a/rust/zerocopy/src/util/macros.rs +++ b/rust/zerocopy/src/util/macros.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// // Copyright 2023 The Fuchsia Authors // // Licensed under a BSD-style license , Apache License, Version 2.0 diff --git a/rust/zerocopy/src/util/mod.rs b/rust/zerocopy/src/util/mod.rs index d6d4c6c2fcd9..02fd4ed62741 100644 --- a/rust/zerocopy/src/util/mod.rs +++ b/rust/zerocopy/src/util/mod.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// // Copyright 2023 The Fuchsia Authors // // Licensed under a BSD-style license , Apache License, Version 2.0 @@ -150,6 +150,8 @@ pub(crate) fn validate_aligned_to(t: T) -> Result<(), Alignment // Ensures that we add the minimum required padding. kani::ensures(|&p| p < align.get()), )] +#[cfg_attr(not(zerocopy_inline_always), inline)] +#[cfg_attr(zerocopy_inline_always, inline(always))] pub(crate) const fn padding_needed_for(len: usize, align: NonZeroUsize) -> usize { #[cfg(kani)] #[kani::proof_for_contract(padding_needed_for)] @@ -251,6 +253,8 @@ fn proof() { n & mask } +#[cfg_attr(not(zerocopy_inline_always), inline)] +#[cfg_attr(zerocopy_inline_always, inline(always))] pub(crate) const fn max(a: NonZeroUsize, b: NonZeroUsize) -> NonZeroUsize { if a.get() < b.get() { b @@ -259,6 +263,8 @@ pub(crate) const fn max(a: NonZeroUsize, b: NonZeroUsize) -> NonZeroUsize { } } +#[cfg_attr(not(zerocopy_inline_always), inline)] +#[cfg_attr(zerocopy_inline_always, inline(always))] pub(crate) const fn min(a: NonZeroUsize, b: NonZeroUsize) -> NonZeroUsize { if a.get() > b.get() { b diff --git a/rust/zerocopy/src/wrappers.rs b/rust/zerocopy/src/wrappers.rs index 266aec25fa58..1a8cf2b41d55 100644 --- a/rust/zerocopy/src/wrappers.rs +++ b/rust/zerocopy/src/wrappers.rs @@ -1,5 +1,5 @@ // SPDX-License-Identifier: (BSD-2-Clause OR Apache-2.0) OR MIT - +// // Copyright 2023 The Fuchsia Authors // // Licensed under a BSD-style license , Apache License, Version 2.0 diff --git a/tools/objtool/check.c b/tools/objtool/check.c index 10b18cf9c360..f03dd59e7fca 100644 --- a/tools/objtool/check.c +++ b/tools/objtool/check.c @@ -206,6 +206,7 @@ static bool is_rust_noreturn(const struct symbol *func) str_ends_with(func->name, "_4core9panicking18panic_nounwind_fmt") || str_ends_with(func->name, "_4core9panicking19assert_failed_inner") || str_ends_with(func->name, "_4core9panicking30panic_null_pointer_dereference") || + str_ends_with(func->name, "_4core9panicking32panic_null_reference_constructed") || str_ends_with(func->name, "_4core9panicking36panic_misaligned_pointer_dereference") || str_ends_with(func->name, "_7___rustc17rust_begin_unwind") || strstr(func->name, "_4core9panicking13assert_failed") ||