From: Bruno Haible Date: Wed, 24 Jul 2024 17:46:44 +0000 (+0200) Subject: xstrtod, xstrtold: Don't treat gradual underflow as an error. X-Git-Url: https://gitweb.git.savannah.gnu.org/gitweb/?a=commitdiff_plain;h=6c19041d86dc0b4a1888c6764986d191e83c5a10;p=gnulib.git xstrtod, xstrtold: Don't treat gradual underflow as an error. * lib/xstrtod.c (XSTRTOD): Upon gradual underflow, return true with errno = 0. * lib/xstrtod.h (xstrtod, xstrtold): Update specification. * tests/test-xstrtod.c (main): For gradual underflow, expect ok && errno == 0. * tests/test-xstrtold.c (main): Likewise. --- diff --git a/ChangeLog b/ChangeLog index 3e9d691efa..a96c219d7e 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,13 @@ +2024-07-24 Bruno Haible + + xstrtod, xstrtold: Don't treat gradual underflow as an error. + * lib/xstrtod.c (XSTRTOD): Upon gradual underflow, return true with + errno = 0. + * lib/xstrtod.h (xstrtod, xstrtold): Update specification. + * tests/test-xstrtod.c (main): For gradual underflow, expect ok && + errno == 0. + * tests/test-xstrtold.c (main): Likewise. + 2024-07-23 Collin Funk Detect UNIX domain sockets supported by recent Windows versions. diff --git a/lib/xstrtod.c b/lib/xstrtod.c index a9ca7e8d10..7565658e4d 100644 --- a/lib/xstrtod.c +++ b/lib/xstrtod.c @@ -57,11 +57,18 @@ XSTRTOD (char const *str, char const **ptr, DOUBLE *result, else { /* Flag overflow as an error. - Flag gradual underflow as an error. + Flag gradual underflow as no error. Flag flush-to-zero underflow as no error. In either case, the caller can inspect *RESULT to get more details. */ if (val != 0 && errno == ERANGE) - ok = false; + { + if (val >= 1 || val <= -1) + /* Overflow. */ + ok = false; + else + /* Gradual underflow. */ + errno = 0; + } } if (ptr != NULL) diff --git a/lib/xstrtod.h b/lib/xstrtod.h index 8ceca6c433..f6a1ed888a 100644 --- a/lib/xstrtod.h +++ b/lib/xstrtod.h @@ -42,8 +42,7 @@ extern "C" { NaN true NaN 0 ±Infinity true ±HUGE_VAL 0 overflow false ±HUGE_VAL ERANGE - gradual underflow [!MSVC] false near zero ERANGE - gradual underflow [MSVC] true near zero 0 + gradual underflow true near zero 0 flush-to-zero underflow true ±0.0 ERANGE other finite value true value 0 @@ -68,8 +67,7 @@ bool xstrtod (const char *str, const char **ptr, double *result, NaN true NaN 0 ±Infinity true ±HUGE_VALL 0 overflow false ±HUGE_VALL ERANGE - gradual underflow [!MSVC] false near zero ERANGE - gradual underflow [MSVC] true near zero 0 + gradual underflow true near zero 0 flush-to-zero underflow true ±0.0L ERANGE other finite value true value 0 diff --git a/tests/test-xstrtod.c b/tests/test-xstrtod.c index 3464120f1e..e02d97203a 100644 --- a/tests/test-xstrtod.c +++ b/tests/test-xstrtod.c @@ -658,36 +658,20 @@ main () const char *ptr; double result = UNINIT; bool ok = xstrtod (input, &ptr, &result, strtod); -#if defined _MSC_VER ASSERT (ok); -#else - ASSERT (!ok); -#endif ASSERT (0.0 < result && result <= DBL_MIN); ASSERT (ptr == input + 6); -#if defined _MSC_VER ASSERT (errno == 0); -#else - ASSERT (errno == ERANGE); -#endif } { const char input[] = "-1e-320"; const char *ptr; double result = UNINIT; bool ok = xstrtod (input, &ptr, &result, strtod); -#if defined _MSC_VER ASSERT (ok); -#else - ASSERT (!ok); -#endif ASSERT (-DBL_MIN <= result && result < 0.0); ASSERT (ptr == input + 7); -#if defined _MSC_VER ASSERT (errno == 0); -#else - ASSERT (errno == ERANGE); -#endif } /* Flush-to-zero underflow. */ diff --git a/tests/test-xstrtold.c b/tests/test-xstrtold.c index b83e78067b..a8788ca100 100644 --- a/tests/test-xstrtold.c +++ b/tests/test-xstrtold.c @@ -662,18 +662,10 @@ main () const char *ptr; long double result = UNINIT; bool ok = xstrtold (input, &ptr, &result, strtold); -#if defined _MSC_VER ASSERT (ok); -#else - ASSERT (!ok); -#endif ASSERT (0.0L < result && result <= LDBL_MIN); ASSERT (ptr == input + strlen (input)); -#if defined _MSC_VER ASSERT (errno == 0); -#else - ASSERT (errno == ERANGE); -#endif } { #if LDBL_MAX_EXP > 10000 @@ -684,18 +676,10 @@ main () const char *ptr; long double result = UNINIT; bool ok = xstrtold (input, &ptr, &result, strtold); -#if defined _MSC_VER ASSERT (ok); -#else - ASSERT (!ok); -#endif ASSERT (-LDBL_MIN <= result && result < 0.0L); ASSERT (ptr == input + strlen (input)); -#if defined _MSC_VER ASSERT (errno == 0); -#else - ASSERT (errno == ERANGE); -#endif } /* Flush-to-zero underflow. */