diff --git a/library/core/src/num/nonzero.rs b/library/core/src/num/nonzero.rs
index 6b113d57f25..f7098bcf6e9 100644
--- a/library/core/src/num/nonzero.rs
+++ b/library/core/src/num/nonzero.rs
@@ -26,167 +26,167 @@ macro_rules! nonzero_integer {
(
#[$stability:meta] #[$const_new_unchecked_stability:meta] $Ty:ident($Int:ty);
) => {
- /// An integer that is known not to equal zero.
+ /// An integer that is known not to equal zero.
+ ///
+ /// This enables some memory layout optimization.
+ #[doc = concat!("For example, `Option<", stringify!($Ty), ">` is the same size as `", stringify!($Int), "`:")]
+ ///
+ /// ```rust
+ /// use std::mem::size_of;
+ #[doc = concat!("assert_eq!(size_of::>(), size_of::<", stringify!($Int), ">());")]
+ /// ```
+ ///
+ /// # Layout
+ ///
+ #[doc = concat!("`", stringify!($Ty), "` is guaranteed to have the same layout and bit validity as `", stringify!($Int), "`")]
+ /// with the exception that `0` is not a valid instance.
+ #[doc = concat!("`Option<", stringify!($Ty), ">` is guaranteed to be compatible with `", stringify!($Int), "`,")]
+ /// including in FFI.
+ ///
+ /// Thanks to the [null pointer optimization],
+ #[doc = concat!("`", stringify!($Ty), "` and `Option<", stringify!($Ty), ">`")]
+ /// are guaranteed to have the same size and alignment:
+ ///
+ /// ```
+ /// # use std::mem::{size_of, align_of};
+ #[doc = concat!("use std::num::", stringify!($Ty), ";")]
+ ///
+ #[doc = concat!("assert_eq!(size_of::<", stringify!($Ty), ">(), size_of:: >());")]
+ #[doc = concat!("assert_eq!(align_of::<", stringify!($Ty), ">(), align_of:: >());")]
+ /// ```
+ ///
+ /// [null pointer optimization]: crate::option#representation
+ #[$stability]
+ #[derive(Copy, Clone, Eq, PartialEq, Ord, PartialOrd, Hash)]
+ #[repr(transparent)]
+ #[rustc_layout_scalar_valid_range_start(1)]
+ #[rustc_nonnull_optimization_guaranteed]
+ #[rustc_diagnostic_item = stringify!($Ty)]
+ pub struct $Ty($Int);
+
+ impl $Ty {
+ /// Creates a non-zero without checking whether the value is non-zero.
+ /// This results in undefined behaviour if the value is zero.
///
- /// This enables some memory layout optimization.
- #[doc = concat!("For example, `Option<", stringify!($Ty), ">` is the same size as `", stringify!($Int), "`:")]
+ /// # Safety
///
- /// ```rust
- /// use std::mem::size_of;
- #[doc = concat!("assert_eq!(size_of:: >(), size_of::<", stringify!($Int), ">());")]
- /// ```
- ///
- /// # Layout
- ///
- #[doc = concat!("`", stringify!($Ty), "` is guaranteed to have the same layout and bit validity as `", stringify!($Int), "`")]
- /// with the exception that `0` is not a valid instance.
- #[doc = concat!("`Option<", stringify!($Ty), ">` is guaranteed to be compatible with `", stringify!($Int), "`,")]
- /// including in FFI.
- ///
- /// Thanks to the [null pointer optimization],
- #[doc = concat!("`", stringify!($Ty), "` and `Option<", stringify!($Ty), ">`")]
- /// are guaranteed to have the same size and alignment:
- ///
- /// ```
- /// # use std::mem::{size_of, align_of};
- #[doc = concat!("use std::num::", stringify!($Ty), ";")]
- ///
- #[doc = concat!("assert_eq!(size_of::<", stringify!($Ty), ">(), size_of:: >());")]
- #[doc = concat!("assert_eq!(align_of::<", stringify!($Ty), ">(), align_of:: >());")]
- /// ```
- ///
- /// [null pointer optimization]: crate::option#representation
+ /// The value must not be zero.
#[$stability]
- #[derive(Copy, Clone, Eq, PartialEq, Ord, PartialOrd, Hash)]
- #[repr(transparent)]
- #[rustc_layout_scalar_valid_range_start(1)]
- #[rustc_nonnull_optimization_guaranteed]
- #[rustc_diagnostic_item = stringify!($Ty)]
- pub struct $Ty($Int);
-
- impl $Ty {
- /// Creates a non-zero without checking whether the value is non-zero.
- /// This results in undefined behaviour if the value is zero.
- ///
- /// # Safety
- ///
- /// The value must not be zero.
- #[$stability]
- #[$const_new_unchecked_stability]
- #[must_use]
- #[inline]
- pub const unsafe fn new_unchecked(n: $Int) -> Self {
- crate::panic::debug_assert_nounwind!(
- n != 0,
- concat!(stringify!($Ty), "::new_unchecked requires a non-zero argument")
- );
- // SAFETY: this is guaranteed to be safe by the caller.
- unsafe {
- Self(n)
- }
- }
-
- /// Creates a non-zero if the given value is not zero.
- #[$stability]
- #[rustc_const_stable(feature = "const_nonzero_int_methods", since = "1.47.0")]
- #[must_use]
- #[inline]
- pub const fn new(n: $Int) -> Option {
- if n != 0 {
- // SAFETY: we just checked that there's no `0`
- Some(unsafe { Self(n) })
- } else {
- None
- }
- }
-
- /// Returns the value as a primitive type.
- #[$stability]
- #[inline]
- #[rustc_const_stable(feature = "const_nonzero_get", since = "1.34.0")]
- pub const fn get(self) -> $Int {
- // FIXME: Remove this after LLVM supports `!range` metadata for function
- // arguments https://github.com/llvm/llvm-project/issues/76628
- //
- // Rustc can set range metadata only if it loads `self` from
- // memory somewhere. If the value of `self` was from by-value argument
- // of some not-inlined function, LLVM don't have range metadata
- // to understand that the value cannot be zero.
-
- // SAFETY: It is an invariant of this type.
- unsafe {
- intrinsics::assume(self.0 != 0);
- }
- self.0
- }
-
- }
-
- #[stable(feature = "from_nonzero", since = "1.31.0")]
- impl From<$Ty> for $Int {
- #[doc = concat!("Converts a `", stringify!($Ty), "` into an `", stringify!($Int), "`")]
- #[inline]
- fn from(nonzero: $Ty) -> Self {
- // Call nonzero to keep information range information
- // from get method.
- nonzero.get()
+ #[$const_new_unchecked_stability]
+ #[must_use]
+ #[inline]
+ pub const unsafe fn new_unchecked(n: $Int) -> Self {
+ crate::panic::debug_assert_nounwind!(
+ n != 0,
+ concat!(stringify!($Ty), "::new_unchecked requires a non-zero argument")
+ );
+ // SAFETY: this is guaranteed to be safe by the caller.
+ unsafe {
+ Self(n)
}
}
- #[stable(feature = "nonzero_bitor", since = "1.45.0")]
- impl BitOr for $Ty {
- type Output = Self;
- #[inline]
- fn bitor(self, rhs: Self) -> Self::Output {
- // SAFETY: since `self` and `rhs` are both nonzero, the
- // result of the bitwise-or will be nonzero.
- unsafe { $Ty::new_unchecked(self.get() | rhs.get()) }
+ /// Creates a non-zero if the given value is not zero.
+ #[$stability]
+ #[rustc_const_stable(feature = "const_nonzero_int_methods", since = "1.47.0")]
+ #[must_use]
+ #[inline]
+ pub const fn new(n: $Int) -> Option {
+ if n != 0 {
+ // SAFETY: we just checked that there's no `0`
+ Some(unsafe { Self(n) })
+ } else {
+ None
}
}
- #[stable(feature = "nonzero_bitor", since = "1.45.0")]
- impl BitOr<$Int> for $Ty {
- type Output = Self;
- #[inline]
- fn bitor(self, rhs: $Int) -> Self::Output {
- // SAFETY: since `self` is nonzero, the result of the
- // bitwise-or will be nonzero regardless of the value of
- // `rhs`.
- unsafe { $Ty::new_unchecked(self.get() | rhs) }
+ /// Returns the value as a primitive type.
+ #[$stability]
+ #[inline]
+ #[rustc_const_stable(feature = "const_nonzero_get", since = "1.34.0")]
+ pub const fn get(self) -> $Int {
+ // FIXME: Remove this after LLVM supports `!range` metadata for function
+ // arguments https://github.com/llvm/llvm-project/issues/76628
+ //
+ // Rustc can set range metadata only if it loads `self` from
+ // memory somewhere. If the value of `self` was from by-value argument
+ // of some not-inlined function, LLVM don't have range metadata
+ // to understand that the value cannot be zero.
+
+ // SAFETY: It is an invariant of this type.
+ unsafe {
+ intrinsics::assume(self.0 != 0);
}
+ self.0
}
- #[stable(feature = "nonzero_bitor", since = "1.45.0")]
- impl BitOr<$Ty> for $Int {
- type Output = $Ty;
- #[inline]
- fn bitor(self, rhs: $Ty) -> Self::Output {
- // SAFETY: since `rhs` is nonzero, the result of the
- // bitwise-or will be nonzero regardless of the value of
- // `self`.
- unsafe { $Ty::new_unchecked(self | rhs.get()) }
- }
- }
+ }
- #[stable(feature = "nonzero_bitor", since = "1.45.0")]
- impl BitOrAssign for $Ty {
- #[inline]
- fn bitor_assign(&mut self, rhs: Self) {
- *self = *self | rhs;
- }
+ #[stable(feature = "from_nonzero", since = "1.31.0")]
+ impl From<$Ty> for $Int {
+ #[doc = concat!("Converts a `", stringify!($Ty), "` into an `", stringify!($Int), "`")]
+ #[inline]
+ fn from(nonzero: $Ty) -> Self {
+ // Call nonzero to keep information range information
+ // from get method.
+ nonzero.get()
}
+ }
- #[stable(feature = "nonzero_bitor", since = "1.45.0")]
- impl BitOrAssign<$Int> for $Ty {
- #[inline]
- fn bitor_assign(&mut self, rhs: $Int) {
- *self = *self | rhs;
- }
+ #[stable(feature = "nonzero_bitor", since = "1.45.0")]
+ impl BitOr for $Ty {
+ type Output = Self;
+ #[inline]
+ fn bitor(self, rhs: Self) -> Self::Output {
+ // SAFETY: since `self` and `rhs` are both nonzero, the
+ // result of the bitwise-or will be nonzero.
+ unsafe { $Ty::new_unchecked(self.get() | rhs.get()) }
}
+ }
- impl_nonzero_fmt! {
- #[$stability] (Debug, Display, Binary, Octal, LowerHex, UpperHex) for $Ty
+ #[stable(feature = "nonzero_bitor", since = "1.45.0")]
+ impl BitOr<$Int> for $Ty {
+ type Output = Self;
+ #[inline]
+ fn bitor(self, rhs: $Int) -> Self::Output {
+ // SAFETY: since `self` is nonzero, the result of the
+ // bitwise-or will be nonzero regardless of the value of
+ // `rhs`.
+ unsafe { $Ty::new_unchecked(self.get() | rhs) }
}
+ }
+
+ #[stable(feature = "nonzero_bitor", since = "1.45.0")]
+ impl BitOr<$Ty> for $Int {
+ type Output = $Ty;
+ #[inline]
+ fn bitor(self, rhs: $Ty) -> Self::Output {
+ // SAFETY: since `rhs` is nonzero, the result of the
+ // bitwise-or will be nonzero regardless of the value of
+ // `self`.
+ unsafe { $Ty::new_unchecked(self | rhs.get()) }
+ }
+ }
+
+ #[stable(feature = "nonzero_bitor", since = "1.45.0")]
+ impl BitOrAssign for $Ty {
+ #[inline]
+ fn bitor_assign(&mut self, rhs: Self) {
+ *self = *self | rhs;
+ }
+ }
+
+ #[stable(feature = "nonzero_bitor", since = "1.45.0")]
+ impl BitOrAssign<$Int> for $Ty {
+ #[inline]
+ fn bitor_assign(&mut self, rhs: $Int) {
+ *self = *self | rhs;
+ }
+ }
+
+ impl_nonzero_fmt! {
+ #[$stability] (Debug, Display, Binary, Octal, LowerHex, UpperHex) for $Ty
+ }
};
}