summaryrefslogtreecommitdiff
path: root/math
diff options
context:
space:
mode:
authorChris Metcalf <cmetcalf@tilera.com>2012-05-17 08:49:19 -0400
committerChris Metcalf <cmetcalf@tilera.com>2012-05-17 08:50:41 -0400
commit0af797def371ceb4f05586d7bcd25841653d2082 (patch)
tree3aa5591836c95fba6b694fb45c1421bf0025de91 /math
parente39745ffa030f685fbba13534a3023d52a27ead8 (diff)
downloadglibc-0af797def371ceb4f05586d7bcd25841653d2082.tar.gz
math: support platforms with limited FP rounding or exception support
For some tests, just claim that fetestexcept() always returns true, so the rest of the test can be compiled. For libm-test, provide known bogus values for unsupported rounding modes, so fesetround() will return failure. Elsewhere, just add some #ifdefs to avoid code that uses particular FP exceptions if the exceptions aren't supported.
Diffstat (limited to 'math')
-rw-r--r--math/bug-nextafter.c6
-rw-r--r--math/bug-nexttoward.c6
-rw-r--r--math/libm-test.inc16
-rw-r--r--math/test-fenv.c6
-rw-r--r--math/test-misc.c6
5 files changed, 40 insertions, 0 deletions
diff --git a/math/bug-nextafter.c b/math/bug-nextafter.c
index 1d21841ea6..558b158391 100644
--- a/math/bug-nextafter.c
+++ b/math/bug-nextafter.c
@@ -4,6 +4,12 @@
#include <stdlib.h>
#include <stdio.h>
+#if !defined(FE_OVERFLOW) && !defined(FE_UNDERFLOW)
+/* If there's no support for the exceptions this test is checking,
+ then just return success and allow the test to be compiled. */
+# define fetestexcept(e) 1
+#endif
+
float zero = 0.0;
float inf = INFINITY;
diff --git a/math/bug-nexttoward.c b/math/bug-nexttoward.c
index ff57e5e3f5..cedb7767b6 100644
--- a/math/bug-nexttoward.c
+++ b/math/bug-nexttoward.c
@@ -4,6 +4,12 @@
#include <stdlib.h>
#include <stdio.h>
+#if !defined(FE_OVERFLOW) && !defined(FE_UNDERFLOW)
+/* If there's no support for the exceptions this test is checking,
+ then just return success and allow the test to be compiled. */
+# define fetestexcept(e) 1
+#endif
+
float zero = 0.0;
float inf = INFINITY;
diff --git a/math/libm-test.inc b/math/libm-test.inc
index 5a38dbf3a7..47bbd5f1ef 100644
--- a/math/libm-test.inc
+++ b/math/libm-test.inc
@@ -128,6 +128,22 @@
#include <string.h>
#include <argp.h>
+/* Allow platforms without all rounding modes to test properly,
+ assuming they provide an __FE_UNDEFINED in <bits/fenv.h> which
+ causes fesetround() to return failure. */
+#ifndef FE_TONEAREST
+# define FE_TONEAREST __FE_UNDEFINED
+#endif
+#ifndef FE_TOWARDZERO
+# define FE_TOWARDZERO __FE_UNDEFINED
+#endif
+#ifndef FE_UPWARD
+# define FE_UPWARD __FE_UNDEFINED
+#endif
+#ifndef FE_DOWNWARD
+# define FE_DOWNWARD __FE_UNDEFINED
+#endif
+
/* Possible exceptions */
#define NO_EXCEPTION 0x0
#define INVALID_EXCEPTION 0x1
diff --git a/math/test-fenv.c b/math/test-fenv.c
index 39c7c33459..19e5415f73 100644
--- a/math/test-fenv.c
+++ b/math/test-fenv.c
@@ -664,9 +664,11 @@ feholdexcept_tests (void)
}
#endif
test_exceptions ("feholdexcept_tests 0 test", NO_EXC, 0);
+#ifdef FE_INVALID
feraiseexcept (FE_INVALID);
test_exceptions ("feholdexcept_tests FE_INVALID test",
INVALID_EXC, 0);
+#endif
res = feupdateenv (&saved);
if (res != 0)
{
@@ -684,7 +686,9 @@ feholdexcept_tests (void)
test_exceptions ("feholdexcept_tests FE_DIVBYZERO|FE_INVALID test",
DIVBYZERO_EXC | INVALID_EXC, 0);
feclearexcept (FE_ALL_EXCEPT);
+#ifdef FE_INVALID
feraiseexcept (FE_INVALID);
+#endif
#if defined FE_TONEAREST && defined FE_UPWARD
res = fesetround (FE_UPWARD);
if (res != 0)
@@ -708,9 +712,11 @@ feholdexcept_tests (void)
}
#endif
test_exceptions ("feholdexcept_tests 0 2nd test", NO_EXC, 0);
+#ifdef FE_INEXACT
feraiseexcept (FE_INEXACT);
test_exceptions ("feholdexcept_tests FE_INEXACT test",
INEXACT_EXC, 0);
+#endif
res = feupdateenv (&saved2);
if (res != 0)
{
diff --git a/math/test-misc.c b/math/test-misc.c
index c0fe5f7a18..55da359ce5 100644
--- a/math/test-misc.c
+++ b/math/test-misc.c
@@ -1186,12 +1186,14 @@ main (void)
(void) &f2;
feclearexcept (FE_ALL_EXCEPT);
f2 += f1;
+#if defined(FE_OVERFLOW) && defined(FE_INEXACT)
int fe = fetestexcept (FE_ALL_EXCEPT);
if (fe != (FE_OVERFLOW | FE_INEXACT))
{
printf ("float overflow test failed: %x\n", fe);
result = 1;
}
+#endif
volatile double d1 = DBL_MAX;
volatile double d2 = DBL_MAX / 2;
@@ -1199,12 +1201,14 @@ main (void)
(void) &d2;
feclearexcept (FE_ALL_EXCEPT);
d2 += d1;
+#if defined(FE_OVERFLOW) && defined(FE_INEXACT)
fe = fetestexcept (FE_ALL_EXCEPT);
if (fe != (FE_OVERFLOW | FE_INEXACT))
{
printf ("double overflow test failed: %x\n", fe);
result = 1;
}
+#endif
#ifndef NO_LONG_DOUBLE
volatile long double ld1 = LDBL_MAX;
@@ -1213,12 +1217,14 @@ main (void)
(void) &ld2;
feclearexcept (FE_ALL_EXCEPT);
ld2 += ld1;
+# if defined(FE_OVERFLOW) && defined(FE_INEXACT)
fe = fetestexcept (FE_ALL_EXCEPT);
if (fe != (FE_OVERFLOW | FE_INEXACT))
{
printf ("long double overflow test failed: %x\n", fe);
result = 1;
}
+# endif
#endif
#if !defined NO_LONG_DOUBLE && LDBL_MANT_DIG == 113