aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog17
-rw-r--r--sysdeps/ieee754/ldbl-128ibm/Makefile3
-rw-r--r--sysdeps/ieee754/ldbl-128ibm/e_remainderl.c4
-rw-r--r--sysdeps/ieee754/ldbl-128ibm/test-fmodl-ldbl-128ibm.c62
-rw-r--r--sysdeps/ieee754/ldbl-128ibm/test-fmodrem-ldbl-128ibm.c84
-rw-r--r--sysdeps/ieee754/ldbl-128ibm/test-remainderl-ldbl-128ibm.c21
-rw-r--r--sysdeps/ieee754/ldbl-128ibm/test-remquol-ldbl-128ibm.c30
7 files changed, 161 insertions, 60 deletions
diff --git a/ChangeLog b/ChangeLog
index 50e32e0..3cb82bc 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,20 @@
+2016-03-08 Joseph Myers <joseph@codesourcery.com>
+
+ [BZ #19677]
+ * sysdeps/ieee754/ldbl-128ibm/e_remainderl.c
+ (__ieee754_remainderl): Put zero low parts in canonical form.
+ * sysdeps/ieee754/ldbl-128ibm/test-fmodrem-ldbl-128ibm.c: New
+ file. Based on
+ sysdeps/ieee754/ldbl-128ibm/test-fmodl-ldbl-128ibm.c.
+ * sysdeps/ieee754/ldbl-128ibm/test-fmodl-ldbl-128ibm.c: Replace
+ with wrapper round test-fmodrem-ldbl-128ibm.c.
+ * sysdeps/ieee754/ldbl-128ibm/test-remainderl-ldbl-128ibm.c: New
+ file.
+ * sysdeps/ieee754/ldbl-128ibm/test-remquol-ldbl-128ibm.c:
+ Likewise.
+ * sysdeps/ieee754/ldbl-128ibm/Makefile (tests): Add
+ test-remainderl-ldbl-128ibm and test-remquol-ldbl-128ibm.
+
2016-03-07 Florian Weimer <fweimer@redhat.com>
[BZ #19610]
diff --git a/sysdeps/ieee754/ldbl-128ibm/Makefile b/sysdeps/ieee754/ldbl-128ibm/Makefile
index b633172..6242edd 100644
--- a/sysdeps/ieee754/ldbl-128ibm/Makefile
+++ b/sysdeps/ieee754/ldbl-128ibm/Makefile
@@ -10,5 +10,6 @@ $(objpfx)tst-strtold-ldbl-128ibm: $(libm)
endif
ifeq ($(subdir),math)
-tests += test-fmodl-ldbl-128ibm
+tests += test-fmodl-ldbl-128ibm test-remainderl-ldbl-128ibm \
+ test-remquol-ldbl-128ibm
endif
diff --git a/sysdeps/ieee754/ldbl-128ibm/e_remainderl.c b/sysdeps/ieee754/ldbl-128ibm/e_remainderl.c
index 1dc59a4..68b8fb3 100644
--- a/sysdeps/ieee754/ldbl-128ibm/e_remainderl.c
+++ b/sysdeps/ieee754/ldbl-128ibm/e_remainderl.c
@@ -46,6 +46,10 @@ __ieee754_remainderl(long double x, long double p)
hp &= 0x7fffffffffffffffLL;
lx ^= sx;
hx &= 0x7fffffffffffffffLL;
+ if (lp == 0x8000000000000000ULL)
+ lp = 0;
+ if (lx == 0x8000000000000000ULL)
+ lx = 0;
/* purge off exception values */
if(hp==0) return (x*p)/(x*p); /* p = 0 */
diff --git a/sysdeps/ieee754/ldbl-128ibm/test-fmodl-ldbl-128ibm.c b/sysdeps/ieee754/ldbl-128ibm/test-fmodl-ldbl-128ibm.c
index 3717c90..73d4bc1 100644
--- a/sysdeps/ieee754/ldbl-128ibm/test-fmodl-ldbl-128ibm.c
+++ b/sysdeps/ieee754/ldbl-128ibm/test-fmodl-ldbl-128ibm.c
@@ -16,62 +16,6 @@
License along with the GNU C Library; if not, see
<http://www.gnu.org/licenses/>. */
-#include <float.h>
-#include <math.h>
-#include <stdio.h>
-
-union u
-{
- long double ld;
- double d[2];
-};
-
-volatile union u p1 = { .d = { DBL_MIN, 0.0 } };
-volatile union u p2 = { .d = { DBL_MIN, -0.0 } };
-volatile union u m1 = { .d = { -DBL_MIN, 0.0 } };
-volatile union u m2 = { .d = { -DBL_MIN, -0.0 } };
-
-static int
-test_fmodl (const char *s, long double x, long double y, long double expected)
-{
- volatile long double r;
- r = fmodl (x, y);
- if (r != expected || copysignl (1.0, r) != copysignl (1.0, expected))
- {
- printf ("FAIL: fmodl (%s)\n", s);
- return 1;
- }
- else
- {
- printf ("PASS: fmodl (%s)\n", s);
- return 0;
- }
-}
-
-#define TEST_FMODL(a, b, e) test_fmodl (#a ", " #b, a, b, e)
-
-static int
-do_test (void)
-{
- int result = 0;
- result |= TEST_FMODL (p1.ld, p1.ld, 0.0L);
- result |= TEST_FMODL (p1.ld, p2.ld, 0.0L);
- result |= TEST_FMODL (p1.ld, m1.ld, 0.0L);
- result |= TEST_FMODL (p1.ld, m2.ld, 0.0L);
- result |= TEST_FMODL (p2.ld, p1.ld, 0.0L);
- result |= TEST_FMODL (p2.ld, p2.ld, 0.0L);
- result |= TEST_FMODL (p2.ld, m1.ld, 0.0L);
- result |= TEST_FMODL (p2.ld, m2.ld, 0.0L);
- result |= TEST_FMODL (m1.ld, p1.ld, -0.0L);
- result |= TEST_FMODL (m1.ld, p2.ld, -0.0L);
- result |= TEST_FMODL (m1.ld, m1.ld, -0.0L);
- result |= TEST_FMODL (m1.ld, m2.ld, -0.0L);
- result |= TEST_FMODL (m2.ld, p1.ld, -0.0L);
- result |= TEST_FMODL (m2.ld, p2.ld, -0.0L);
- result |= TEST_FMODL (m2.ld, m1.ld, -0.0L);
- result |= TEST_FMODL (m2.ld, m2.ld, -0.0L);
- return result;
-}
-
-#define TEST_FUNCTION do_test ()
-#include "../../../test-skeleton.c"
+#define FUNC fmodl
+#define SETUP
+#include "test-fmodrem-ldbl-128ibm.c"
diff --git a/sysdeps/ieee754/ldbl-128ibm/test-fmodrem-ldbl-128ibm.c b/sysdeps/ieee754/ldbl-128ibm/test-fmodrem-ldbl-128ibm.c
new file mode 100644
index 0000000..4e1640c
--- /dev/null
+++ b/sysdeps/ieee754/ldbl-128ibm/test-fmodrem-ldbl-128ibm.c
@@ -0,0 +1,84 @@
+/* Test for ldbl-128ibm fmodl etc. handling of equal values.
+ Copyright (C) 2016 Free Software Foundation, Inc.
+ This file is part of the GNU C Library.
+
+ The GNU C Library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Lesser General Public
+ License as published by the Free Software Foundation; either
+ version 2.1 of the License, or (at your option) any later version.
+
+ The GNU C Library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public
+ License along with the GNU C Library; if not, see
+ <http://www.gnu.org/licenses/>. */
+
+#include <fenv.h>
+#include <float.h>
+#include <math.h>
+#include <stdio.h>
+
+/* FUNC is defined to be the name of the function to test. */
+#define STRX(x) #x
+#define STR(x) STRX (x)
+#define SFUNC STR (FUNC)
+
+union u
+{
+ long double ld;
+ double d[2];
+};
+
+volatile union u p1 = { .d = { DBL_MIN, 0.0 } };
+volatile union u p2 = { .d = { DBL_MIN, -0.0 } };
+volatile union u m1 = { .d = { -DBL_MIN, 0.0 } };
+volatile union u m2 = { .d = { -DBL_MIN, -0.0 } };
+
+static int
+test_func (const char *s, long double x, long double y, long double expected)
+{
+ volatile long double r;
+ r = FUNC (x, y);
+ if (r != expected || copysignl (1.0, r) != copysignl (1.0, expected))
+ {
+ printf ("FAIL: " SFUNC " (%s)\n", s);
+ return 1;
+ }
+ else
+ {
+ printf ("PASS: " SFUNC " (%s)\n", s);
+ return 0;
+ }
+}
+
+#define TEST_FUNC(a, b, e) test_func (#a ", " #b, a, b, e)
+
+static int
+do_test (void)
+{
+ int result = 0;
+ SETUP;
+ result |= TEST_FUNC (p1.ld, p1.ld, 0.0L);
+ result |= TEST_FUNC (p1.ld, p2.ld, 0.0L);
+ result |= TEST_FUNC (p1.ld, m1.ld, 0.0L);
+ result |= TEST_FUNC (p1.ld, m2.ld, 0.0L);
+ result |= TEST_FUNC (p2.ld, p1.ld, 0.0L);
+ result |= TEST_FUNC (p2.ld, p2.ld, 0.0L);
+ result |= TEST_FUNC (p2.ld, m1.ld, 0.0L);
+ result |= TEST_FUNC (p2.ld, m2.ld, 0.0L);
+ result |= TEST_FUNC (m1.ld, p1.ld, -0.0L);
+ result |= TEST_FUNC (m1.ld, p2.ld, -0.0L);
+ result |= TEST_FUNC (m1.ld, m1.ld, -0.0L);
+ result |= TEST_FUNC (m1.ld, m2.ld, -0.0L);
+ result |= TEST_FUNC (m2.ld, p1.ld, -0.0L);
+ result |= TEST_FUNC (m2.ld, p2.ld, -0.0L);
+ result |= TEST_FUNC (m2.ld, m1.ld, -0.0L);
+ result |= TEST_FUNC (m2.ld, m2.ld, -0.0L);
+ return result;
+}
+
+#define TEST_FUNCTION do_test ()
+#include "../../../test-skeleton.c"
diff --git a/sysdeps/ieee754/ldbl-128ibm/test-remainderl-ldbl-128ibm.c b/sysdeps/ieee754/ldbl-128ibm/test-remainderl-ldbl-128ibm.c
new file mode 100644
index 0000000..767a670
--- /dev/null
+++ b/sysdeps/ieee754/ldbl-128ibm/test-remainderl-ldbl-128ibm.c
@@ -0,0 +1,21 @@
+/* Test for ldbl-128ibm remainderl handling of equal values (bug 19677).
+ Copyright (C) 2016 Free Software Foundation, Inc.
+ This file is part of the GNU C Library.
+
+ The GNU C Library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Lesser General Public
+ License as published by the Free Software Foundation; either
+ version 2.1 of the License, or (at your option) any later version.
+
+ The GNU C Library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public
+ License along with the GNU C Library; if not, see
+ <http://www.gnu.org/licenses/>. */
+
+#define FUNC remainderl
+#define SETUP fesetround (FE_DOWNWARD)
+#include "test-fmodrem-ldbl-128ibm.c"
diff --git a/sysdeps/ieee754/ldbl-128ibm/test-remquol-ldbl-128ibm.c b/sysdeps/ieee754/ldbl-128ibm/test-remquol-ldbl-128ibm.c
new file mode 100644
index 0000000..b691e3f
--- /dev/null
+++ b/sysdeps/ieee754/ldbl-128ibm/test-remquol-ldbl-128ibm.c
@@ -0,0 +1,30 @@
+/* Test for ldbl-128ibm remquol handling of equal values (bug 19677).
+ Copyright (C) 2016 Free Software Foundation, Inc.
+ This file is part of the GNU C Library.
+
+ The GNU C Library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Lesser General Public
+ License as published by the Free Software Foundation; either
+ version 2.1 of the License, or (at your option) any later version.
+
+ The GNU C Library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public
+ License along with the GNU C Library; if not, see
+ <http://www.gnu.org/licenses/>. */
+
+#include <math.h>
+
+static long double
+wrap_remquol (long double x, long double y)
+{
+ int quo;
+ return remquol (x, y, &quo);
+}
+
+#define FUNC wrap_remquol
+#define SETUP fesetround (FE_DOWNWARD)
+#include "test-fmodrem-ldbl-128ibm.c"