]> git.lizzy.rs Git - rust.git/blob - library/core/src/num/nonzero.rs
Rollup merge of #90202 - matthewjasper:xcrate-hygiene, r=petrochenkov
[rust.git] / library / core / src / num / nonzero.rs
1 //! Definitions of integer that is known not to equal zero.
2
3 use crate::fmt;
4 use crate::ops::{BitOr, BitOrAssign, Div, Rem};
5 use crate::str::FromStr;
6
7 use super::from_str_radix;
8 use super::{IntErrorKind, ParseIntError};
9 use crate::intrinsics;
10
11 macro_rules! impl_nonzero_fmt {
12     ( #[$stability: meta] ( $( $Trait: ident ),+ ) for $Ty: ident ) => {
13         $(
14             #[$stability]
15             impl fmt::$Trait for $Ty {
16                 #[inline]
17                 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
18                     self.get().fmt(f)
19                 }
20             }
21         )+
22     }
23 }
24
25 macro_rules! nonzero_integers {
26     ( $( #[$stability: meta] #[$const_new_unchecked_stability: meta] $Ty: ident($Int: ty); )+ ) => {
27         $(
28             /// An integer that is known not to equal zero.
29             ///
30             /// This enables some memory layout optimization.
31             #[doc = concat!("For example, `Option<", stringify!($Ty), ">` is the same size as `", stringify!($Int), "`:")]
32             ///
33             /// ```rust
34             /// use std::mem::size_of;
35             #[doc = concat!("assert_eq!(size_of::<Option<core::num::", stringify!($Ty), ">>(), size_of::<", stringify!($Int), ">());")]
36             /// ```
37             #[$stability]
38             #[derive(Copy, Clone, Eq, PartialEq, Ord, PartialOrd, Hash)]
39             #[repr(transparent)]
40             #[rustc_layout_scalar_valid_range_start(1)]
41             #[rustc_nonnull_optimization_guaranteed]
42             pub struct $Ty($Int);
43
44             impl $Ty {
45                 /// Creates a non-zero without checking whether the value is non-zero.
46                 /// This results in undefined behaviour if the value is zero.
47                 ///
48                 /// # Safety
49                 ///
50                 /// The value must not be zero.
51                 #[$stability]
52                 #[$const_new_unchecked_stability]
53                 #[must_use]
54                 #[inline]
55                 pub const unsafe fn new_unchecked(n: $Int) -> Self {
56                     // SAFETY: this is guaranteed to be safe by the caller.
57                     unsafe { Self(n) }
58                 }
59
60                 /// Creates a non-zero if the given value is not zero.
61                 #[$stability]
62                 #[rustc_const_stable(feature = "const_nonzero_int_methods", since = "1.47.0")]
63                 #[must_use]
64                 #[inline]
65                 pub const fn new(n: $Int) -> Option<Self> {
66                     if n != 0 {
67                         // SAFETY: we just checked that there's no `0`
68                         Some(unsafe { Self(n) })
69                     } else {
70                         None
71                     }
72                 }
73
74                 /// Returns the value as a primitive type.
75                 #[$stability]
76                 #[inline]
77                 #[rustc_const_stable(feature = "nonzero", since = "1.34.0")]
78                 pub const fn get(self) -> $Int {
79                     self.0
80                 }
81
82             }
83
84             #[stable(feature = "from_nonzero", since = "1.31.0")]
85             #[rustc_const_unstable(feature = "const_num_from_num", issue = "87852")]
86             impl const From<$Ty> for $Int {
87                 #[doc = concat!("Converts a `", stringify!($Ty), "` into an `", stringify!($Int), "`")]
88                 #[inline]
89                 fn from(nonzero: $Ty) -> Self {
90                     nonzero.0
91                 }
92             }
93
94             #[stable(feature = "nonzero_bitor", since = "1.45.0")]
95             #[rustc_const_unstable(feature = "const_ops", issue = "90080")]
96             impl const BitOr for $Ty {
97                 type Output = Self;
98                 #[inline]
99                 fn bitor(self, rhs: Self) -> Self::Output {
100                     // SAFETY: since `self` and `rhs` are both nonzero, the
101                     // result of the bitwise-or will be nonzero.
102                     unsafe { $Ty::new_unchecked(self.get() | rhs.get()) }
103                 }
104             }
105
106             #[stable(feature = "nonzero_bitor", since = "1.45.0")]
107             #[rustc_const_unstable(feature = "const_ops", issue = "90080")]
108             impl const BitOr<$Int> for $Ty {
109                 type Output = Self;
110                 #[inline]
111                 fn bitor(self, rhs: $Int) -> Self::Output {
112                     // SAFETY: since `self` is nonzero, the result of the
113                     // bitwise-or will be nonzero regardless of the value of
114                     // `rhs`.
115                     unsafe { $Ty::new_unchecked(self.get() | rhs) }
116                 }
117             }
118
119             #[stable(feature = "nonzero_bitor", since = "1.45.0")]
120             #[rustc_const_unstable(feature = "const_ops", issue = "90080")]
121             impl const BitOr<$Ty> for $Int {
122                 type Output = $Ty;
123                 #[inline]
124                 fn bitor(self, rhs: $Ty) -> Self::Output {
125                     // SAFETY: since `rhs` is nonzero, the result of the
126                     // bitwise-or will be nonzero regardless of the value of
127                     // `self`.
128                     unsafe { $Ty::new_unchecked(self | rhs.get()) }
129                 }
130             }
131
132             #[stable(feature = "nonzero_bitor", since = "1.45.0")]
133             #[rustc_const_unstable(feature = "const_ops", issue = "90080")]
134             impl const BitOrAssign for $Ty {
135                 #[inline]
136                 fn bitor_assign(&mut self, rhs: Self) {
137                     *self = *self | rhs;
138                 }
139             }
140
141             #[stable(feature = "nonzero_bitor", since = "1.45.0")]
142             #[rustc_const_unstable(feature = "const_ops", issue = "90080")]
143             impl const BitOrAssign<$Int> for $Ty {
144                 #[inline]
145                 fn bitor_assign(&mut self, rhs: $Int) {
146                     *self = *self | rhs;
147                 }
148             }
149
150             impl_nonzero_fmt! {
151                 #[$stability] (Debug, Display, Binary, Octal, LowerHex, UpperHex) for $Ty
152             }
153         )+
154     }
155 }
156
157 nonzero_integers! {
158     #[stable(feature = "nonzero", since = "1.28.0")] #[rustc_const_stable(feature = "nonzero", since = "1.28.0")] NonZeroU8(u8);
159     #[stable(feature = "nonzero", since = "1.28.0")] #[rustc_const_stable(feature = "nonzero", since = "1.28.0")] NonZeroU16(u16);
160     #[stable(feature = "nonzero", since = "1.28.0")] #[rustc_const_stable(feature = "nonzero", since = "1.28.0")] NonZeroU32(u32);
161     #[stable(feature = "nonzero", since = "1.28.0")] #[rustc_const_stable(feature = "nonzero", since = "1.28.0")] NonZeroU64(u64);
162     #[stable(feature = "nonzero", since = "1.28.0")] #[rustc_const_stable(feature = "nonzero", since = "1.28.0")] NonZeroU128(u128);
163     #[stable(feature = "nonzero", since = "1.28.0")] #[rustc_const_stable(feature = "nonzero", since = "1.28.0")] NonZeroUsize(usize);
164     #[stable(feature = "signed_nonzero", since = "1.34.0")] #[rustc_const_stable(feature = "signed_nonzero", since = "1.34.0")] NonZeroI8(i8);
165     #[stable(feature = "signed_nonzero", since = "1.34.0")] #[rustc_const_stable(feature = "signed_nonzero", since = "1.34.0")] NonZeroI16(i16);
166     #[stable(feature = "signed_nonzero", since = "1.34.0")] #[rustc_const_stable(feature = "signed_nonzero", since = "1.34.0")] NonZeroI32(i32);
167     #[stable(feature = "signed_nonzero", since = "1.34.0")] #[rustc_const_stable(feature = "signed_nonzero", since = "1.34.0")] NonZeroI64(i64);
168     #[stable(feature = "signed_nonzero", since = "1.34.0")] #[rustc_const_stable(feature = "signed_nonzero", since = "1.34.0")] NonZeroI128(i128);
169     #[stable(feature = "signed_nonzero", since = "1.34.0")] #[rustc_const_stable(feature = "signed_nonzero", since = "1.34.0")] NonZeroIsize(isize);
170 }
171
172 macro_rules! from_str_radix_nzint_impl {
173     ($($t:ty)*) => {$(
174         #[stable(feature = "nonzero_parse", since = "1.35.0")]
175         impl FromStr for $t {
176             type Err = ParseIntError;
177             fn from_str(src: &str) -> Result<Self, Self::Err> {
178                 Self::new(from_str_radix(src, 10)?)
179                     .ok_or(ParseIntError {
180                         kind: IntErrorKind::Zero
181                     })
182             }
183         }
184     )*}
185 }
186
187 from_str_radix_nzint_impl! { NonZeroU8 NonZeroU16 NonZeroU32 NonZeroU64 NonZeroU128 NonZeroUsize
188 NonZeroI8 NonZeroI16 NonZeroI32 NonZeroI64 NonZeroI128 NonZeroIsize }
189
190 macro_rules! nonzero_leading_trailing_zeros {
191     ( $( $Ty: ident($Uint: ty) , $LeadingTestExpr:expr ;)+ ) => {
192         $(
193             impl $Ty {
194                 /// Returns the number of leading zeros in the binary representation of `self`.
195                 ///
196                 /// On many architectures, this function can perform better than `leading_zeros()` on the underlying integer type, as special handling of zero can be avoided.
197                 ///
198                 /// # Examples
199                 ///
200                 /// Basic usage:
201                 ///
202                 /// ```
203                 #[doc = concat!("let n = std::num::", stringify!($Ty), "::new(", stringify!($LeadingTestExpr), ").unwrap();")]
204                 ///
205                 /// assert_eq!(n.leading_zeros(), 0);
206                 /// ```
207                 #[stable(feature = "nonzero_leading_trailing_zeros", since = "1.53.0")]
208                 #[rustc_const_stable(feature = "nonzero_leading_trailing_zeros", since = "1.53.0")]
209                 #[must_use = "this returns the result of the operation, \
210                               without modifying the original"]
211                 #[inline]
212                 pub const fn leading_zeros(self) -> u32 {
213                     // SAFETY: since `self` can not be zero it is safe to call ctlz_nonzero
214                     unsafe { intrinsics::ctlz_nonzero(self.0 as $Uint) as u32 }
215                 }
216
217                 /// Returns the number of trailing zeros in the binary representation
218                 /// of `self`.
219                 ///
220                 /// On many architectures, this function can perform better than `trailing_zeros()` on the underlying integer type, as special handling of zero can be avoided.
221                 ///
222                 /// # Examples
223                 ///
224                 /// Basic usage:
225                 ///
226                 /// ```
227                 #[doc = concat!("let n = std::num::", stringify!($Ty), "::new(0b0101000).unwrap();")]
228                 ///
229                 /// assert_eq!(n.trailing_zeros(), 3);
230                 /// ```
231                 #[stable(feature = "nonzero_leading_trailing_zeros", since = "1.53.0")]
232                 #[rustc_const_stable(feature = "nonzero_leading_trailing_zeros", since = "1.53.0")]
233                 #[must_use = "this returns the result of the operation, \
234                               without modifying the original"]
235                 #[inline]
236                 pub const fn trailing_zeros(self) -> u32 {
237                     // SAFETY: since `self` can not be zero it is safe to call cttz_nonzero
238                     unsafe { intrinsics::cttz_nonzero(self.0 as $Uint) as u32 }
239                 }
240
241             }
242         )+
243     }
244 }
245
246 nonzero_leading_trailing_zeros! {
247     NonZeroU8(u8), u8::MAX;
248     NonZeroU16(u16), u16::MAX;
249     NonZeroU32(u32), u32::MAX;
250     NonZeroU64(u64), u64::MAX;
251     NonZeroU128(u128), u128::MAX;
252     NonZeroUsize(usize), usize::MAX;
253     NonZeroI8(u8), -1i8;
254     NonZeroI16(u16), -1i16;
255     NonZeroI32(u32), -1i32;
256     NonZeroI64(u64), -1i64;
257     NonZeroI128(u128), -1i128;
258     NonZeroIsize(usize), -1isize;
259 }
260
261 macro_rules! nonzero_integers_div {
262     ( $( $Ty: ident($Int: ty); )+ ) => {
263         $(
264             #[stable(feature = "nonzero_div", since = "1.51.0")]
265             #[rustc_const_unstable(feature = "const_ops", issue = "90080")]
266             impl const Div<$Ty> for $Int {
267                 type Output = $Int;
268                 /// This operation rounds towards zero,
269                 /// truncating any fractional part of the exact result, and cannot panic.
270                 #[inline]
271                 fn div(self, other: $Ty) -> $Int {
272                     // SAFETY: div by zero is checked because `other` is a nonzero,
273                     // and MIN/-1 is checked because `self` is an unsigned int.
274                     unsafe { crate::intrinsics::unchecked_div(self, other.get()) }
275                 }
276             }
277
278             #[stable(feature = "nonzero_div", since = "1.51.0")]
279             #[rustc_const_unstable(feature = "const_ops", issue = "90080")]
280             impl const Rem<$Ty> for $Int {
281                 type Output = $Int;
282                 /// This operation satisfies `n % d == n - (n / d) * d`, and cannot panic.
283                 #[inline]
284                 fn rem(self, other: $Ty) -> $Int {
285                     // SAFETY: rem by zero is checked because `other` is a nonzero,
286                     // and MIN/-1 is checked because `self` is an unsigned int.
287                     unsafe { crate::intrinsics::unchecked_rem(self, other.get()) }
288                 }
289             }
290         )+
291     }
292 }
293
294 nonzero_integers_div! {
295     NonZeroU8(u8);
296     NonZeroU16(u16);
297     NonZeroU32(u32);
298     NonZeroU64(u64);
299     NonZeroU128(u128);
300     NonZeroUsize(usize);
301 }
302
303 // A bunch of methods for unsigned nonzero types only.
304 macro_rules! nonzero_unsigned_operations {
305     ( $( $Ty: ident($Int: ty); )+ ) => {
306         $(
307             impl $Ty {
308                 /// Add an unsigned integer to a non-zero value.
309                 /// Check for overflow and return [`None`] on overflow
310                 /// As a consequence, the result cannot wrap to zero.
311                 ///
312                 ///
313                 /// # Examples
314                 ///
315                 /// ```
316                 /// #![feature(nonzero_ops)]
317                 #[doc = concat!("# use std::num::", stringify!($Ty), ";")]
318                 ///
319                 /// # fn main() { test().unwrap(); }
320                 /// # fn test() -> Option<()> {
321                 #[doc = concat!("let one = ", stringify!($Ty), "::new(1)?;")]
322                 #[doc = concat!("let two = ", stringify!($Ty), "::new(2)?;")]
323                 #[doc = concat!("let max = ", stringify!($Ty), "::new(",
324                                 stringify!($Int), "::MAX)?;")]
325                 ///
326                 /// assert_eq!(Some(two), one.checked_add(1));
327                 /// assert_eq!(None, max.checked_add(1));
328                 /// # Some(())
329                 /// # }
330                 /// ```
331                 #[unstable(feature = "nonzero_ops", issue = "84186")]
332                 #[must_use = "this returns the result of the operation, \
333                               without modifying the original"]
334                 #[inline]
335                 pub const fn checked_add(self, other: $Int) -> Option<$Ty> {
336                     if let Some(result) = self.get().checked_add(other) {
337                         // SAFETY: $Int::checked_add returns None on overflow
338                         // so the result cannot be zero.
339                         Some(unsafe { $Ty::new_unchecked(result) })
340                     } else {
341                         None
342                     }
343                 }
344
345                 /// Add an unsigned integer to a non-zero value.
346                 #[doc = concat!("Return [`", stringify!($Int), "::MAX`] on overflow.")]
347                 ///
348                 /// # Examples
349                 ///
350                 /// ```
351                 /// #![feature(nonzero_ops)]
352                 #[doc = concat!("# use std::num::", stringify!($Ty), ";")]
353                 ///
354                 /// # fn main() { test().unwrap(); }
355                 /// # fn test() -> Option<()> {
356                 #[doc = concat!("let one = ", stringify!($Ty), "::new(1)?;")]
357                 #[doc = concat!("let two = ", stringify!($Ty), "::new(2)?;")]
358                 #[doc = concat!("let max = ", stringify!($Ty), "::new(",
359                                 stringify!($Int), "::MAX)?;")]
360                 ///
361                 /// assert_eq!(two, one.saturating_add(1));
362                 /// assert_eq!(max, max.saturating_add(1));
363                 /// # Some(())
364                 /// # }
365                 /// ```
366                 #[unstable(feature = "nonzero_ops", issue = "84186")]
367                 #[must_use = "this returns the result of the operation, \
368                               without modifying the original"]
369                 #[inline]
370                 pub const fn saturating_add(self, other: $Int) -> $Ty {
371                     // SAFETY: $Int::saturating_add returns $Int::MAX on overflow
372                     // so the result cannot be zero.
373                     unsafe { $Ty::new_unchecked(self.get().saturating_add(other)) }
374                 }
375
376                 /// Add an unsigned integer to a non-zero value,
377                 /// assuming overflow cannot occur.
378                 /// Overflow is unchecked, and it is undefined behaviour to overflow
379                 /// *even if the result would wrap to a non-zero value*.
380                 /// The behaviour is undefined as soon as
381                 #[doc = concat!("`self + rhs > ", stringify!($Int), "::MAX`.")]
382                 ///
383                 /// # Examples
384                 ///
385                 /// ```
386                 /// #![feature(nonzero_ops)]
387                 #[doc = concat!("# use std::num::", stringify!($Ty), ";")]
388                 ///
389                 /// # fn main() { test().unwrap(); }
390                 /// # fn test() -> Option<()> {
391                 #[doc = concat!("let one = ", stringify!($Ty), "::new(1)?;")]
392                 #[doc = concat!("let two = ", stringify!($Ty), "::new(2)?;")]
393                 ///
394                 /// assert_eq!(two, unsafe { one.unchecked_add(1) });
395                 /// # Some(())
396                 /// # }
397                 /// ```
398                 #[unstable(feature = "nonzero_ops", issue = "84186")]
399                 #[must_use = "this returns the result of the operation, \
400                               without modifying the original"]
401                 #[inline]
402                 pub const unsafe fn unchecked_add(self, other: $Int) -> $Ty {
403                     // SAFETY: The caller ensures there is no overflow.
404                     unsafe { $Ty::new_unchecked(self.get().unchecked_add(other)) }
405                 }
406
407                 /// Returns the smallest power of two greater than or equal to n.
408                 /// Check for overflow and return [`None`]
409                 /// if the next power of two is greater than the type’s maximum value.
410                 /// As a consequence, the result cannot wrap to zero.
411                 ///
412                 /// # Examples
413                 ///
414                 /// ```
415                 /// #![feature(nonzero_ops)]
416                 #[doc = concat!("# use std::num::", stringify!($Ty), ";")]
417                 ///
418                 /// # fn main() { test().unwrap(); }
419                 /// # fn test() -> Option<()> {
420                 #[doc = concat!("let two = ", stringify!($Ty), "::new(2)?;")]
421                 #[doc = concat!("let three = ", stringify!($Ty), "::new(3)?;")]
422                 #[doc = concat!("let four = ", stringify!($Ty), "::new(4)?;")]
423                 #[doc = concat!("let max = ", stringify!($Ty), "::new(",
424                                 stringify!($Int), "::MAX)?;")]
425                 ///
426                 /// assert_eq!(Some(two), two.checked_next_power_of_two() );
427                 /// assert_eq!(Some(four), three.checked_next_power_of_two() );
428                 /// assert_eq!(None, max.checked_next_power_of_two() );
429                 /// # Some(())
430                 /// # }
431                 /// ```
432                 #[unstable(feature = "nonzero_ops", issue = "84186")]
433                 #[must_use = "this returns the result of the operation, \
434                               without modifying the original"]
435                 #[inline]
436                 pub const fn checked_next_power_of_two(self) -> Option<$Ty> {
437                     if let Some(nz) = self.get().checked_next_power_of_two() {
438                         // SAFETY: The next power of two is positive
439                         // and overflow is checked.
440                         Some(unsafe { $Ty::new_unchecked(nz) })
441                     } else {
442                         None
443                     }
444                 }
445             }
446         )+
447     }
448 }
449
450 nonzero_unsigned_operations! {
451     NonZeroU8(u8);
452     NonZeroU16(u16);
453     NonZeroU32(u32);
454     NonZeroU64(u64);
455     NonZeroU128(u128);
456     NonZeroUsize(usize);
457 }
458
459 // A bunch of methods for signed nonzero types only.
460 macro_rules! nonzero_signed_operations {
461     ( $( $Ty: ident($Int: ty) -> $Uty: ident($Uint: ty); )+ ) => {
462         $(
463             impl $Ty {
464                 /// Computes the absolute value of self.
465                 #[doc = concat!("See [`", stringify!($Int), "::abs`]")]
466                 /// for documentation on overflow behaviour.
467                 ///
468                 /// # Example
469                 ///
470                 /// ```
471                 /// #![feature(nonzero_ops)]
472                 #[doc = concat!("# use std::num::", stringify!($Ty), ";")]
473                 ///
474                 /// # fn main() { test().unwrap(); }
475                 /// # fn test() -> Option<()> {
476                 #[doc = concat!("let pos = ", stringify!($Ty), "::new(1)?;")]
477                 #[doc = concat!("let neg = ", stringify!($Ty), "::new(-1)?;")]
478                 ///
479                 /// assert_eq!(pos, pos.abs());
480                 /// assert_eq!(pos, neg.abs());
481                 /// # Some(())
482                 /// # }
483                 /// ```
484                 #[unstable(feature = "nonzero_ops", issue = "84186")]
485                 #[must_use = "this returns the result of the operation, \
486                               without modifying the original"]
487                 #[inline]
488                 pub const fn abs(self) -> $Ty {
489                     // SAFETY: This cannot overflow to zero.
490                     unsafe { $Ty::new_unchecked(self.get().abs()) }
491                 }
492
493                 /// Checked absolute value.
494                 /// Check for overflow and returns [`None`] if
495                 #[doc = concat!("`self == ", stringify!($Int), "::MIN`.")]
496                 /// The result cannot be zero.
497                 ///
498                 /// # Example
499                 ///
500                 /// ```
501                 /// #![feature(nonzero_ops)]
502                 #[doc = concat!("# use std::num::", stringify!($Ty), ";")]
503                 ///
504                 /// # fn main() { test().unwrap(); }
505                 /// # fn test() -> Option<()> {
506                 #[doc = concat!("let pos = ", stringify!($Ty), "::new(1)?;")]
507                 #[doc = concat!("let neg = ", stringify!($Ty), "::new(-1)?;")]
508                 #[doc = concat!("let min = ", stringify!($Ty), "::new(",
509                                 stringify!($Int), "::MIN)?;")]
510                 ///
511                 /// assert_eq!(Some(pos), neg.checked_abs());
512                 /// assert_eq!(None, min.checked_abs());
513                 /// # Some(())
514                 /// # }
515                 /// ```
516                 #[unstable(feature = "nonzero_ops", issue = "84186")]
517                 #[must_use = "this returns the result of the operation, \
518                               without modifying the original"]
519                 #[inline]
520                 pub const fn checked_abs(self) -> Option<$Ty> {
521                     if let Some(nz) = self.get().checked_abs() {
522                         // SAFETY: absolute value of nonzero cannot yield zero values.
523                         Some(unsafe { $Ty::new_unchecked(nz) })
524                     } else {
525                         None
526                     }
527                 }
528
529                 /// Computes the absolute value of self,
530                 /// with overflow information, see
531                 #[doc = concat!("[`", stringify!($Int), "::overflowing_abs`].")]
532                 ///
533                 /// # Example
534                 ///
535                 /// ```
536                 /// #![feature(nonzero_ops)]
537                 #[doc = concat!("# use std::num::", stringify!($Ty), ";")]
538                 ///
539                 /// # fn main() { test().unwrap(); }
540                 /// # fn test() -> Option<()> {
541                 #[doc = concat!("let pos = ", stringify!($Ty), "::new(1)?;")]
542                 #[doc = concat!("let neg = ", stringify!($Ty), "::new(-1)?;")]
543                 #[doc = concat!("let min = ", stringify!($Ty), "::new(",
544                                 stringify!($Int), "::MIN)?;")]
545                 ///
546                 /// assert_eq!((pos, false), pos.overflowing_abs());
547                 /// assert_eq!((pos, false), neg.overflowing_abs());
548                 /// assert_eq!((min, true), min.overflowing_abs());
549                 /// # Some(())
550                 /// # }
551                 /// ```
552                 #[unstable(feature = "nonzero_ops", issue = "84186")]
553                 #[must_use = "this returns the result of the operation, \
554                               without modifying the original"]
555                 #[inline]
556                 pub const fn overflowing_abs(self) -> ($Ty, bool) {
557                     let (nz, flag) = self.get().overflowing_abs();
558                     (
559                         // SAFETY: absolute value of nonzero cannot yield zero values.
560                         unsafe { $Ty::new_unchecked(nz) },
561                         flag,
562                     )
563                 }
564
565                 /// Saturating absolute value, see
566                 #[doc = concat!("[`", stringify!($Int), "::saturating_abs`].")]
567                 ///
568                 /// # Example
569                 ///
570                 /// ```
571                 /// #![feature(nonzero_ops)]
572                 #[doc = concat!("# use std::num::", stringify!($Ty), ";")]
573                 ///
574                 /// # fn main() { test().unwrap(); }
575                 /// # fn test() -> Option<()> {
576                 #[doc = concat!("let pos = ", stringify!($Ty), "::new(1)?;")]
577                 #[doc = concat!("let neg = ", stringify!($Ty), "::new(-1)?;")]
578                 #[doc = concat!("let min = ", stringify!($Ty), "::new(",
579                                 stringify!($Int), "::MIN)?;")]
580                 #[doc = concat!("let min_plus = ", stringify!($Ty), "::new(",
581                                 stringify!($Int), "::MIN + 1)?;")]
582                 #[doc = concat!("let max = ", stringify!($Ty), "::new(",
583                                 stringify!($Int), "::MAX)?;")]
584                 ///
585                 /// assert_eq!(pos, pos.saturating_abs());
586                 /// assert_eq!(pos, neg.saturating_abs());
587                 /// assert_eq!(max, min.saturating_abs());
588                 /// assert_eq!(max, min_plus.saturating_abs());
589                 /// # Some(())
590                 /// # }
591                 /// ```
592                 #[unstable(feature = "nonzero_ops", issue = "84186")]
593                 #[must_use = "this returns the result of the operation, \
594                               without modifying the original"]
595                 #[inline]
596                 pub const fn saturating_abs(self) -> $Ty {
597                     // SAFETY: absolute value of nonzero cannot yield zero values.
598                     unsafe { $Ty::new_unchecked(self.get().saturating_abs()) }
599                 }
600
601                 /// Wrapping absolute value, see
602                 #[doc = concat!("[`", stringify!($Int), "::wrapping_abs`].")]
603                 ///
604                 /// # Example
605                 ///
606                 /// ```
607                 /// #![feature(nonzero_ops)]
608                 #[doc = concat!("# use std::num::", stringify!($Ty), ";")]
609                 ///
610                 /// # fn main() { test().unwrap(); }
611                 /// # fn test() -> Option<()> {
612                 #[doc = concat!("let pos = ", stringify!($Ty), "::new(1)?;")]
613                 #[doc = concat!("let neg = ", stringify!($Ty), "::new(-1)?;")]
614                 #[doc = concat!("let min = ", stringify!($Ty), "::new(",
615                                 stringify!($Int), "::MIN)?;")]
616                 #[doc = concat!("let max = ", stringify!($Ty), "::new(",
617                                 stringify!($Int), "::MAX)?;")]
618                 ///
619                 /// assert_eq!(pos, pos.wrapping_abs());
620                 /// assert_eq!(pos, neg.wrapping_abs());
621                 /// assert_eq!(min, min.wrapping_abs());
622                 /// # // FIXME: add once Neg is implemented?
623                 /// # // assert_eq!(max, (-max).wrapping_abs());
624                 /// # Some(())
625                 /// # }
626                 /// ```
627                 #[unstable(feature = "nonzero_ops", issue = "84186")]
628                 #[must_use = "this returns the result of the operation, \
629                               without modifying the original"]
630                 #[inline]
631                 pub const fn wrapping_abs(self) -> $Ty {
632                     // SAFETY: absolute value of nonzero cannot yield zero values.
633                     unsafe { $Ty::new_unchecked(self.get().wrapping_abs()) }
634                 }
635
636                 /// Computes the absolute value of self
637                 /// without any wrapping or panicking.
638                 ///
639                 /// # Example
640                 ///
641                 /// ```
642                 /// #![feature(nonzero_ops)]
643                 #[doc = concat!("# use std::num::", stringify!($Ty), ";")]
644                 #[doc = concat!("# use std::num::", stringify!($Uty), ";")]
645                 ///
646                 /// # fn main() { test().unwrap(); }
647                 /// # fn test() -> Option<()> {
648                 #[doc = concat!("let u_pos = ", stringify!($Uty), "::new(1)?;")]
649                 #[doc = concat!("let i_pos = ", stringify!($Ty), "::new(1)?;")]
650                 #[doc = concat!("let i_neg = ", stringify!($Ty), "::new(-1)?;")]
651                 #[doc = concat!("let i_min = ", stringify!($Ty), "::new(",
652                                 stringify!($Int), "::MIN)?;")]
653                 #[doc = concat!("let u_max = ", stringify!($Uty), "::new(",
654                                 stringify!($Uint), "::MAX / 2 + 1)?;")]
655                 ///
656                 /// assert_eq!(u_pos, i_pos.unsigned_abs());
657                 /// assert_eq!(u_pos, i_neg.unsigned_abs());
658                 /// assert_eq!(u_max, i_min.unsigned_abs());
659                 /// # Some(())
660                 /// # }
661                 /// ```
662                 #[unstable(feature = "nonzero_ops", issue = "84186")]
663                 #[must_use = "this returns the result of the operation, \
664                               without modifying the original"]
665                 #[inline]
666                 pub const fn unsigned_abs(self) -> $Uty {
667                     // SAFETY: absolute value of nonzero cannot yield zero values.
668                     unsafe { $Uty::new_unchecked(self.get().unsigned_abs()) }
669                 }
670             }
671         )+
672     }
673 }
674
675 nonzero_signed_operations! {
676     NonZeroI8(i8) -> NonZeroU8(u8);
677     NonZeroI16(i16) -> NonZeroU16(u16);
678     NonZeroI32(i32) -> NonZeroU32(u32);
679     NonZeroI64(i64) -> NonZeroU64(u64);
680     NonZeroI128(i128) -> NonZeroU128(u128);
681     NonZeroIsize(isize) -> NonZeroUsize(usize);
682 }
683
684 // A bunch of methods for both signed and unsigned nonzero types.
685 macro_rules! nonzero_unsigned_signed_operations {
686     ( $( $signedness:ident $Ty: ident($Int: ty); )+ ) => {
687         $(
688             impl $Ty {
689                 /// Multiply two non-zero integers together.
690                 /// Check for overflow and return [`None`] on overflow.
691                 /// As a consequence, the result cannot wrap to zero.
692                 ///
693                 /// # Examples
694                 ///
695                 /// ```
696                 /// #![feature(nonzero_ops)]
697                 #[doc = concat!("# use std::num::", stringify!($Ty), ";")]
698                 ///
699                 /// # fn main() { test().unwrap(); }
700                 /// # fn test() -> Option<()> {
701                 #[doc = concat!("let two = ", stringify!($Ty), "::new(2)?;")]
702                 #[doc = concat!("let four = ", stringify!($Ty), "::new(4)?;")]
703                 #[doc = concat!("let max = ", stringify!($Ty), "::new(",
704                                 stringify!($Int), "::MAX)?;")]
705                 ///
706                 /// assert_eq!(Some(four), two.checked_mul(two));
707                 /// assert_eq!(None, max.checked_mul(two));
708                 /// # Some(())
709                 /// # }
710                 /// ```
711                 #[unstable(feature = "nonzero_ops", issue = "84186")]
712                 #[must_use = "this returns the result of the operation, \
713                               without modifying the original"]
714                 #[inline]
715                 pub const fn checked_mul(self, other: $Ty) -> Option<$Ty> {
716                     if let Some(result) = self.get().checked_mul(other.get()) {
717                         // SAFETY: checked_mul returns None on overflow
718                         // and `other` is also non-null
719                         // so the result cannot be zero.
720                         Some(unsafe { $Ty::new_unchecked(result) })
721                     } else {
722                         None
723                     }
724                 }
725
726                 /// Multiply two non-zero integers together.
727                 #[doc = concat!("Return [`", stringify!($Int), "::MAX`] on overflow.")]
728                 ///
729                 /// # Examples
730                 ///
731                 /// ```
732                 /// #![feature(nonzero_ops)]
733                 #[doc = concat!("# use std::num::", stringify!($Ty), ";")]
734                 ///
735                 /// # fn main() { test().unwrap(); }
736                 /// # fn test() -> Option<()> {
737                 #[doc = concat!("let two = ", stringify!($Ty), "::new(2)?;")]
738                 #[doc = concat!("let four = ", stringify!($Ty), "::new(4)?;")]
739                 #[doc = concat!("let max = ", stringify!($Ty), "::new(",
740                                 stringify!($Int), "::MAX)?;")]
741                 ///
742                 /// assert_eq!(four, two.saturating_mul(two));
743                 /// assert_eq!(max, four.saturating_mul(max));
744                 /// # Some(())
745                 /// # }
746                 /// ```
747                 #[unstable(feature = "nonzero_ops", issue = "84186")]
748                 #[must_use = "this returns the result of the operation, \
749                               without modifying the original"]
750                 #[inline]
751                 pub const fn saturating_mul(self, other: $Ty) -> $Ty {
752                     // SAFETY: saturating_mul returns u*::MAX on overflow
753                     // and `other` is also non-null
754                     // so the result cannot be zero.
755                     unsafe { $Ty::new_unchecked(self.get().saturating_mul(other.get())) }
756                 }
757
758                 /// Multiply two non-zero integers together,
759                 /// assuming overflow cannot occur.
760                 /// Overflow is unchecked, and it is undefined behaviour to overflow
761                 /// *even if the result would wrap to a non-zero value*.
762                 /// The behaviour is undefined as soon as
763                 #[doc = sign_dependent_expr!{
764                     $signedness ?
765                     if signed {
766                         concat!("`self * rhs > ", stringify!($Int), "::MAX`, ",
767                                 "or `self * rhs < ", stringify!($Int), "::MIN`.")
768                     }
769                     if unsigned {
770                         concat!("`self * rhs > ", stringify!($Int), "::MAX`.")
771                     }
772                 }]
773                 ///
774                 /// # Examples
775                 ///
776                 /// ```
777                 /// #![feature(nonzero_ops)]
778                 #[doc = concat!("# use std::num::", stringify!($Ty), ";")]
779                 ///
780                 /// # fn main() { test().unwrap(); }
781                 /// # fn test() -> Option<()> {
782                 #[doc = concat!("let two = ", stringify!($Ty), "::new(2)?;")]
783                 #[doc = concat!("let four = ", stringify!($Ty), "::new(4)?;")]
784                 ///
785                 /// assert_eq!(four, unsafe { two.unchecked_mul(two) });
786                 /// # Some(())
787                 /// # }
788                 /// ```
789                 #[unstable(feature = "nonzero_ops", issue = "84186")]
790                 #[must_use = "this returns the result of the operation, \
791                               without modifying the original"]
792                 #[inline]
793                 pub const unsafe fn unchecked_mul(self, other: $Ty) -> $Ty {
794                     // SAFETY: The caller ensures there is no overflow.
795                     unsafe { $Ty::new_unchecked(self.get().unchecked_mul(other.get())) }
796                 }
797
798                 /// Raise non-zero value to an integer power.
799                 /// Check for overflow and return [`None`] on overflow.
800                 /// As a consequence, the result cannot wrap to zero.
801                 ///
802                 /// # Examples
803                 ///
804                 /// ```
805                 /// #![feature(nonzero_ops)]
806                 #[doc = concat!("# use std::num::", stringify!($Ty), ";")]
807                 ///
808                 /// # fn main() { test().unwrap(); }
809                 /// # fn test() -> Option<()> {
810                 #[doc = concat!("let three = ", stringify!($Ty), "::new(3)?;")]
811                 #[doc = concat!("let twenty_seven = ", stringify!($Ty), "::new(27)?;")]
812                 #[doc = concat!("let half_max = ", stringify!($Ty), "::new(",
813                                 stringify!($Int), "::MAX / 2)?;")]
814                 ///
815                 /// assert_eq!(Some(twenty_seven), three.checked_pow(3));
816                 /// assert_eq!(None, half_max.checked_pow(3));
817                 /// # Some(())
818                 /// # }
819                 /// ```
820                 #[unstable(feature = "nonzero_ops", issue = "84186")]
821                 #[must_use = "this returns the result of the operation, \
822                               without modifying the original"]
823                 #[inline]
824                 pub const fn checked_pow(self, other: u32) -> Option<$Ty> {
825                     if let Some(result) = self.get().checked_pow(other) {
826                         // SAFETY: checked_pow returns None on overflow
827                         // so the result cannot be zero.
828                         Some(unsafe { $Ty::new_unchecked(result) })
829                     } else {
830                         None
831                     }
832                 }
833
834                 /// Raise non-zero value to an integer power.
835                 #[doc = sign_dependent_expr!{
836                     $signedness ?
837                     if signed {
838                         concat!("Return [`", stringify!($Int), "::MIN`] ",
839                                     "or [`", stringify!($Int), "::MAX`] on overflow.")
840                     }
841                     if unsigned {
842                         concat!("Return [`", stringify!($Int), "::MAX`] on overflow.")
843                     }
844                 }]
845                 ///
846                 /// # Examples
847                 ///
848                 /// ```
849                 /// #![feature(nonzero_ops)]
850                 #[doc = concat!("# use std::num::", stringify!($Ty), ";")]
851                 ///
852                 /// # fn main() { test().unwrap(); }
853                 /// # fn test() -> Option<()> {
854                 #[doc = concat!("let three = ", stringify!($Ty), "::new(3)?;")]
855                 #[doc = concat!("let twenty_seven = ", stringify!($Ty), "::new(27)?;")]
856                 #[doc = concat!("let max = ", stringify!($Ty), "::new(",
857                                 stringify!($Int), "::MAX)?;")]
858                 ///
859                 /// assert_eq!(twenty_seven, three.saturating_pow(3));
860                 /// assert_eq!(max, max.saturating_pow(3));
861                 /// # Some(())
862                 /// # }
863                 /// ```
864                 #[unstable(feature = "nonzero_ops", issue = "84186")]
865                 #[must_use = "this returns the result of the operation, \
866                               without modifying the original"]
867                 #[inline]
868                 pub const fn saturating_pow(self, other: u32) -> $Ty {
869                     // SAFETY: saturating_pow returns u*::MAX on overflow
870                     // so the result cannot be zero.
871                     unsafe { $Ty::new_unchecked(self.get().saturating_pow(other)) }
872                 }
873             }
874         )+
875     }
876 }
877
878 // Use this when the generated code should differ between signed and unsigned types.
879 macro_rules! sign_dependent_expr {
880     (signed ? if signed { $signed_case:expr } if unsigned { $unsigned_case:expr } ) => {
881         $signed_case
882     };
883     (unsigned ? if signed { $signed_case:expr } if unsigned { $unsigned_case:expr } ) => {
884         $unsigned_case
885     };
886 }
887
888 nonzero_unsigned_signed_operations! {
889     unsigned NonZeroU8(u8);
890     unsigned NonZeroU16(u16);
891     unsigned NonZeroU32(u32);
892     unsigned NonZeroU64(u64);
893     unsigned NonZeroU128(u128);
894     unsigned NonZeroUsize(usize);
895     signed NonZeroI8(i8);
896     signed NonZeroI16(i16);
897     signed NonZeroI32(i32);
898     signed NonZeroI64(i64);
899     signed NonZeroI128(i128);
900     signed NonZeroIsize(isize);
901 }
902
903 macro_rules! nonzero_unsigned_is_power_of_two {
904     ( $( $Ty: ident )+ ) => {
905         $(
906             impl $Ty {
907
908                 /// Returns `true` if and only if `self == (1 << k)` for some `k`.
909                 ///
910                 /// On many architectures, this function can perform better than `is_power_of_two()`
911                 /// on the underlying integer type, as special handling of zero can be avoided.
912                 ///
913                 /// # Examples
914                 ///
915                 /// Basic usage:
916                 ///
917                 /// ```
918                 /// #![feature(nonzero_is_power_of_two)]
919                 ///
920                 #[doc = concat!("let eight = std::num::", stringify!($Ty), "::new(8).unwrap();")]
921                 /// assert!(eight.is_power_of_two());
922                 #[doc = concat!("let ten = std::num::", stringify!($Ty), "::new(10).unwrap();")]
923                 /// assert!(!ten.is_power_of_two());
924                 /// ```
925                 #[must_use]
926                 #[unstable(feature = "nonzero_is_power_of_two", issue = "81106")]
927                 #[inline]
928                 pub const fn is_power_of_two(self) -> bool {
929                     // LLVM 11 normalizes `unchecked_sub(x, 1) & x == 0` to the implementation seen here.
930                     // On the basic x86-64 target, this saves 3 instructions for the zero check.
931                     // On x86_64 with BMI1, being nonzero lets it codegen to `BLSR`, which saves an instruction
932                     // compared to the `POPCNT` implementation on the underlying integer type.
933
934                     intrinsics::ctpop(self.get()) < 2
935                 }
936
937             }
938         )+
939     }
940 }
941
942 nonzero_unsigned_is_power_of_two! { NonZeroU8 NonZeroU16 NonZeroU32 NonZeroU64 NonZeroU128 NonZeroUsize }