From 46e4b5e5124374b6622d6e10f94364d3b8544fda Mon Sep 17 00:00:00 2001 From: Bruno Haible Date: Sat, 7 Oct 2023 15:09:23 +0200 Subject: [PATCH] tests: Refactor functions for quiet NaNs. * tests/qnan.h: New file, based on tests/totalorder.c. * tests/nan.h: Add double-inclusion guard. * tests/test-signbit.c: Include qnan.h. (test_signbitf, test_signbitd, test_signbitl): Simplify. * tests/test-totalorder.c: Include qnan.h instead of NaN.h. (TOTALORDER_NAN): Remove macro. (TOTALORDER_POSITIVE_NAN, TOTALORDER_NEGATIVE_NAN): New macros. (positive_nan, negative_nan): Remove functions. (main): Update. * tests/test-totalorderf.c (TOTALORDER_NAN): Remove macro. (TOTALORDER_POSITIVE_NAN, TOTALORDER_NEGATIVE_NAN): New macros. * tests/test-totalorderl.c (TOTALORDER_NAN): Remove macro. (TOTALORDER_POSITIVE_NAN, TOTALORDER_NEGATIVE_NAN): New macros. * modules/signbit-tests (Files): Add tests/nan.h, tests/qnan.h. * modules/totalorder-tests (Files): Add tests/qnan.h. (Depends-on): Add signbit. * modules/totalorderf-tests (Files): Add tests/qnan.h. (Depends-on): Add signbit. * modules/totalorderl-tests (Files): Add tests/qnan.h. (Depends-on): Add signbit. --- ChangeLog | 24 ++++++++++++ modules/signbit-tests | 2 + modules/totalorder-tests | 2 + modules/totalorderf-tests | 2 + modules/totalorderl-tests | 2 + tests/nan.h | 8 +++- tests/qnan.h | 82 +++++++++++++++++++++++++++++++++++++++ tests/test-signbit.c | 40 ++++--------------- tests/test-totalorder.c | 29 +++----------- tests/test-totalorderf.c | 3 +- tests/test-totalorderl.c | 3 +- 11 files changed, 137 insertions(+), 60 deletions(-) create mode 100644 tests/qnan.h diff --git a/ChangeLog b/ChangeLog index 94f8906aef..0a0a6a3338 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,27 @@ +2023-10-07 Bruno Haible + + tests: Refactor functions for quiet NaNs. + * tests/qnan.h: New file, based on tests/totalorder.c. + * tests/nan.h: Add double-inclusion guard. + * tests/test-signbit.c: Include qnan.h. + (test_signbitf, test_signbitd, test_signbitl): Simplify. + * tests/test-totalorder.c: Include qnan.h instead of NaN.h. + (TOTALORDER_NAN): Remove macro. + (TOTALORDER_POSITIVE_NAN, TOTALORDER_NEGATIVE_NAN): New macros. + (positive_nan, negative_nan): Remove functions. + (main): Update. + * tests/test-totalorderf.c (TOTALORDER_NAN): Remove macro. + (TOTALORDER_POSITIVE_NAN, TOTALORDER_NEGATIVE_NAN): New macros. + * tests/test-totalorderl.c (TOTALORDER_NAN): Remove macro. + (TOTALORDER_POSITIVE_NAN, TOTALORDER_NEGATIVE_NAN): New macros. + * modules/signbit-tests (Files): Add tests/nan.h, tests/qnan.h. + * modules/totalorder-tests (Files): Add tests/qnan.h. + (Depends-on): Add signbit. + * modules/totalorderf-tests (Files): Add tests/qnan.h. + (Depends-on): Add signbit. + * modules/totalorderl-tests (Files): Add tests/qnan.h. + (Depends-on): Add signbit. + 2023-10-07 Bruno Haible totalorder*: Fix compilation error on glibc 2.25..2.30. diff --git a/modules/signbit-tests b/modules/signbit-tests index 65d5602b90..9465de790b 100644 --- a/modules/signbit-tests +++ b/modules/signbit-tests @@ -2,6 +2,8 @@ Files: tests/test-signbit.c tests/minus-zero.h tests/infinity.h +tests/nan.h +tests/qnan.h tests/macros.h m4/exponentf.m4 m4/exponentd.m4 diff --git a/modules/totalorder-tests b/modules/totalorder-tests index fbcfb11a99..43eff42e7a 100644 --- a/modules/totalorder-tests +++ b/modules/totalorder-tests @@ -3,9 +3,11 @@ tests/test-totalorder.c tests/minus-zero.h tests/infinity.h tests/nan.h +tests/qnan.h tests/macros.h Depends-on: +signbit configure.ac: diff --git a/modules/totalorderf-tests b/modules/totalorderf-tests index e76c9fda38..581e3e8cc2 100644 --- a/modules/totalorderf-tests +++ b/modules/totalorderf-tests @@ -4,9 +4,11 @@ tests/test-totalorder.c tests/minus-zero.h tests/infinity.h tests/nan.h +tests/qnan.h tests/macros.h Depends-on: +signbit configure.ac: diff --git a/modules/totalorderl-tests b/modules/totalorderl-tests index cfc50e21e9..c443fcc525 100644 --- a/modules/totalorderl-tests +++ b/modules/totalorderl-tests @@ -4,9 +4,11 @@ tests/test-totalorder.c tests/minus-zero.h tests/infinity.h tests/nan.h +tests/qnan.h tests/macros.h Depends-on: +signbit configure.ac: diff --git a/tests/nan.h b/tests/nan.h index 05f141d2a9..3ba41d8de9 100644 --- a/tests/nan.h +++ b/tests/nan.h @@ -1,4 +1,4 @@ -/* Macros for not-a-number. +/* Macros for quiet not-a-number. Copyright (C) 2007-2023 Free Software Foundation, Inc. This program is free software: you can redistribute it and/or modify @@ -14,6 +14,9 @@ You should have received a copy of the GNU General Public License along with this program. If not, see . */ +#ifndef _TESTS_NAN_H +#define _TESTS_NAN_H + /* IBM z/OS supports both hexadecimal and IEEE floating-point formats. The former does not support NaN and its isnan() implementation returns zero @@ -83,3 +86,6 @@ NaNl () #else # define NaNl() (0.0L / 0.0L) #endif + + +#endif /* _TESTS_NAN_H */ diff --git a/tests/qnan.h b/tests/qnan.h new file mode 100644 index 0000000000..7006699865 --- /dev/null +++ b/tests/qnan.h @@ -0,0 +1,82 @@ +/* Macros for quiet not-a-number. + Copyright (C) 2023 Free Software Foundation, Inc. + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program 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 General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . */ + +#include + +#include "nan.h" + + +/* Returns a quiet 'float' NaN with sign bit == 0. */ +_GL_UNUSED static float +positive_NaNf () +{ + /* 'volatile' works around a GCC bug: + */ + float volatile nan = NaNf (); + return (signbit (nan) ? - nan : nan); +} + +/* Returns a quiet 'float' NaN with sign bit == 1. */ +_GL_UNUSED static float +negative_NaNf () +{ + /* 'volatile' works around a GCC bug: + */ + float volatile nan = NaNf (); + return (signbit (nan) ? nan : - nan); +} + + +/* Returns a quiet 'double' NaN with sign bit == 0. */ +_GL_UNUSED static double +positive_NaNd () +{ + /* 'volatile' works around a GCC bug: + */ + double volatile nan = NaNd (); + return (signbit (nan) ? - nan : nan); +} + +/* Returns a quiet 'double' NaN with sign bit == 1. */ +_GL_UNUSED static double +negative_NaNd () +{ + /* 'volatile' works around a GCC bug: + */ + double volatile nan = NaNd (); + return (signbit (nan) ? nan : - nan); +} + + +/* Returns a quiet 'long double' NaN with sign bit == 0. */ +_GL_UNUSED static long double +positive_NaNl () +{ + /* 'volatile' works around a GCC bug: + */ + long double volatile nan = NaNl (); + return (signbit (nan) ? - nan : nan); +} + +/* Returns a quiet 'long double' NaN with sign bit == 1. */ +_GL_UNUSED static long double +negative_NaNl () +{ + /* 'volatile' works around a GCC bug: + */ + long double volatile nan = NaNl (); + return (signbit (nan) ? nan : - nan); +} diff --git a/tests/test-signbit.c b/tests/test-signbit.c index 3d2fae405b..2c1daccef2 100644 --- a/tests/test-signbit.c +++ b/tests/test-signbit.c @@ -30,6 +30,7 @@ #include "minus-zero.h" #include "infinity.h" +#include "qnan.h" #include "macros.h" float zerof = 0.0f; @@ -56,17 +57,8 @@ test_signbitf () ASSERT (!signbit (Infinityf ())); ASSERT (signbit (- Infinityf ())); /* Quiet NaN. */ - { - float nan = zerof / zerof; - float pos_nan; - float neg_nan; - if (signbit (nan)) - pos_nan = - nan, neg_nan = nan; - else - pos_nan = nan, neg_nan = - nan; - ASSERT (!signbit (pos_nan)); - ASSERT (signbit (neg_nan)); - } + ASSERT (!signbit (positive_NaNf ())); + ASSERT (signbit (negative_NaNf ())); #if defined FLT_EXPBIT0_WORD && defined FLT_EXPBIT0_BIT /* Signalling NaN. */ { @@ -111,17 +103,8 @@ test_signbitd () ASSERT (!signbit (Infinityd ())); ASSERT (signbit (- Infinityd ())); /* Quiet NaN. */ - { - double nan = zerod / zerod; - double pos_nan; - double neg_nan; - if (signbit (nan)) - pos_nan = - nan, neg_nan = nan; - else - pos_nan = nan, neg_nan = - nan; - ASSERT (!signbit (pos_nan)); - ASSERT (signbit (neg_nan)); - } + ASSERT (!signbit (positive_NaNd ())); + ASSERT (signbit (negative_NaNd ())); #if defined DBL_EXPBIT0_WORD && defined DBL_EXPBIT0_BIT /* Signalling NaN. */ { @@ -164,17 +147,8 @@ test_signbitl () ASSERT (!signbit (Infinityl ())); ASSERT (signbit (- Infinityl ())); /* Quiet NaN. */ - { - long double nan = zerol / zerol; - long double pos_nan; - long double neg_nan; - if (signbit (nan)) - pos_nan = - nan, neg_nan = nan; - else - pos_nan = nan, neg_nan = - nan; - ASSERT (!signbit (pos_nan)); - ASSERT (signbit (neg_nan)); - } + ASSERT (!signbit (positive_NaNl ())); + ASSERT (signbit (negative_NaNl ())); #if defined LDBL_EXPBIT0_WORD && defined LDBL_EXPBIT0_BIT /* Signalling NaN. */ { diff --git a/tests/test-totalorder.c b/tests/test-totalorder.c index b4a121c2a2..b63c7c2211 100644 --- a/tests/test-totalorder.c +++ b/tests/test-totalorder.c @@ -21,44 +21,25 @@ #include "infinity.h" #include "macros.h" #include "minus-zero.h" -#include "nan.h" +#include "qnan.h" #ifndef TOTALORDER # define TOTALORDER totalorder # define TOTALORDER_INF Infinityd # define TOTALORDER_MINUS_ZERO minus_zerod -# define TOTALORDER_NAN NaNd +# define TOTALORDER_POSITIVE_NAN positive_NaNd +# define TOTALORDER_NEGATIVE_NAN negative_NaNd # define TOTALORDER_TYPE double #endif -/* Return a quiet NaN with sign bit == 0. */ -static TOTALORDER_TYPE -positive_nan () -{ - /* 'volatile' works around a GCC bug: - */ - TOTALORDER_TYPE volatile nan = TOTALORDER_NAN (); - return (signbit (nan) ? - nan : nan); -} - -/* Return a quiet NaN with sign bit == 1. */ -static TOTALORDER_TYPE -negative_nan () -{ - /* 'volatile' works around a GCC bug: - */ - TOTALORDER_TYPE volatile nan = TOTALORDER_NAN (); - return (signbit (nan) ? nan : - nan); -} - int main () { TOTALORDER_TYPE x[] = { - negative_nan (), -TOTALORDER_INF (), -1e37, -1, -1e-5, + TOTALORDER_NEGATIVE_NAN (), -TOTALORDER_INF (), -1e37, -1, -1e-5, TOTALORDER_MINUS_ZERO, 0, - 1e-5, 1, 1e37, TOTALORDER_INF (), positive_nan () + 1e-5, 1, 1e37, TOTALORDER_INF (), TOTALORDER_POSITIVE_NAN () }; int n = sizeof x / sizeof *x; diff --git a/tests/test-totalorderf.c b/tests/test-totalorderf.c index 2dcb47aca4..5fd27031c0 100644 --- a/tests/test-totalorderf.c +++ b/tests/test-totalorderf.c @@ -1,6 +1,7 @@ #define TOTALORDER totalorderf #define TOTALORDER_INF Infinityf #define TOTALORDER_MINUS_ZERO minus_zerof -#define TOTALORDER_NAN NaNf +#define TOTALORDER_POSITIVE_NAN positive_NaNf +#define TOTALORDER_NEGATIVE_NAN negative_NaNf #define TOTALORDER_TYPE float #include "test-totalorder.c" diff --git a/tests/test-totalorderl.c b/tests/test-totalorderl.c index ac454ad848..c8f1fbd4b6 100644 --- a/tests/test-totalorderl.c +++ b/tests/test-totalorderl.c @@ -1,6 +1,7 @@ #define TOTALORDER totalorderl #define TOTALORDER_INF Infinityl #define TOTALORDER_MINUS_ZERO minus_zerol -#define TOTALORDER_NAN NaNl +#define TOTALORDER_POSITIVE_NAN positive_NaNl +#define TOTALORDER_NEGATIVE_NAN negative_NaNl #define TOTALORDER_TYPE long double #include "test-totalorder.c" -- 2.39.5