Selaa lähdekoodia

refactor float conversion

Aaron Kutch 4 vuotta sitten
vanhempi
commit
01eaf808c6
7 muutettua tiedostoa jossa 198 lisäystä ja 222 poistoa
  1. 144 155
      src/float/conv.rs
  2. 34 5
      src/float/mod.rs
  3. 1 2
      src/float/pow.rs
  4. 17 53
      src/int/mod.rs
  5. 0 5
      src/lib.rs
  6. 1 1
      testcrate/tests/div_rem.rs
  7. 1 1
      testcrate/tests/mul.rs

+ 144 - 155
src/float/conv.rs

@@ -1,90 +1,88 @@
 use float::Float;
-use int::Int;
-
-macro_rules! int_to_float {
-    ($i:expr, $ity:ty, $fty:ty) => {{
-        let i = $i;
-        if i == 0 {
-            return 0.0;
-        }
-
-        let mant_dig = <$fty>::SIGNIFICAND_BITS + 1;
-        let exponent_bias = <$fty>::EXPONENT_BIAS;
-
-        let n = <$ity as Int>::BITS;
-        let (s, a) = i.extract_sign();
-        let mut a = a;
-
-        // number of significant digits
-        let sd = n - a.leading_zeros();
-
-        // exponent
-        let mut e = sd - 1;
+use int::{CastInto, Int};
+
+fn int_to_float<I: Int, F: Float>(i: I) -> F
+where
+    F::Int: CastInto<u32>,
+    F::Int: CastInto<I>,
+    I::UnsignedInt: CastInto<F::Int>,
+    u32: CastInto<F::Int>,
+{
+    if i == I::ZERO {
+        return F::ZERO;
+    }
 
-        if <$ity as Int>::BITS < mant_dig {
-            return <$fty>::from_parts(
-                s,
-                (e + exponent_bias) as <$fty as Float>::Int,
-                (a as <$fty as Float>::Int) << (mant_dig - e - 1),
-            );
-        }
+    let two = I::UnsignedInt::ONE + I::UnsignedInt::ONE;
+    let four = two + two;
+    let sign = i < I::ZERO;
+    let mut x = Int::abs_diff(i, I::ZERO);
+
+    // number of significant digits in the integer
+    let i_sd = I::BITS - x.leading_zeros();
+    // significant digits for the float, including implicit bit
+    let f_sd = F::SIGNIFICAND_BITS + 1;
+
+    // exponent
+    let mut exp = i_sd - 1;
+
+    if I::BITS < f_sd {
+        return F::from_parts(
+            sign,
+            (exp + F::EXPONENT_BIAS).cast(),
+            x.cast() << (f_sd - exp - 1),
+        );
+    }
 
-        a = if sd > mant_dig {
-            /* start:  0000000000000000000001xxxxxxxxxxxxxxxxxxxxxxPQxxxxxxxxxxxxxxxxxx
-             *  finish: 000000000000000000000000000000000000001xxxxxxxxxxxxxxxxxxxxxxPQR
-             *                                                12345678901234567890123456
-             *  1 = msb 1 bit
-             *  P = bit MANT_DIG-1 bits to the right of 1
-             *  Q = bit MANT_DIG bits to the right of 1
-             *  R = "or" of all bits to the right of Q
-             */
-            let mant_dig_plus_one = mant_dig + 1;
-            let mant_dig_plus_two = mant_dig + 2;
-            a = if sd == mant_dig_plus_one {
-                a << 1
-            } else if sd == mant_dig_plus_two {
-                a
-            } else {
-                (a >> (sd - mant_dig_plus_two)) as <$ity as Int>::UnsignedInt
-                    | ((a & <$ity as Int>::UnsignedInt::max_value())
-                        .wrapping_shl((n + mant_dig_plus_two) - sd)
-                        != 0) as <$ity as Int>::UnsignedInt
-            };
-
-            /* finish: */
-            a |= ((a & 4) != 0) as <$ity as Int>::UnsignedInt; /* Or P into R */
-            a += 1; /* round - this step may add a significant bit */
-            a >>= 2; /* dump Q and R */
-
-            /* a is now rounded to mant_dig or mant_dig+1 bits */
-            if (a & (1 << mant_dig)) != 0 {
-                a >>= 1;
-                e += 1;
-            }
-            a
-        /* a is now rounded to mant_dig bits */
+    x = if i_sd > f_sd {
+        // start:  0000000000000000000001xxxxxxxxxxxxxxxxxxxxxxPQxxxxxxxxxxxxxxxxxx
+        // finish: 000000000000000000000000000000000000001xxxxxxxxxxxxxxxxxxxxxxPQR
+        //                                               12345678901234567890123456
+        // 1 = the implicit bit
+        // P = bit f_sd-1 bits to the right of 1
+        // Q = bit f_sd bits to the right of 1
+        // R = "or" of all bits to the right of Q
+        let f_sd_add2 = f_sd + 2;
+        x = if i_sd == (f_sd + 1) {
+            x << 1
+        } else if i_sd == f_sd_add2 {
+            x
         } else {
-            a.wrapping_shl(mant_dig - sd)
-            /* a is now rounded to mant_dig bits */
+            (x >> (i_sd - f_sd_add2))
+                | Int::from_bool(
+                    (x & I::UnsignedInt::MAX).wrapping_shl((I::BITS + f_sd_add2) - i_sd)
+                        != Int::ZERO,
+                )
         };
 
-        <$fty>::from_parts(
-            s,
-            (e + exponent_bias) as <$fty as Float>::Int,
-            a as <$fty as Float>::Int,
-        )
-    }};
+        // R |= P
+        x |= Int::from_bool((x & four) != I::UnsignedInt::ZERO);
+        // round - this step may add a significant bit
+        x += Int::ONE;
+        // dump Q and R
+        x >>= 2;
+
+        // a is now rounded to f_sd or f_sd+1 bits
+        if (x & (I::UnsignedInt::ONE << f_sd)) != Int::ZERO {
+            x >>= 1;
+            exp += 1;
+        }
+        x
+    } else {
+        x.wrapping_shl(f_sd - i_sd)
+    };
+
+    F::from_parts(sign, (exp + F::EXPONENT_BIAS).cast(), x.cast())
 }
 
 intrinsics! {
     #[arm_aeabi_alias = __aeabi_i2f]
     pub extern "C" fn __floatsisf(i: i32) -> f32 {
-        int_to_float!(i, i32, f32)
+        int_to_float(i)
     }
 
     #[arm_aeabi_alias = __aeabi_i2d]
     pub extern "C" fn __floatsidf(i: i32) -> f64 {
-        int_to_float!(i, i32, f64)
+        int_to_float(i)
     }
 
     #[maybe_use_optimized_c_shim]
@@ -95,7 +93,7 @@ intrinsics! {
         if cfg!(target_arch = "x86_64") {
             i as f32
         } else {
-            int_to_float!(i, i64, f32)
+            int_to_float(i)
         }
     }
 
@@ -107,181 +105,172 @@ intrinsics! {
         if cfg!(target_arch = "x86_64") {
             i as f64
         } else {
-            int_to_float!(i, i64, f64)
+            int_to_float(i)
         }
     }
 
     #[unadjusted_on_win64]
     pub extern "C" fn __floattisf(i: i128) -> f32 {
-        int_to_float!(i, i128, f32)
+        int_to_float(i)
     }
 
     #[unadjusted_on_win64]
     pub extern "C" fn __floattidf(i: i128) -> f64 {
-        int_to_float!(i, i128, f64)
+        int_to_float(i)
     }
 
     #[arm_aeabi_alias = __aeabi_ui2f]
     pub extern "C" fn __floatunsisf(i: u32) -> f32 {
-        int_to_float!(i, u32, f32)
+        int_to_float(i)
     }
 
     #[arm_aeabi_alias = __aeabi_ui2d]
     pub extern "C" fn __floatunsidf(i: u32) -> f64 {
-        int_to_float!(i, u32, f64)
+        int_to_float(i)
     }
 
     #[maybe_use_optimized_c_shim]
     #[arm_aeabi_alias = __aeabi_ul2f]
     pub extern "C" fn __floatundisf(i: u64) -> f32 {
-        int_to_float!(i, u64, f32)
+        int_to_float(i)
     }
 
     #[maybe_use_optimized_c_shim]
     #[arm_aeabi_alias = __aeabi_ul2d]
     pub extern "C" fn __floatundidf(i: u64) -> f64 {
-        int_to_float!(i, u64, f64)
+        int_to_float(i)
     }
 
     #[unadjusted_on_win64]
     pub extern "C" fn __floatuntisf(i: u128) -> f32 {
-        int_to_float!(i, u128, f32)
+        int_to_float(i)
     }
 
     #[unadjusted_on_win64]
     pub extern "C" fn __floatuntidf(i: u128) -> f64 {
-        int_to_float!(i, u128, f64)
+        int_to_float(i)
     }
 }
 
-#[derive(PartialEq)]
-enum Sign {
-    Positive,
-    Negative,
-}
+fn float_to_int<F: Float, I: Int>(f: F) -> I
+where
+    F::ExpInt: CastInto<u32>,
+    u32: CastInto<F::ExpInt>,
+    F::Int: CastInto<I>,
+{
+    // converting NaNs is UB, so we don't consider them
+
+    let sign = f.sign();
+    let mut exp = f.exp();
 
-macro_rules! float_to_int {
-    ($f:expr, $fty:ty, $ity:ty) => {{
-        let f = $f;
-        let fixint_min = <$ity>::min_value();
-        let fixint_max = <$ity>::max_value();
-        let fixint_bits = <$ity as Int>::BITS as usize;
-        let fixint_unsigned = fixint_min == 0;
-
-        let sign_bit = <$fty>::SIGN_MASK;
-        let significand_bits = <$fty>::SIGNIFICAND_BITS as usize;
-        let exponent_bias = <$fty>::EXPONENT_BIAS as usize;
-        //let exponent_max = <$fty>::exponent_max() as usize;
-
-        // Break a into sign, exponent, significand
-        let a_rep = <$fty>::repr(f);
-        let a_abs = a_rep & !sign_bit;
-
-        // this is used to work around -1 not being available for unsigned
-        let sign = if (a_rep & sign_bit) == 0 {
-            Sign::Positive
+    // if less than one or unsigned & negative
+    if (exp < F::EXPONENT_BIAS.cast()) || (!I::SIGNED && sign) {
+        return I::ZERO;
+    }
+    exp -= F::EXPONENT_BIAS.cast();
+
+    // If the value is too large for `I`, saturate.
+    let bits: F::ExpInt = I::BITS.cast();
+    let max = if I::SIGNED {
+        bits - F::ExpInt::ONE
+    } else {
+        bits
+    };
+    if max <= exp {
+        return if sign {
+            // It happens that I::MIN is handled correctly
+            I::MIN
         } else {
-            Sign::Negative
+            I::MAX
         };
-        let mut exponent = (a_abs >> significand_bits) as usize;
-        let significand = (a_abs & <$fty>::SIGNIFICAND_MASK) | <$fty>::IMPLICIT_BIT;
+    };
 
-        // if < 1 or unsigned & negative
-        if exponent < exponent_bias || fixint_unsigned && sign == Sign::Negative {
-            return 0;
-        }
-        exponent -= exponent_bias;
-
-        // If the value is infinity, saturate.
-        // If the value is too large for the integer type, 0.
-        if exponent
-            >= (if fixint_unsigned {
-                fixint_bits
-            } else {
-                fixint_bits - 1
-            })
-        {
-            return if sign == Sign::Positive {
-                fixint_max
-            } else {
-                fixint_min
-            };
-        }
-        // If 0 <= exponent < significand_bits, right shift to get the result.
-        // Otherwise, shift left.
-        // (sign - 1) will never overflow as negative signs are already returned as 0 for unsigned
-        let r = if exponent < significand_bits {
-            (significand >> (significand_bits - exponent)) as $ity
+    // `0 <= exp < max`
+
+    // If 0 <= exponent < F::SIGNIFICAND_BITS, right shift to get the result. Otherwise, shift left.
+    let sig_bits: F::ExpInt = F::SIGNIFICAND_BITS.cast();
+    // The larger integer has to be casted into, or else the shift overflows
+    let r: I = if F::Int::BITS < I::BITS {
+        let tmp: I = if exp < sig_bits {
+            f.imp_frac().cast() >> (sig_bits - exp).cast()
         } else {
-            (significand as $ity) << (exponent - significand_bits)
+            f.imp_frac().cast() << (exp - sig_bits).cast()
         };
-
-        if sign == Sign::Negative {
-            (!r).wrapping_add(1)
+        tmp
+    } else {
+        let tmp: F::Int = if exp < sig_bits {
+            f.imp_frac() >> (sig_bits - exp).cast()
         } else {
-            r
-        }
-    }};
+            f.imp_frac() << (exp - sig_bits).cast()
+        };
+        tmp.cast()
+    };
+
+    if sign {
+        r.wrapping_neg()
+    } else {
+        r
+    }
 }
 
 intrinsics! {
     #[arm_aeabi_alias = __aeabi_f2iz]
     pub extern "C" fn __fixsfsi(f: f32) -> i32 {
-        float_to_int!(f, f32, i32)
+        float_to_int(f)
     }
 
     #[arm_aeabi_alias = __aeabi_f2lz]
     pub extern "C" fn __fixsfdi(f: f32) -> i64 {
-        float_to_int!(f, f32, i64)
+        float_to_int(f)
     }
 
     #[unadjusted_on_win64]
     pub extern "C" fn __fixsfti(f: f32) -> i128 {
-        float_to_int!(f, f32, i128)
+        float_to_int(f)
     }
 
     #[arm_aeabi_alias = __aeabi_d2iz]
     pub extern "C" fn __fixdfsi(f: f64) -> i32 {
-        float_to_int!(f, f64, i32)
+        float_to_int(f)
     }
 
     #[arm_aeabi_alias = __aeabi_d2lz]
     pub extern "C" fn __fixdfdi(f: f64) -> i64 {
-        float_to_int!(f, f64, i64)
+        float_to_int(f)
     }
 
     #[unadjusted_on_win64]
     pub extern "C" fn __fixdfti(f: f64) -> i128 {
-        float_to_int!(f, f64, i128)
+        float_to_int(f)
     }
 
     #[arm_aeabi_alias = __aeabi_f2uiz]
     pub extern "C" fn __fixunssfsi(f: f32) -> u32 {
-        float_to_int!(f, f32, u32)
+        float_to_int(f)
     }
 
     #[arm_aeabi_alias = __aeabi_f2ulz]
     pub extern "C" fn __fixunssfdi(f: f32) -> u64 {
-        float_to_int!(f, f32, u64)
+        float_to_int(f)
     }
 
     #[unadjusted_on_win64]
     pub extern "C" fn __fixunssfti(f: f32) -> u128 {
-        float_to_int!(f, f32, u128)
+        float_to_int(f)
     }
 
     #[arm_aeabi_alias = __aeabi_d2uiz]
     pub extern "C" fn __fixunsdfsi(f: f64) -> u32 {
-        float_to_int!(f, f64, u32)
+        float_to_int(f)
     }
 
     #[arm_aeabi_alias = __aeabi_d2ulz]
     pub extern "C" fn __fixunsdfdi(f: f64) -> u64 {
-        float_to_int!(f, f64, u64)
+        float_to_int(f)
     }
 
     #[unadjusted_on_win64]
     pub extern "C" fn __fixunsdfti(f: f64) -> u128 {
-        float_to_int!(f, f64, u128)
+        float_to_int(f)
     }
 }

+ 34 - 5
src/float/mod.rs

@@ -30,6 +30,9 @@ pub trait Float:
     /// A int of the same with as the float
     type SignedInt: Int;
 
+    /// An int capable of containing the exponent bits plus a sign bit. This is signed.
+    type ExpInt: Int;
+
     const ZERO: Self;
     const ONE: Self;
 
@@ -71,6 +74,18 @@ pub trait Float:
     /// compared.
     fn eq_repr(self, rhs: Self) -> bool;
 
+    /// Returns the sign bit
+    fn sign(self) -> bool;
+
+    /// Returns the exponent with bias
+    fn exp(self) -> Self::ExpInt;
+
+    /// Returns the significand with no implicit bit (or the "fractional" part)
+    fn frac(self) -> Self::Int;
+
+    /// Returns the significand with implicit bit
+    fn imp_frac(self) -> Self::Int;
+
     /// Returns a `Self::Int` transmuted back to `Self`
     fn from_repr(a: Self::Int) -> Self;
 
@@ -81,14 +96,16 @@ pub trait Float:
     fn normalize(significand: Self::Int) -> (i32, Self::Int);
 
     /// Returns if `self` is subnormal
-    fn is_subnormal(&self) -> bool;
+    fn is_subnormal(self) -> bool;
 }
 
 macro_rules! float_impl {
-    ($ty:ident, $ity:ident, $sity:ident, $bits:expr, $significand_bits:expr) => {
+    ($ty:ident, $ity:ident, $sity:ident, $expty:ident, $bits:expr, $significand_bits:expr) => {
         impl Float for $ty {
             type Int = $ity;
             type SignedInt = $sity;
+            type ExpInt = $expty;
+
             const ZERO: Self = 0.0;
             const ONE: Self = 1.0;
 
@@ -113,6 +130,18 @@ macro_rules! float_impl {
                     self.repr() == rhs.repr()
                 }
             }
+            fn sign(self) -> bool {
+                self.signed_repr() < Self::SignedInt::ZERO
+            }
+            fn exp(self) -> Self::ExpInt {
+                ((self.to_bits() & Self::EXPONENT_MASK) >> Self::SIGNIFICAND_BITS) as Self::ExpInt
+            }
+            fn frac(self) -> Self::Int {
+                self.to_bits() & Self::SIGNIFICAND_MASK
+            }
+            fn imp_frac(self) -> Self::Int {
+                self.frac() | Self::IMPLICIT_BIT
+            }
             fn from_repr(a: Self::Int) -> Self {
                 Self::from_bits(a)
             }
@@ -132,12 +161,12 @@ macro_rules! float_impl {
                     significand << shift as Self::Int,
                 )
             }
-            fn is_subnormal(&self) -> bool {
+            fn is_subnormal(self) -> bool {
                 (self.repr() & Self::EXPONENT_MASK) == Self::Int::ZERO
             }
         }
     };
 }
 
-float_impl!(f32, u32, i32, 32, 23);
-float_impl!(f64, u64, i64, 64, 52);
+float_impl!(f32, u32, i32, i16, 32, 23);
+float_impl!(f64, u64, i64, i16, 64, 52);

+ 1 - 2
src/float/pow.rs

@@ -1,5 +1,4 @@
 use float::Float;
-use int::Int;
 
 trait Pow: Float {
     /// Returns `a` raised to the power `b`
@@ -11,7 +10,7 @@ trait Pow: Float {
             if (b & 1) != 0 {
                 r *= a;
             }
-            b = b.aborting_div(2);
+            b = ((b as u32) >> 1) as i32;
             if b == 0 {
                 break;
             }

+ 17 - 53
src/int/mod.rs

@@ -15,9 +15,11 @@ pub use self::leading_zeros::__clzsi2;
 #[doc(hidden)]
 pub trait Int:
     Copy
+    + core::fmt::Debug
     + PartialEq
     + PartialOrd
     + ops::AddAssign
+    + ops::SubAssign
     + ops::BitAndAssign
     + ops::BitOrAssign
     + ops::BitXorAssign
@@ -38,12 +40,16 @@ pub trait Int:
     /// Unsigned version of Self
     type UnsignedInt: Int;
 
+    /// If `Self` is a signed integer
+    const SIGNED: bool;
+
     /// The bitwidth of the int type
     const BITS: u32;
 
     const ZERO: Self;
     const ONE: Self;
     const MIN: Self;
+    const MAX: Self;
 
     /// LUT used for maximizing the space covered and minimizing the computational cost of fuzzing
     /// in `testcrate`. For example, Self = u128 produces [0,1,2,7,8,15,16,31,32,63,64,95,96,111,
@@ -52,18 +58,6 @@ pub trait Int:
     /// The number of entries of `FUZZ_LENGTHS` actually used. The maximum is 20 for u128.
     const FUZZ_NUM: usize;
 
-    /// Extracts the sign from self and returns a tuple.
-    ///
-    /// # Examples
-    ///
-    /// ```rust,ignore
-    /// let i = -25_i32;
-    /// let (sign, u) = i.extract_sign();
-    /// assert_eq!(sign, true);
-    /// assert_eq!(u, 25_u32);
-    /// ```
-    fn extract_sign(self) -> (bool, Self::UnsignedInt);
-
     fn unsigned(self) -> Self::UnsignedInt;
     fn from_unsigned(unsigned: Self::UnsignedInt) -> Self;
 
@@ -77,8 +71,6 @@ pub trait Int:
 
     // copied from primitive integers, but put in a trait
     fn is_zero(self) -> bool;
-    fn max_value() -> Self;
-    fn min_value() -> Self;
     fn wrapping_neg(self) -> Self;
     fn wrapping_add(self, other: Self) -> Self;
     fn wrapping_mul(self, other: Self) -> Self;
@@ -87,25 +79,18 @@ pub trait Int:
     fn wrapping_shr(self, other: u32) -> Self;
     fn rotate_left(self, other: u32) -> Self;
     fn overflowing_add(self, other: Self) -> (Self, bool);
-    fn aborting_div(self, other: Self) -> Self;
-    fn aborting_rem(self, other: Self) -> Self;
     fn leading_zeros(self) -> u32;
 }
 
-fn unwrap<T>(t: Option<T>) -> T {
-    match t {
-        Some(t) => t,
-        None => ::abort(),
-    }
-}
-
 macro_rules! int_impl_common {
     ($ty:ty) => {
         const BITS: u32 = <Self>::BITS;
+        const SIGNED: bool = Self::MIN != Self::ZERO;
 
         const ZERO: Self = 0;
         const ONE: Self = 1;
         const MIN: Self = <Self>::MIN;
+        const MAX: Self = <Self>::MAX;
 
         const FUZZ_LENGTHS: [u8; 20] = {
             let bits = <Self as Int>::BITS;
@@ -177,14 +162,6 @@ macro_rules! int_impl_common {
             self == Self::ZERO
         }
 
-        fn max_value() -> Self {
-            <Self>::max_value()
-        }
-
-        fn min_value() -> Self {
-            <Self>::min_value()
-        }
-
         fn wrapping_neg(self) -> Self {
             <Self>::wrapping_neg(self)
         }
@@ -217,14 +194,6 @@ macro_rules! int_impl_common {
             <Self>::overflowing_add(self, other)
         }
 
-        fn aborting_div(self, other: Self) -> Self {
-            unwrap(<Self>::checked_div(self, other))
-        }
-
-        fn aborting_rem(self, other: Self) -> Self {
-            unwrap(<Self>::checked_rem(self, other))
-        }
-
         fn leading_zeros(self) -> u32 {
             <Self>::leading_zeros(self)
         }
@@ -237,10 +206,6 @@ macro_rules! int_impl {
             type OtherSign = $ity;
             type UnsignedInt = $uty;
 
-            fn extract_sign(self) -> (bool, $uty) {
-                (false, self)
-            }
-
             fn unsigned(self) -> $uty {
                 self
             }
@@ -264,14 +229,6 @@ macro_rules! int_impl {
             type OtherSign = $uty;
             type UnsignedInt = $uty;
 
-            fn extract_sign(self) -> (bool, $uty) {
-                if self < 0 {
-                    (true, (!(self as $uty)).wrapping_add(1))
-                } else {
-                    (false, self as $uty)
-                }
-            }
-
             fn unsigned(self) -> $uty {
                 self as $uty
             }
@@ -395,13 +352,14 @@ impl_h_int!(
 );
 
 /// Trait to express (possibly lossy) casting of integers
-pub(crate) trait CastInto<T: Copy>: Copy {
+#[doc(hidden)]
+pub trait CastInto<T: Copy>: Copy {
     fn cast(self) -> T;
 }
 
 macro_rules! cast_into {
     ($ty:ty) => {
-        cast_into!($ty; usize, isize, u32, i32, u64, i64, u128, i128);
+        cast_into!($ty; usize, isize, u8, i8, u16, i16, u32, i32, u64, i64, u128, i128);
     };
     ($ty:ty; $($into:ty),*) => {$(
         impl CastInto<$into> for $ty {
@@ -412,6 +370,12 @@ macro_rules! cast_into {
     )*};
 }
 
+cast_into!(usize);
+cast_into!(isize);
+cast_into!(u8);
+cast_into!(i8);
+cast_into!(u16);
+cast_into!(i16);
 cast_into!(u32);
 cast_into!(i32);
 cast_into!(u64);

+ 0 - 5
src/lib.rs

@@ -31,11 +31,6 @@
 #[cfg(test)]
 extern crate core;
 
-#[allow(unused_unsafe)]
-fn abort() -> ! {
-    unsafe { core::intrinsics::abort() }
-}
-
 #[macro_use]
 mod macros;
 

+ 1 - 1
testcrate/tests/div_rem.rs

@@ -108,7 +108,7 @@ macro_rules! float {
                 let quo0 = x / y;
                 let quo1: $i = $fn(x, y);
                 // division of subnormals is not currently handled
-                if !(Float::is_subnormal(&quo0) || Float::is_subnormal(&quo1)) {
+                if !(Float::is_subnormal(quo0) || Float::is_subnormal(quo1)) {
                     if !Float::eq_repr(quo0, quo1) {
                         panic!(
                             "{}({}, {}): std: {}, builtins: {}",

+ 1 - 1
testcrate/tests/mul.rs

@@ -86,7 +86,7 @@ macro_rules! float_mul {
                 let mul0 = x * y;
                 let mul1: $f = $fn(x, y);
                 // multiplication of subnormals is not currently handled
-                if !(Float::is_subnormal(&mul0) || Float::is_subnormal(&mul1)) {
+                if !(Float::is_subnormal(mul0) || Float::is_subnormal(mul1)) {
                     if !Float::eq_repr(mul0, mul1) {
                         panic!(
                             "{}({}, {}): std: {}, builtins: {}",