about summary refs log tree commit diff
diff options
context:
space:
mode:
authorYuki Okushi <huyuumi.dev@gmail.com>2021-01-30 13:36:44 +0900
committerGitHub <noreply@github.com>2021-01-30 13:36:44 +0900
commit91ea1cbc177e3ed460c5435092d1cc07e4423428 (patch)
treebbbfedc01fcb61520e165a67efa8d99ca8ecab7a
parentb94d84d38a3d306a54c5a23caa54d373a2202b9f (diff)
parentedf2e3725e8d95b52784990a0c05978db5646bfb (diff)
downloadrust-91ea1cbc177e3ed460c5435092d1cc07e4423428.tar.gz
rust-91ea1cbc177e3ed460c5435092d1cc07e4423428.zip
Rollup merge of #80959 - jhpratt:unsigned_abs-stabilization, r=m-ou-se
Stabilize `unsigned_abs`

Resolves #74913.

This PR stabilizes the `i*::unsigned_abs()` method, which returns the absolute value of an integer _as its unsigned equivalent_. This has the advantage that it does not overflow on `i*::MIN`.

I have gone ahead and used this in a couple locations throughout the repository.
-rw-r--r--compiler/rustc_middle/src/mir/interpret/mod.rs9
-rw-r--r--compiler/rustc_middle/src/mir/interpret/pointer.rs4
-rw-r--r--compiler/rustc_mir/src/interpret/intrinsics.rs4
-rw-r--r--compiler/rustc_symbol_mangling/src/v0.rs2
-rw-r--r--library/core/src/num/dec2flt/mod.rs2
-rw-r--r--library/core/src/num/int_macros.rs4
6 files changed, 8 insertions, 17 deletions
diff --git a/compiler/rustc_middle/src/mir/interpret/mod.rs b/compiler/rustc_middle/src/mir/interpret/mod.rs
index 80b58642136..55fe5f971e7 100644
--- a/compiler/rustc_middle/src/mir/interpret/mod.rs
+++ b/compiler/rustc_middle/src/mir/interpret/mod.rs
@@ -588,12 +588,3 @@ pub fn read_target_uint(endianness: Endian, mut source: &[u8]) -> Result<u128, i
     debug_assert!(source.len() == 0); // We should have consumed the source buffer.
     uint
 }
-
-/// Computes the unsigned absolute value without wrapping or panicking.
-#[inline]
-pub fn uabs(value: i64) -> u64 {
-    // The only tricky part here is if value == i64::MIN. In that case,
-    // wrapping_abs() returns i64::MIN == -2^63. Casting this value to a u64
-    // gives 2^63, the correct value.
-    value.wrapping_abs() as u64
-}
diff --git a/compiler/rustc_middle/src/mir/interpret/pointer.rs b/compiler/rustc_middle/src/mir/interpret/pointer.rs
index e3d5a085613..8774b48fb3e 100644
--- a/compiler/rustc_middle/src/mir/interpret/pointer.rs
+++ b/compiler/rustc_middle/src/mir/interpret/pointer.rs
@@ -1,4 +1,4 @@
-use super::{uabs, AllocId, InterpResult};
+use super::{AllocId, InterpResult};
 
 use rustc_macros::HashStable;
 use rustc_target::abi::{HasDataLayout, Size};
@@ -57,7 +57,7 @@ pub trait PointerArithmetic: HasDataLayout {
     #[inline]
     fn overflowing_signed_offset(&self, val: u64, i: i64) -> (u64, bool) {
         // We need to make sure that i fits in a machine isize.
-        let n = uabs(i);
+        let n = i.unsigned_abs();
         if i >= 0 {
             let (val, over) = self.overflowing_offset(val, n);
             (val, over || i > self.machine_isize_max())
diff --git a/compiler/rustc_mir/src/interpret/intrinsics.rs b/compiler/rustc_mir/src/interpret/intrinsics.rs
index 58858c09f44..f4309c9cd95 100644
--- a/compiler/rustc_mir/src/interpret/intrinsics.rs
+++ b/compiler/rustc_mir/src/interpret/intrinsics.rs
@@ -7,7 +7,7 @@ use std::convert::TryFrom;
 use rustc_hir::def_id::DefId;
 use rustc_middle::mir::{
     self,
-    interpret::{uabs, ConstValue, GlobalId, InterpResult, Scalar},
+    interpret::{ConstValue, GlobalId, InterpResult, Scalar},
     BinOp,
 };
 use rustc_middle::ty;
@@ -542,7 +542,7 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
         // memory between these pointers must be accessible. Note that we do not require the
         // pointers to be properly aligned (unlike a read/write operation).
         let min_ptr = if offset_bytes >= 0 { ptr } else { offset_ptr };
-        let size: u64 = uabs(offset_bytes);
+        let size = offset_bytes.unsigned_abs();
         // This call handles checking for integer/NULL pointers.
         self.memory.check_ptr_access_align(
             min_ptr,
diff --git a/compiler/rustc_symbol_mangling/src/v0.rs b/compiler/rustc_symbol_mangling/src/v0.rs
index c84e2cb45a6..bbf7ecc39cf 100644
--- a/compiler/rustc_symbol_mangling/src/v0.rs
+++ b/compiler/rustc_symbol_mangling/src/v0.rs
@@ -530,7 +530,7 @@ impl Printer<'tcx> for SymbolMangler<'tcx> {
                     if val < 0 {
                         neg = true;
                     }
-                    Some(val.wrapping_abs() as u128)
+                    Some(val.unsigned_abs())
                 })
             }
             _ => {
diff --git a/library/core/src/num/dec2flt/mod.rs b/library/core/src/num/dec2flt/mod.rs
index 91c61f814e1..20ac165c6c7 100644
--- a/library/core/src/num/dec2flt/mod.rs
+++ b/library/core/src/num/dec2flt/mod.rs
@@ -332,7 +332,7 @@ fn bound_intermediate_digits(decimal: &Decimal<'_>, e: i64) -> u64 {
         // It tries to find a positive number k such that `f << k / 10^e` is an in-range
         // significand. This will result in about `2^53 * f * 10^e` < `10^17 * f * 10^e`.
         // One input that triggers this is 0.33...33 (375 x 3).
-        f_len + (e.abs() as u64) + 17
+        f_len + e.unsigned_abs() + 17
     }
 }
 
diff --git a/library/core/src/num/int_macros.rs b/library/core/src/num/int_macros.rs
index f732f11d909..8fdd7c9e5d7 100644
--- a/library/core/src/num/int_macros.rs
+++ b/library/core/src/num/int_macros.rs
@@ -1158,12 +1158,12 @@ macro_rules! int_impl {
         /// Basic usage:
         ///
         /// ```
-        /// #![feature(unsigned_abs)]
         #[doc = concat!("assert_eq!(100", stringify!($SelfT), ".unsigned_abs(), 100", stringify!($UnsignedT), ");")]
         #[doc = concat!("assert_eq!((-100", stringify!($SelfT), ").unsigned_abs(), 100", stringify!($UnsignedT), ");")]
         /// assert_eq!((-128i8).unsigned_abs(), 128u8);
         /// ```
-        #[unstable(feature = "unsigned_abs", issue = "74913")]
+        #[stable(feature = "unsigned_abs", since = "1.51.0")]
+        #[rustc_const_stable(feature = "unsigned_abs", since = "1.51.0")]
         #[inline]
         pub const fn unsigned_abs(self) -> $UnsignedT {
              self.wrapping_abs() as $UnsignedT