From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: by sourceware.org (Postfix, from userid 2153) id 1B6F53858D37; Thu, 2 Mar 2023 23:42:07 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org 1B6F53858D37 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gcc.gnu.org; s=default; t=1677800527; bh=lLERo0BMz9DGm0ZU5hepF2Ok0V32AlhDH+s0xZ5Gb9Y=; h=From:To:Subject:Date:From; b=irG6llFeZgpk6T8VxyfCVPrNWTnBo0rPMvm3GiEU0fXvPvNY9aVbpU3aTFWz2qnb2 231nTlFIEFClEgvnaFELsbXIle40noYifBUbRlh9v4/vAubtWwVygpyGs7aq6Q2tiG yoNx/j+HhFRHa4YiWjtVLCkPM/1wKyZtliSZpw04= MIME-Version: 1.0 Content-Transfer-Encoding: 7bit Content-Type: text/plain; charset="utf-8" From: Jakub Jelinek To: gcc-cvs@gcc.gnu.org Subject: [gcc r13-6427] libquadmath: Assorted libquadmath strtoflt128 fixes [PR87204, PR94756] X-Act-Checkin: gcc X-Git-Author: Jakub Jelinek X-Git-Refname: refs/heads/master X-Git-Oldrev: 6978df2c04df165eaa6aac9e17b6c770bed460e3 X-Git-Newrev: df63f4162c78ef799d4ea9dec3443d5e9c51e5aa Message-Id: <20230302234207.1B6F53858D37@sourceware.org> Date: Thu, 2 Mar 2023 23:42:07 +0000 (GMT) List-Id: https://gcc.gnu.org/g:df63f4162c78ef799d4ea9dec3443d5e9c51e5aa commit r13-6427-gdf63f4162c78ef799d4ea9dec3443d5e9c51e5aa Author: Jakub Jelinek Date: Fri Mar 3 00:40:13 2023 +0100 libquadmath: Assorted libquadmath strtoflt128 fixes [PR87204, PR94756] This patch cherry-pickx 8 commits from glibc which fix various strtod_l bugs. Additionally, it makes mp_limb_t 64-bit on llp64 targets like 64-bit cygwin. 2023-03-03 niXman Jakub Jelinek PR libquadmath/87204 PR libquadmath/94756 * printf/gmp-impl.h (mp_limb_t, mp_limb_signed_t, BITS_PER_MP_LIMB): Use 64-bit limbs on LLP64 targets. * strtod/strtod_l.c (round_and_return): Cherry-pick glibc 9310c284ae9 BZ #16151, 4406c41c1d6 BZ #16965 and fcd6b5ac36a BZ #23279 fixes. (____STRTOF_INTERNAL): Cherry-pick glibc b0debe14fcf BZ #23007, 5556d30caee BZ #18247, 09555b9721d and c6aac3bf366 BZ #26137 and d84f25c7d87 fixes. Diff: --- libquadmath/printf/gmp-impl.h | 10 +++++++++- libquadmath/strtod/strtod_l.c | 38 ++++++++++++++++++++++++++------------ 2 files changed, 35 insertions(+), 13 deletions(-) diff --git a/libquadmath/printf/gmp-impl.h b/libquadmath/printf/gmp-impl.h index 94d88efc57f..c5c9c8e01e8 100644 --- a/libquadmath/printf/gmp-impl.h +++ b/libquadmath/printf/gmp-impl.h @@ -33,10 +33,18 @@ MA 02111-1307, USA. */ #define MAX(h,i) ((h) > (i) ? (h) : (i)) #endif +#if __SIZEOF_LONG__ == 4 && __SIZEOF_LONG_LONG__ == 8 \ + && __SIZEOF_POINTER__ == 8 +/* Use 64-bit limbs on LLP64 targets. */ +#define BITS_PER_MP_LIMB (__SIZEOF_LONG_LONG__ * __CHAR_BIT__) +typedef unsigned long long int mp_limb_t; +typedef long long int mp_limb_signed_t; +#else #define BITS_PER_MP_LIMB (__SIZEOF_LONG__ * __CHAR_BIT__) -#define BYTES_PER_MP_LIMB (BITS_PER_MP_LIMB / __CHAR_BIT__) typedef unsigned long int mp_limb_t; typedef long int mp_limb_signed_t; +#endif +#define BYTES_PER_MP_LIMB (BITS_PER_MP_LIMB / __CHAR_BIT__) typedef mp_limb_t * mp_ptr; typedef const mp_limb_t * mp_srcptr; diff --git a/libquadmath/strtod/strtod_l.c b/libquadmath/strtod/strtod_l.c index 0b0e85a3cf7..38602841cd7 100644 --- a/libquadmath/strtod/strtod_l.c +++ b/libquadmath/strtod/strtod_l.c @@ -200,7 +200,7 @@ round_and_return (mp_limb_t *retval, intmax_t exponent, int negative, round_limb = retval[RETURN_LIMB_SIZE - 1]; round_bit = (MANT_DIG - 1) % BITS_PER_MP_LIMB; - for (i = 0; i < RETURN_LIMB_SIZE; ++i) + for (i = 0; i < RETURN_LIMB_SIZE - 1; ++i) more_bits |= retval[i] != 0; MPN_ZERO (retval, RETURN_LIMB_SIZE); } @@ -215,9 +215,14 @@ round_and_return (mp_limb_t *retval, intmax_t exponent, int negative, more_bits |= ((round_limb & ((((mp_limb_t) 1) << round_bit) - 1)) != 0); - (void) mpn_rshift (retval, &retval[shift / BITS_PER_MP_LIMB], - RETURN_LIMB_SIZE - (shift / BITS_PER_MP_LIMB), - shift % BITS_PER_MP_LIMB); + /* mpn_rshift requires 0 < shift < BITS_PER_MP_LIMB. */ + if ((shift % BITS_PER_MP_LIMB) != 0) + (void) mpn_rshift (retval, &retval[shift / BITS_PER_MP_LIMB], + RETURN_LIMB_SIZE - (shift / BITS_PER_MP_LIMB), + shift % BITS_PER_MP_LIMB); + else + for (i = 0; i < RETURN_LIMB_SIZE - (shift / BITS_PER_MP_LIMB); i++) + retval[i] = retval[i + (shift / BITS_PER_MP_LIMB)]; MPN_ZERO (&retval[RETURN_LIMB_SIZE - (shift / BITS_PER_MP_LIMB)], shift / BITS_PER_MP_LIMB); } @@ -276,7 +281,7 @@ round_and_return (mp_limb_t *retval, intmax_t exponent, int negative, } } - if (exponent > MAX_EXP) + if (exponent >= MAX_EXP) goto overflow; #ifdef HAVE_FENV_H @@ -308,7 +313,7 @@ round_and_return (mp_limb_t *retval, intmax_t exponent, int negative, } #endif - if (exponent > MAX_EXP) + if (exponent >= MAX_EXP) overflow: return overflow_value (negative); @@ -688,7 +693,7 @@ ____STRTOF_INTERNAL (nptr, endptr, group) if (endptr != NULL) *endptr = (STRING_TYPE *) cp; - return retval; + return negative ? -retval : retval; } /* It is really a text we do not recognize. */ @@ -1193,7 +1198,16 @@ ____STRTOF_INTERNAL (nptr, endptr, group) if (__builtin_expect (exponent > MAX_10_EXP + 1 - (intmax_t) int_no, 0)) return overflow_value (negative); - if (__builtin_expect (exponent < MIN_10_EXP - (DIG + 1), 0)) + /* 10^(MIN_10_EXP-1) is not normal. Thus, 10^(MIN_10_EXP-1) / + 2^MANT_DIG is below half the least subnormal, so anything with a + base-10 exponent less than the base-10 exponent (which is + MIN_10_EXP - 1 - ceil(MANT_DIG*log10(2))) of that value + underflows. DIG is floor((MANT_DIG-1)log10(2)), so an exponent + below MIN_10_EXP - (DIG + 3) underflows. But EXPONENT is + actually an exponent multiplied only by a fractional part, not an + integer part, so an exponent below MIN_10_EXP - (DIG + 2) + underflows. */ + if (__builtin_expect (exponent < MIN_10_EXP - (DIG + 2), 0)) return underflow_value (negative); if (int_no > 0) @@ -1360,7 +1374,7 @@ ____STRTOF_INTERNAL (nptr, endptr, group) assert (dig_no > int_no && exponent <= 0 - && exponent >= MIN_10_EXP - (DIG + 1)); + && exponent >= MIN_10_EXP - (DIG + 2)); /* We need to compute MANT_DIG - BITS fractional bits that lie within the mantissa of the result, the following bit for @@ -1651,8 +1665,8 @@ ____STRTOF_INTERNAL (nptr, endptr, group) d1 = den[densize - 2]; /* The division does not work if the upper limb of the two-limb - numerator is greater than the denominator. */ - if (mpn_cmp (num, &den[densize - numsize], numsize) > 0) + numerator is greater than or equal to the denominator. */ + if (mpn_cmp (num, &den[densize - numsize], numsize) >= 0) num[numsize++] = 0; if (numsize < densize) @@ -1761,7 +1775,7 @@ ____STRTOF_INTERNAL (nptr, endptr, group) got_limb; } - for (i = densize; num[i] == 0 && i >= 0; --i) + for (i = densize; i >= 0 && num[i] == 0; --i) ; return round_and_return (retval, exponent - 1, negative, quot, BITS_PER_MP_LIMB - 1 - used,