This is the mail archive of the
libc-alpha@sourceware.org
mailing list for the glibc project.
Fix ldbl-128 lrintl, lroundl missing exceptions for 32-bit long (bug 19085) [committed]
- From: Joseph Myers <joseph at codesourcery dot com>
- To: <libc-alpha at sourceware dot org>
- Date: Wed, 7 Oct 2015 16:12:07 +0000
- Subject: Fix ldbl-128 lrintl, lroundl missing exceptions for 32-bit long (bug 19085) [committed]
- Authentication-results: sourceware.org; auth=none
The ldbl-128 implementations of lrintl and lroundl miss "invalid"
exceptions on systems with 32-bit long for arguments that overflow
long but have exponent below 48. This patch fixes this by rearranging
the sequence of tests in the code so the exponent < 48 case is only
used for exponents that don't overflow long.
Tested for mips64 (n32 and n64). Committed.
2015-10-07 Joseph Myers <joseph@codesourcery.com>
[BZ #19085]
* sysdeps/ieee754/ldbl-128/s_lrintl.c (__lrintl): Move test for
exponent below 48 inside case for non-overflowing exponent.
* sysdeps/ieee754/ldbl-128/s_lroundl.c (__lroundl): Likewise.
diff --git a/sysdeps/ieee754/ldbl-128/s_lrintl.c b/sysdeps/ieee754/ldbl-128/s_lrintl.c
index b0e0cfc..d0b0aeb 100644
--- a/sysdeps/ieee754/ldbl-128/s_lrintl.c
+++ b/sysdeps/ieee754/ldbl-128/s_lrintl.c
@@ -45,20 +45,20 @@ __lrintl (long double x)
i0 &= 0x0000ffffffffffffLL;
i0 |= 0x0001000000000000LL;
- if (j0 < 48)
+ if (j0 < (int32_t) (8 * sizeof (long int)) - 1)
{
- w = two112[sx] + x;
- t = w - two112[sx];
- GET_LDOUBLE_WORDS64 (i0, i1, t);
- j0 = ((i0 >> 48) & 0x7fff) - 0x3fff;
- i0 &= 0x0000ffffffffffffLL;
- i0 |= 0x0001000000000000LL;
+ if (j0 < 48)
+ {
+ w = two112[sx] + x;
+ t = w - two112[sx];
+ GET_LDOUBLE_WORDS64 (i0, i1, t);
+ j0 = ((i0 >> 48) & 0x7fff) - 0x3fff;
+ i0 &= 0x0000ffffffffffffLL;
+ i0 |= 0x0001000000000000LL;
- result = (j0 < 0 ? 0 : i0 >> (48 - j0));
- }
- else if (j0 < (int32_t) (8 * sizeof (long int)) - 1)
- {
- if (j0 >= 112)
+ result = (j0 < 0 ? 0 : i0 >> (48 - j0));
+ }
+ else if (j0 >= 112)
result = ((long int) i0 << (j0 - 48)) | (i1 << (j0 - 112));
else
{
diff --git a/sysdeps/ieee754/ldbl-128/s_lroundl.c b/sysdeps/ieee754/ldbl-128/s_lroundl.c
index 8421609..64b285e 100644
--- a/sysdeps/ieee754/ldbl-128/s_lroundl.c
+++ b/sysdeps/ieee754/ldbl-128/s_lroundl.c
@@ -37,19 +37,19 @@ __lroundl (long double x)
i0 &= 0x0000ffffffffffffLL;
i0 |= 0x0001000000000000LL;
- if (j0 < 48)
+ if (j0 < (int32_t) (8 * sizeof (long int)) - 1)
{
- if (j0 < 0)
- return j0 < -1 ? 0 : sign;
- else
+ if (j0 < 48)
{
- i0 += 0x0000800000000000LL >> j0;
- result = i0 >> (48 - j0);
+ if (j0 < 0)
+ return j0 < -1 ? 0 : sign;
+ else
+ {
+ i0 += 0x0000800000000000LL >> j0;
+ result = i0 >> (48 - j0);
+ }
}
- }
- else if (j0 < (int32_t) (8 * sizeof (long int)) - 1)
- {
- if (j0 >= 112)
+ else if (j0 >= 112)
result = ((long int) i0 << (j0 - 48)) | (i1 << (j0 - 112));
else
{
--
Joseph S. Myers
joseph@codesourcery.com