From 77782516eb51b13ce913730d6522843721cef913 Mon Sep 17 00:00:00 2001 From: stefanf Date: Fri, 22 Apr 2005 08:30:33 +0000 Subject: Fix raising the inexact exception (FE_INEXACT) if the result differs from the argument. Noticed by: das --- lib/msun/src/s_ceill.c | 19 ++++++++++++------- lib/msun/src/s_floorl.c | 19 ++++++++++++------- lib/msun/src/s_truncl.c | 14 ++++++++++---- 3 files changed, 34 insertions(+), 18 deletions(-) (limited to 'lib') diff --git a/lib/msun/src/s_ceill.c b/lib/msun/src/s_ceill.c index 92f5033..1de973b 100644 --- a/lib/msun/src/s_ceill.c +++ b/lib/msun/src/s_ceill.c @@ -50,6 +50,8 @@ static char rcsid[] = "$FreeBSD$"; } while (0) #endif +static const long double huge = 1.0e300; + long double ceill(long double x) { @@ -58,13 +60,14 @@ ceill(long double x) if (e < MANH_SIZE - 1) { if (e < 0) { /* raise inexact if x != 0 */ - if (u.bits.exp > 0 || (u.bits.manh | u.bits.manl) != 0) - u.e = u.bits.sign ? 0.0 : 1.0; + if (huge + x > 0.0) + if (u.bits.exp > 0 || + (u.bits.manh | u.bits.manl) != 0) + u.e = u.bits.sign ? 0.0 : 1.0; } else { uint64_t m = ((1llu << MANH_SIZE) - 1) >> (e + 1); if (((u.bits.manh & m) | u.bits.manl) == 0) return (x); /* x is integral */ - /* raise inexact flag */ if (!u.bits.sign) { #ifdef LDBL_IMPLICIT_NBIT if (e == 0) @@ -73,14 +76,15 @@ ceill(long double x) #endif INC_MANH(u, 1llu << (MANH_SIZE - e - 1)); } - u.bits.manh &= ~m; - u.bits.manl = 0; + if (huge + x > 0.0) { /* raise inexact flag */ + u.bits.manh &= ~m; + u.bits.manl = 0; + } } } else if (e < LDBL_MANT_DIG - 1) { uint64_t m = (uint64_t)-1 >> (64 - LDBL_MANT_DIG + e + 1); if ((u.bits.manl & m) == 0) return (x); /* x is integral */ - /* raise inexact flag */ if (!u.bits.sign) { if (e == MANH_SIZE - 1) INC_MANH(u, 1); @@ -91,7 +95,8 @@ ceill(long double x) INC_MANH(u, 1); } } - u.bits.manl &= ~m; + if (huge + x > 0.0) /* raise inexact flag */ + u.bits.manl &= ~m; } return (u.e); } diff --git a/lib/msun/src/s_floorl.c b/lib/msun/src/s_floorl.c index 571d26c..9dd13b6 100644 --- a/lib/msun/src/s_floorl.c +++ b/lib/msun/src/s_floorl.c @@ -50,6 +50,8 @@ static char rcsid[] = "$FreeBSD$"; } while (0) #endif +static const long double huge = 1.0e300; + long double floorl(long double x) { @@ -58,13 +60,14 @@ floorl(long double x) if (e < MANH_SIZE - 1) { if (e < 0) { /* raise inexact if x != 0 */ - if (u.bits.exp > 0 || (u.bits.manh | u.bits.manl) != 0) - u.e = u.bits.sign ? -1.0 : 0.0; + if (huge + x > 0.0) + if (u.bits.exp > 0 || + (u.bits.manh | u.bits.manl) != 0) + u.e = u.bits.sign ? -1.0 : 0.0; } else { uint64_t m = ((1llu << MANH_SIZE) - 1) >> (e + 1); if (((u.bits.manh & m) | u.bits.manl) == 0) return (x); /* x is integral */ - /* raise inexact flag */ if (u.bits.sign) { #ifdef LDBL_IMPLICIT_NBIT if (e == 0) @@ -73,14 +76,15 @@ floorl(long double x) #endif INC_MANH(u, 1llu << (MANH_SIZE - e - 1)); } - u.bits.manh &= ~m; - u.bits.manl = 0; + if (huge + x > 0.0) { /* raise inexact flag */ + u.bits.manh &= ~m; + u.bits.manl = 0; + } } } else if (e < LDBL_MANT_DIG - 1) { uint64_t m = (uint64_t)-1 >> (64 - LDBL_MANT_DIG + e + 1); if ((u.bits.manl & m) == 0) return (x); /* x is integral */ - /* raise inexact flag */ if (u.bits.sign) { if (e == MANH_SIZE - 1) INC_MANH(u, 1); @@ -91,7 +95,8 @@ floorl(long double x) INC_MANH(u, 1); } } - u.bits.manl &= ~m; + if (huge + x > 0.0) /* raise inexact flag */ + u.bits.manl &= ~m; } return (u.e); } diff --git a/lib/msun/src/s_truncl.c b/lib/msun/src/s_truncl.c index d535e9c..c475b90 100644 --- a/lib/msun/src/s_truncl.c +++ b/lib/msun/src/s_truncl.c @@ -36,6 +36,8 @@ static char rcsid[] = "$FreeBSD$"; #define MANH_SIZE LDBL_MANH_SIZE #endif +static const long double huge = 1.0e300; + long double truncl(long double x) { @@ -44,19 +46,23 @@ truncl(long double x) if (e < MANH_SIZE - 1) { if (e < 0) { /* raise inexact if x != 0 */ - u.e = 0.0; + if (huge + x > 0.0) + u.e = 0.0; } else { uint64_t m = ((1llu << MANH_SIZE) - 1) >> (e + 1); if (((u.bits.manh & m) | u.bits.manl) == 0) return (x); /* x is integral */ - u.bits.manh &= ~m; - u.bits.manl = 0; + if (huge + x > 0.0) { /* raise inexact flag */ + u.bits.manh &= ~m; + u.bits.manl = 0; + } } } else if (e < LDBL_MANT_DIG - 1) { uint64_t m = (uint64_t)-1 >> (64 - LDBL_MANT_DIG + e + 1); if ((u.bits.manl & m) == 0) return (x); /* x is integral */ - u.bits.manl &= ~m; + if (huge + x > 0.0) /* raise inexact flag */ + u.bits.manl &= ~m; } return (u.e); } -- cgit v1.1