diff --git a/library/compiler-builtins/libm/etc/function-definitions.json b/library/compiler-builtins/libm/etc/function-definitions.json index 8c5903e93b92..7ffe91eadd6f 100644 --- a/library/compiler-builtins/libm/etc/function-definitions.json +++ b/library/compiler-builtins/libm/etc/function-definitions.json @@ -379,26 +379,30 @@ "fmax": { "sources": [ "src/libm_helper.rs", - "src/math/fmax.rs" + "src/math/fmax.rs", + "src/math/generic/fmax.rs" ], "type": "f64" }, "fmaxf": { "sources": [ - "src/math/fmaxf.rs" + "src/math/fmaxf.rs", + "src/math/generic/fmax.rs" ], "type": "f32" }, "fmin": { "sources": [ "src/libm_helper.rs", - "src/math/fmin.rs" + "src/math/fmin.rs", + "src/math/generic/fmin.rs" ], "type": "f64" }, "fminf": { "sources": [ - "src/math/fminf.rs" + "src/math/fminf.rs", + "src/math/generic/fmin.rs" ], "type": "f32" }, diff --git a/library/compiler-builtins/libm/src/math/fmax.rs b/library/compiler-builtins/libm/src/math/fmax.rs index 93c97bc611c7..d5d9b513b849 100644 --- a/library/compiler-builtins/libm/src/math/fmax.rs +++ b/library/compiler-builtins/libm/src/math/fmax.rs @@ -1,12 +1,5 @@ +/// Return the greater of two arguments or, if either argument is NaN, the other argument. #[cfg_attr(all(test, assert_no_panic), no_panic::no_panic)] pub fn fmax(x: f64, y: f64) -> f64 { - // IEEE754 says: maxNum(x, y) is the canonicalized number y if x < y, x if y < x, the - // canonicalized number if one operand is a number and the other a quiet NaN. Otherwise it - // is either x or y, canonicalized (this means results might differ among implementations). - // When either x or y is a signalingNaN, then the result is according to 6.2. - // - // Since we do not support sNaN in Rust yet, we do not need to handle them. - // FIXME(nagisa): due to https://bugs.llvm.org/show_bug.cgi?id=33303 we canonicalize by - // multiplying by 1.0. Should switch to the `canonicalize` when it works. - (if x.is_nan() || x < y { y } else { x }) * 1.0 + super::generic::fmax(x, y) } diff --git a/library/compiler-builtins/libm/src/math/fmaxf.rs b/library/compiler-builtins/libm/src/math/fmaxf.rs index 60774664752d..3197d5cf2ca1 100644 --- a/library/compiler-builtins/libm/src/math/fmaxf.rs +++ b/library/compiler-builtins/libm/src/math/fmaxf.rs @@ -1,12 +1,5 @@ +/// Return the greater of two arguments or, if either argument is NaN, the other argument. #[cfg_attr(all(test, assert_no_panic), no_panic::no_panic)] pub fn fmaxf(x: f32, y: f32) -> f32 { - // IEEE754 says: maxNum(x, y) is the canonicalized number y if x < y, x if y < x, the - // canonicalized number if one operand is a number and the other a quiet NaN. Otherwise it - // is either x or y, canonicalized (this means results might differ among implementations). - // When either x or y is a signalingNaN, then the result is according to 6.2. - // - // Since we do not support sNaN in Rust yet, we do not need to handle them. - // FIXME(nagisa): due to https://bugs.llvm.org/show_bug.cgi?id=33303 we canonicalize by - // multiplying by 1.0. Should switch to the `canonicalize` when it works. - (if x.is_nan() || x < y { y } else { x }) * 1.0 + super::generic::fmax(x, y) } diff --git a/library/compiler-builtins/libm/src/math/fmin.rs b/library/compiler-builtins/libm/src/math/fmin.rs index ab1509f34a65..df8ff7c32e3b 100644 --- a/library/compiler-builtins/libm/src/math/fmin.rs +++ b/library/compiler-builtins/libm/src/math/fmin.rs @@ -1,12 +1,5 @@ +/// Return the lesser of two arguments or, if either argument is NaN, the other argument. #[cfg_attr(all(test, assert_no_panic), no_panic::no_panic)] pub fn fmin(x: f64, y: f64) -> f64 { - // IEEE754 says: minNum(x, y) is the canonicalized number x if x < y, y if y < x, the - // canonicalized number if one operand is a number and the other a quiet NaN. Otherwise it - // is either x or y, canonicalized (this means results might differ among implementations). - // When either x or y is a signalingNaN, then the result is according to 6.2. - // - // Since we do not support sNaN in Rust yet, we do not need to handle them. - // FIXME(nagisa): due to https://bugs.llvm.org/show_bug.cgi?id=33303 we canonicalize by - // multiplying by 1.0. Should switch to the `canonicalize` when it works. - (if y.is_nan() || x < y { x } else { y }) * 1.0 + super::generic::fmin(x, y) } diff --git a/library/compiler-builtins/libm/src/math/fminf.rs b/library/compiler-builtins/libm/src/math/fminf.rs index 0049e7117ae0..b2cdfe89d64d 100644 --- a/library/compiler-builtins/libm/src/math/fminf.rs +++ b/library/compiler-builtins/libm/src/math/fminf.rs @@ -1,12 +1,5 @@ +/// Return the lesser of two arguments or, if either argument is NaN, the other argument. #[cfg_attr(all(test, assert_no_panic), no_panic::no_panic)] pub fn fminf(x: f32, y: f32) -> f32 { - // IEEE754 says: minNum(x, y) is the canonicalized number x if x < y, y if y < x, the - // canonicalized number if one operand is a number and the other a quiet NaN. Otherwise it - // is either x or y, canonicalized (this means results might differ among implementations). - // When either x or y is a signalingNaN, then the result is according to 6.2. - // - // Since we do not support sNaN in Rust yet, we do not need to handle them. - // FIXME(nagisa): due to https://bugs.llvm.org/show_bug.cgi?id=33303 we canonicalize by - // multiplying by 1.0. Should switch to the `canonicalize` when it works. - (if y.is_nan() || x < y { x } else { y }) * 1.0 + super::generic::fmin(x, y) } diff --git a/library/compiler-builtins/libm/src/math/generic/fmax.rs b/library/compiler-builtins/libm/src/math/generic/fmax.rs new file mode 100644 index 000000000000..97803052bc27 --- /dev/null +++ b/library/compiler-builtins/libm/src/math/generic/fmax.rs @@ -0,0 +1,14 @@ +use super::super::Float; + +#[cfg_attr(all(test, assert_no_panic), no_panic::no_panic)] +pub fn fmax(x: F, y: F) -> F { + // IEEE754 says: maxNum(x, y) is the canonicalized number y if x < y, x if y < x, the + // canonicalized number if one operand is a number and the other a quiet NaN. Otherwise it + // is either x or y, canonicalized (this means results might differ among implementations). + // When either x or y is a signalingNaN, then the result is according to 6.2. + // + // Since we do not support sNaN in Rust yet, we do not need to handle them. + // FIXME(nagisa): due to https://bugs.llvm.org/show_bug.cgi?id=33303 we canonicalize by + // multiplying by 1.0. Should switch to the `canonicalize` when it works. + (if x.is_nan() || x < y { y } else { x }) * F::ONE +} diff --git a/library/compiler-builtins/libm/src/math/generic/fmin.rs b/library/compiler-builtins/libm/src/math/generic/fmin.rs new file mode 100644 index 000000000000..697f72004860 --- /dev/null +++ b/library/compiler-builtins/libm/src/math/generic/fmin.rs @@ -0,0 +1,13 @@ +use super::super::Float; + +pub fn fmin(x: F, y: F) -> F { + // IEEE754 says: minNum(x, y) is the canonicalized number x if x < y, y if y < x, the + // canonicalized number if one operand is a number and the other a quiet NaN. Otherwise it + // is either x or y, canonicalized (this means results might differ among implementations). + // When either x or y is a signalingNaN, then the result is according to 6.2. + // + // Since we do not support sNaN in Rust yet, we do not need to handle them. + // FIXME(nagisa): due to https://bugs.llvm.org/show_bug.cgi?id=33303 we canonicalize by + // multiplying by 1.0. Should switch to the `canonicalize` when it works. + (if y.is_nan() || x < y { x } else { y }) * F::ONE +} diff --git a/library/compiler-builtins/libm/src/math/generic/mod.rs b/library/compiler-builtins/libm/src/math/generic/mod.rs index 1f557719f42c..819781a219aa 100644 --- a/library/compiler-builtins/libm/src/math/generic/mod.rs +++ b/library/compiler-builtins/libm/src/math/generic/mod.rs @@ -3,6 +3,8 @@ mod copysign; mod fabs; mod fdim; mod floor; +mod fmax; +mod fmin; mod rint; mod round; mod scalbn; @@ -14,6 +16,8 @@ pub use copysign::copysign; pub use fabs::fabs; pub use fdim::fdim; pub use floor::floor; +pub use fmax::fmax; +pub use fmin::fmin; pub use rint::rint; pub use round::round; pub use scalbn::scalbn;