- Add mpfr-4.2.0-cummulative.patch, cummulative patches for

mpfr 4.2.0:
  * A test of the thousands separator in tsprintf.c is based on the
    output from the GNU C Library up to 2.36, which is incorrect.
  * The mpfr_ui_pow_ui function has infinite loop in case of overflow.
  * The tfprintf and tprintf tests may fail in locales where decimal_point
    has several bytes, such as ps_AF.
  * In particular cases that are very hard to round, mpfr_rec_sqrt may yield
    a stack overflow due to many small allocations in the stack, based on
    alloca().
- Remove tests-tsprintf.patch that's included in the above set.

OBS-URL: https://build.opensuse.org/package/show/devel:libraries:c_c++/mpfr?expand=0&rev=78
This commit is contained in:
Richard Biener 2023-04-18 08:22:48 +00:00 committed by Git OBS Bridge
parent abeb6a1f64
commit ad0e704d8b
4 changed files with 537 additions and 57 deletions

View File

@ -0,0 +1,521 @@
diff -Naurd mpfr-4.2.0-a/PATCHES mpfr-4.2.0-b/PATCHES
--- mpfr-4.2.0-a/PATCHES 2023-04-17 21:17:39.748645280 +0000
+++ mpfr-4.2.0-b/PATCHES 2023-04-17 21:17:39.792645218 +0000
@@ -0,0 +1 @@
+tsprintf-thousands
diff -Naurd mpfr-4.2.0-a/VERSION mpfr-4.2.0-b/VERSION
--- mpfr-4.2.0-a/VERSION 2023-01-06 10:55:57.000000000 +0000
+++ mpfr-4.2.0-b/VERSION 2023-04-17 21:17:39.792645218 +0000
@@ -1 +1 @@
-4.2.0
+4.2.0-p1
diff -Naurd mpfr-4.2.0-a/src/mpfr.h mpfr-4.2.0-b/src/mpfr.h
--- mpfr-4.2.0-a/src/mpfr.h 2023-01-06 10:55:57.000000000 +0000
+++ mpfr-4.2.0-b/src/mpfr.h 2023-04-17 21:17:39.788645224 +0000
@@ -27,7 +27,7 @@
#define MPFR_VERSION_MAJOR 4
#define MPFR_VERSION_MINOR 2
#define MPFR_VERSION_PATCHLEVEL 0
-#define MPFR_VERSION_STRING "4.2.0"
+#define MPFR_VERSION_STRING "4.2.0-p1"
/* User macros:
MPFR_USE_FILE: Define it to make MPFR define functions dealing
diff -Naurd mpfr-4.2.0-a/src/version.c mpfr-4.2.0-b/src/version.c
--- mpfr-4.2.0-a/src/version.c 2023-01-06 10:55:57.000000000 +0000
+++ mpfr-4.2.0-b/src/version.c 2023-04-17 21:17:39.792645218 +0000
@@ -25,5 +25,5 @@
const char *
mpfr_get_version (void)
{
- return "4.2.0";
+ return "4.2.0-p1";
}
diff -Naurd mpfr-4.2.0-a/tests/tsprintf.c mpfr-4.2.0-b/tests/tsprintf.c
--- mpfr-4.2.0-a/tests/tsprintf.c 2023-01-05 17:09:48.000000000 +0000
+++ mpfr-4.2.0-b/tests/tsprintf.c 2023-04-17 21:17:39.784645229 +0000
@@ -1715,7 +1715,25 @@
check_sprintf ("000000001,000", "%'013.4Rg", x);
#ifdef PRINTF_GROUPFLAG
- check_vsprintf ("+01,234,567 :", "%0+ -'13.10Pd:", (mpfr_prec_t) 1234567);
+ /* Do not test the thousands separator with a precision field larger
+ than the number of digits (thus needing leading zeros), such as
+ "%0+ -'13.10Pd:" (used up to MPFR 4.2.0), since the GNU libc is
+ buggy: https://sourceware.org/bugzilla/show_bug.cgi?id=23432
+ We don't know about the other implementations.
+ This new test works fine with glibc up to 2.36, but fails with 2.37
+ (as reported by Klaus Dittrich in the MPFR mailing-list); this is
+ actually a bug introduced in glibc 2.37, not in MPFR:
+ https://sourceware.org/bugzilla/show_bug.cgi?id=30068
+ Since this bug can yield a buffer overflow (CVE-2023-25139), possibly
+ affecting MPFR users, let us rather require a fix in glibc. This bug
+ has been fixed in the 2.37 branch:
+ https://sourceware.org/git/?p=glibc.git;a=commit;h=07b9521fc6
+ If we wanted to check that and avoid a failure of the test because of
+ a buggy C library (while MPFR would be consistent with the C library),
+ we could compare the MPFR output with both the correct output and the
+ output from the C library (possibly buggy). But to do that in a clean
+ way, this would require a change in the check_vsprintf() call. */
+ check_vsprintf ("+1,234,567 :", "%0+ -'13Pd:", (mpfr_prec_t) 1234567);
#endif
mpfr_clear (x);
diff -Naurd mpfr-4.2.0-a/PATCHES mpfr-4.2.0-b/PATCHES
--- mpfr-4.2.0-a/PATCHES 2023-04-17 21:18:00.464616127 +0000
+++ mpfr-4.2.0-b/PATCHES 2023-04-17 21:18:00.512616059 +0000
@@ -0,0 +1 @@
+ui_pow_ui-overflow
diff -Naurd mpfr-4.2.0-a/VERSION mpfr-4.2.0-b/VERSION
--- mpfr-4.2.0-a/VERSION 2023-04-17 21:17:39.792645218 +0000
+++ mpfr-4.2.0-b/VERSION 2023-04-17 21:18:00.512616059 +0000
@@ -1 +1 @@
-4.2.0-p1
+4.2.0-p2
diff -Naurd mpfr-4.2.0-a/src/mpfr.h mpfr-4.2.0-b/src/mpfr.h
--- mpfr-4.2.0-a/src/mpfr.h 2023-04-17 21:17:39.788645224 +0000
+++ mpfr-4.2.0-b/src/mpfr.h 2023-04-17 21:18:00.508616065 +0000
@@ -27,7 +27,7 @@
#define MPFR_VERSION_MAJOR 4
#define MPFR_VERSION_MINOR 2
#define MPFR_VERSION_PATCHLEVEL 0
-#define MPFR_VERSION_STRING "4.2.0-p1"
+#define MPFR_VERSION_STRING "4.2.0-p2"
/* User macros:
MPFR_USE_FILE: Define it to make MPFR define functions dealing
diff -Naurd mpfr-4.2.0-a/src/ui_pow_ui.c mpfr-4.2.0-b/src/ui_pow_ui.c
--- mpfr-4.2.0-a/src/ui_pow_ui.c 2023-01-05 17:09:48.000000000 +0000
+++ mpfr-4.2.0-b/src/ui_pow_ui.c 2023-04-17 21:18:00.504616070 +0000
@@ -23,7 +23,7 @@
#include "mpfr-impl.h"
int
-mpfr_ui_pow_ui (mpfr_ptr x, unsigned long int y, unsigned long int n,
+mpfr_ui_pow_ui (mpfr_ptr x, unsigned long int k, unsigned long int n,
mpfr_rnd_t rnd)
{
mpfr_exp_t err;
@@ -35,22 +35,28 @@
MPFR_ZIV_DECL (loop);
MPFR_SAVE_EXPO_DECL (expo);
+ MPFR_LOG_FUNC
+ (("k=%lu n=%lu rnd=%d", k, n, rnd),
+ ("y[%Pu]=%.*Rg inexact=%d",
+ mpfr_get_prec (x), mpfr_log_prec, x, inexact));
+
if (MPFR_UNLIKELY (n <= 1))
{
if (n == 1)
- return mpfr_set_ui (x, y, rnd); /* y^1 = y */
+ return mpfr_set_ui (x, k, rnd); /* k^1 = k */
else
- return mpfr_set_ui (x, 1, rnd); /* y^0 = 1 for any y */
+ return mpfr_set_ui (x, 1, rnd); /* k^0 = 1 for any k */
}
- else if (MPFR_UNLIKELY (y <= 1))
+ else if (MPFR_UNLIKELY (k <= 1))
{
- if (y == 1)
+ if (k == 1)
return mpfr_set_ui (x, 1, rnd); /* 1^n = 1 for any n > 0 */
else
return mpfr_set_ui (x, 0, rnd); /* 0^n = 0 for any n > 0 */
}
- for (size_n = 0, m = n; m; size_n++, m >>= 1);
+ for (size_n = 0, m = n; m != 0; size_n++, m >>= 1)
+ ;
MPFR_SAVE_EXPO_MARK (expo);
prec = MPFR_PREC (x) + 3 + size_n;
@@ -60,23 +66,55 @@
for (;;)
{
int i = size_n;
+ unsigned int inex_res;
- inexact = mpfr_set_ui (res, y, MPFR_RNDU);
+ inex_res = mpfr_set_ui (res, k, MPFR_RNDU);
err = 1;
/* now 2^(i-1) <= n < 2^i: i=1+floor(log2(n)) */
for (i -= 2; i >= 0; i--)
{
- inexact |= mpfr_sqr (res, res, MPFR_RNDU);
+ inex_res |= mpfr_sqr (res, res, MPFR_RNDU);
err++;
if (n & (1UL << i))
- inexact |= mpfr_mul_ui (res, res, y, MPFR_RNDU);
+ inex_res |= mpfr_mul_ui (res, res, k, MPFR_RNDU);
}
+
+ if (MPFR_UNLIKELY (MPFR_IS_INF (res)))
+ {
+ mpfr_t kf;
+ mpz_t z;
+ int size_k;
+ MPFR_BLOCK_DECL (flags);
+
+ /* Let's handle the overflow by calling mpfr_pow_z.
+ Alternatively, we could call mpfr_pow_ui; this would
+ need a bit shorter code below, but mpfr_pow_ui handles
+ the overflow by calling mpfr_pow_z, so that calling
+ mpfr_pow_z directly should be a bit more efficient. */
+
+ MPFR_ZIV_FREE (loop);
+ mpfr_clear (res);
+ for (size_k = 0, m = k; m != 0; size_k++, m >>= 1)
+ ;
+ mpfr_init2 (kf, size_k);
+ inexact = mpfr_set_ui (kf, k, MPFR_RNDN);
+ MPFR_ASSERTD (inexact == 0);
+ mpz_init (z);
+ mpz_set_ui (z, n);
+ MPFR_BLOCK (flags, inexact = mpfr_pow_z (x, kf, z, rnd););
+ mpz_clear (z);
+ mpfr_clear (kf);
+ MPFR_SAVE_EXPO_UPDATE_FLAGS (expo, flags);
+ goto end;
+ }
+
/* since the loop is executed floor(log2(n)) times,
we have err = 1+floor(log2(n)).
Since prec >= MPFR_PREC(x) + 4 + floor(log2(n)), prec > err */
err = prec - err;
- if (MPFR_LIKELY (inexact == 0
+ MPFR_LOG_VAR (res);
+ if (MPFR_LIKELY (!inex_res
|| MPFR_CAN_ROUND (res, err, MPFR_PREC (x), rnd)))
break;
@@ -90,6 +128,7 @@
mpfr_clear (res);
+ end:
MPFR_SAVE_EXPO_FREE (expo);
return mpfr_check_range (x, inexact, rnd);
}
diff -Naurd mpfr-4.2.0-a/src/version.c mpfr-4.2.0-b/src/version.c
--- mpfr-4.2.0-a/src/version.c 2023-04-17 21:17:39.792645218 +0000
+++ mpfr-4.2.0-b/src/version.c 2023-04-17 21:18:00.512616059 +0000
@@ -25,5 +25,5 @@
const char *
mpfr_get_version (void)
{
- return "4.2.0-p1";
+ return "4.2.0-p2";
}
diff -Naurd mpfr-4.2.0-a/tests/tlog10.c mpfr-4.2.0-b/tests/tlog10.c
--- mpfr-4.2.0-a/tests/tlog10.c 2023-01-05 17:09:48.000000000 +0000
+++ mpfr-4.2.0-b/tests/tlog10.c 2023-04-17 21:18:00.504616070 +0000
@@ -49,6 +49,60 @@
#define TEST_RANDOM_POS 8
#include "tgeneric.c"
+/* On 2023-02-13, one gets an infinite loop in mpfr_log10 on both
+ 32-bit and 64-bit hosts when the precision is not large enough
+ (precision 12 and below). */
+static void
+bug20230213 (void)
+{
+ mpfr_exp_t old_emin, old_emax, e;
+ mpfr_t t, x, y0, y1, y2;
+ int prec;
+
+ old_emin = mpfr_get_emin ();
+ old_emax = mpfr_get_emax ();
+
+ set_emin (MPFR_EMIN_MIN);
+ set_emax (MPFR_EMAX_MAX);
+ e = mpfr_get_emax () - 1;
+
+ /* The precisions of t and y0 should be large enough to avoid
+ a hard-to-round case for the target precisions. */
+ mpfr_inits2 (64, t, y0, (mpfr_ptr) 0);
+ mpfr_set_exp_t (y0, e, MPFR_RNDN);
+ mpfr_log_ui (t, 10, MPFR_RNDN);
+ mpfr_div (y0, y0, t, MPFR_RNDN);
+ mpfr_log_ui (t, 2, MPFR_RNDN);
+ mpfr_mul (y0, y0, t, MPFR_RNDN);
+
+ for (prec = 16; prec >= MPFR_PREC_MIN; prec--)
+ {
+ mpfr_inits2 (prec, x, y1, y2, (mpfr_ptr) 0);
+ mpfr_set (y1, y0, MPFR_RNDN);
+
+ mpfr_set_ui_2exp (x, 1, e, MPFR_RNDN);
+ mpfr_log10 (y2, x, MPFR_RNDN);
+ MPFR_ASSERTN (MPFR_IS_PURE_FP (y2));
+ MPFR_ASSERTN (MPFR_IS_POS (y2));
+
+ if (! mpfr_equal_p (y1, y2))
+ {
+ printf ("Error in bug20230213.\n");
+ printf ("Expected ");
+ mpfr_dump (y1);
+ printf ("Got ");
+ mpfr_dump (y2);
+ exit (1);
+ }
+ mpfr_clears (x, y1, y2, (mpfr_ptr) 0);
+ }
+
+ mpfr_clears (t, y0, (mpfr_ptr) 0);
+
+ set_emin (old_emin);
+ set_emax (old_emax);
+}
+
int
main (int argc, char *argv[])
{
@@ -112,6 +166,8 @@
mpfr_clear (x);
mpfr_clear (y);
+ bug20230213 ();
+
data_check ("data/log10", mpfr_log10, "mpfr_log10");
tests_end_mpfr ();
diff -Naurd mpfr-4.2.0-a/tests/tui_pow.c mpfr-4.2.0-b/tests/tui_pow.c
--- mpfr-4.2.0-a/tests/tui_pow.c 2023-01-05 17:09:48.000000000 +0000
+++ mpfr-4.2.0-b/tests/tui_pow.c 2023-04-17 21:18:00.504616070 +0000
@@ -142,6 +142,37 @@
mpfr_clear (t);
}
+static void
+huge (void)
+{
+ mpfr_exp_t old_emin, old_emax;
+ mpfr_t x;
+
+ old_emin = mpfr_get_emin ();
+ old_emax = mpfr_get_emax ();
+
+ set_emin (MPFR_EMIN_MIN);
+ set_emax (MPFR_EMAX_MAX);
+
+ mpfr_init2 (x, 8);
+
+ /* The purpose of this test is more to check that mpfr_ui_pow_ui
+ terminates (without taking much memory) rather than checking
+ the value of x. On 2023-02-13, the +Inf case was not handled
+ in the Ziv iteration, yielding an infinite loop, affecting
+ mpfr_log10 in particular. See
+ commit 90de094f0d9c309daca707aa227470d810866616
+ */
+ mpfr_ui_pow_ui (x, 5, ULONG_MAX, MPFR_RNDN);
+ if (MPFR_EMAX_MAX <= ULONG_MAX) /* true with default _MPFR_EXP_FORMAT */
+ MPFR_ASSERTN (MPFR_IS_INF (x));
+
+ mpfr_clear (x);
+
+ set_emin (old_emin);
+ set_emax (old_emax);
+}
+
int
main (int argc, char *argv[])
{
@@ -180,6 +211,7 @@
}
test1 ();
+ huge ();
{
mpfr_t z, t;
diff -Naurd mpfr-4.2.0-a/PATCHES mpfr-4.2.0-b/PATCHES
--- mpfr-4.2.0-a/PATCHES 2023-04-17 21:18:26.860579184 +0000
+++ mpfr-4.2.0-b/PATCHES 2023-04-17 21:18:26.904579122 +0000
@@ -0,0 +1 @@
+multibyte-decimal_point
diff -Naurd mpfr-4.2.0-a/VERSION mpfr-4.2.0-b/VERSION
--- mpfr-4.2.0-a/VERSION 2023-04-17 21:18:00.512616059 +0000
+++ mpfr-4.2.0-b/VERSION 2023-04-17 21:18:26.904579122 +0000
@@ -1 +1 @@
-4.2.0-p2
+4.2.0-p3
diff -Naurd mpfr-4.2.0-a/src/mpfr.h mpfr-4.2.0-b/src/mpfr.h
--- mpfr-4.2.0-a/src/mpfr.h 2023-04-17 21:18:00.508616065 +0000
+++ mpfr-4.2.0-b/src/mpfr.h 2023-04-17 21:18:26.900579128 +0000
@@ -27,7 +27,7 @@
#define MPFR_VERSION_MAJOR 4
#define MPFR_VERSION_MINOR 2
#define MPFR_VERSION_PATCHLEVEL 0
-#define MPFR_VERSION_STRING "4.2.0-p2"
+#define MPFR_VERSION_STRING "4.2.0-p3"
/* User macros:
MPFR_USE_FILE: Define it to make MPFR define functions dealing
diff -Naurd mpfr-4.2.0-a/src/version.c mpfr-4.2.0-b/src/version.c
--- mpfr-4.2.0-a/src/version.c 2023-04-17 21:18:00.512616059 +0000
+++ mpfr-4.2.0-b/src/version.c 2023-04-17 21:18:26.904579122 +0000
@@ -25,5 +25,5 @@
const char *
mpfr_get_version (void)
{
- return "4.2.0-p2";
+ return "4.2.0-p3";
}
diff -Naurd mpfr-4.2.0-a/tests/tfprintf.c mpfr-4.2.0-b/tests/tfprintf.c
--- mpfr-4.2.0-a/tests/tfprintf.c 2023-01-05 17:09:48.000000000 +0000
+++ mpfr-4.2.0-b/tests/tfprintf.c 2023-04-17 21:18:26.896579133 +0000
@@ -61,6 +61,12 @@
exit (1); \
}
+#if MPFR_LCONV_DPTS
+#define DPLEN ((int) strlen (localeconv()->decimal_point))
+#else
+#define DPLEN 1
+#endif
+
/* limit for random precision in random() */
const int prec_max_printf = 5000;
@@ -195,12 +201,12 @@
lo, &ulo);
check_length (2, ulo, 36, lu);
check_vfprintf (fout, "a. %hi, b. %*f, c. %Re%hn", ush, 3, f, mpfr, &ush);
- check_length (3, ush, 46, hu);
+ check_length (3, ush, 45 + DPLEN, hu);
check_vfprintf (fout, "a. %hi, b. %f, c. %#.2Rf%n", sh, d, mpfr, &i);
- check_length (4, i, 29, d);
+ check_length (4, i, 28 + DPLEN, d);
check_vfprintf (fout, "a. %R*A, b. %Fe, c. %i%zn", rnd, mpfr, mpf, sz,
&sz);
- check_length (5, (unsigned long) sz, 34, lu); /* no format specifier "%zu" in C90 */
+ check_length (5, (unsigned long) sz, 33 + DPLEN, lu); /* no format specifier "%zu" in C90 */
check_vfprintf (fout, "a. %Pu, b. %c, c. %Zi%Zn", prec, ch, mpz, &mpz);
check_length_with_cmp (6, mpz, 17, mpz_cmp_ui (mpz, 17), Zi);
check_vfprintf (fout, "%% a. %#.0RNg, b. %Qx%Rn, c. %p", mpfr, mpq, &mpfr,
@@ -224,7 +230,7 @@
#ifdef PRINTF_L
check_vfprintf (fout, "a. %RA, b. %Lf, c. %QX%zn", mpfr, ld, mpq, &sz);
- check_length (9, (unsigned long) sz, 30, lu); /* no format specifier "%zu" in C90 */
+ check_length (9, (unsigned long) sz, 29 + DPLEN, lu); /* no format specifier "%zu" in C90 */
#endif
#ifndef NPRINTF_HH
diff -Naurd mpfr-4.2.0-a/tests/tprintf.c mpfr-4.2.0-b/tests/tprintf.c
--- mpfr-4.2.0-a/tests/tprintf.c 2023-01-05 17:09:48.000000000 +0000
+++ mpfr-4.2.0-b/tests/tprintf.c 2023-04-17 21:18:26.896579133 +0000
@@ -68,6 +68,12 @@
exit (1); \
}
+#if MPFR_LCONV_DPTS
+#define DPLEN ((int) strlen (localeconv()->decimal_point))
+#else
+#define DPLEN 1
+#endif
+
/* limit for random precision in random() */
const int prec_max_printf = 5000;
/* boolean: is stdout redirected to a file ? */
@@ -316,11 +322,11 @@
check_vprintf ("a. %c, b. %Rb, c. %u, d. %li%ln", i, mpfr, i, lo, &ulo);
check_length (2, ulo, 36, lu);
check_vprintf ("a. %hi, b. %*f, c. %Re%hn", ush, 3, f, mpfr, &ush);
- check_length (3, ush, 46, hu);
+ check_length (3, ush, 45 + DPLEN, hu);
check_vprintf ("a. %hi, b. %f, c. %#.2Rf%n", sh, d, mpfr, &i);
- check_length (4, i, 29, d);
+ check_length (4, i, 28 + DPLEN, d);
check_vprintf ("a. %R*A, b. %Fe, c. %i%zn", rnd, mpfr, mpf, sz, &sz);
- check_length (5, (unsigned long) sz, 34, lu); /* no format specifier '%zu' in C90 */
+ check_length (5, (unsigned long) sz, 33 + DPLEN, lu); /* no format specifier '%zu' in C90 */
check_vprintf ("a. %Pu, b. %c, c. %RUG, d. %Zi%Zn", prec, ch, mpfr, mpz, &mpz);
check_length_with_cmp (6, mpz, 24, mpz_cmp_ui (mpz, 24), Zi);
check_vprintf ("%% a. %#.0RNg, b. %Qx%Rn c. %p",
@@ -344,7 +350,7 @@
#ifdef PRINTF_L
check_vprintf ("a. %RA, b. %Lf, c. %QX%zn", mpfr, ld, mpq, &sz);
- check_length (9, (unsigned long) sz, 30, lu); /* no format specifier '%zu' in C90 */
+ check_length (9, (unsigned long) sz, 29 + DPLEN, lu); /* no format specifier '%zu' in C90 */
#endif
#ifndef NPRINTF_HH
diff -Naurd mpfr-4.2.0-a/PATCHES mpfr-4.2.0-b/PATCHES
--- mpfr-4.2.0-a/PATCHES 2023-04-17 21:19:01.988530337 +0000
+++ mpfr-4.2.0-b/PATCHES 2023-04-17 21:19:02.032530276 +0000
@@ -0,0 +1 @@
+rec_sqrt-zivloop
diff -Naurd mpfr-4.2.0-a/VERSION mpfr-4.2.0-b/VERSION
--- mpfr-4.2.0-a/VERSION 2023-04-17 21:18:26.904579122 +0000
+++ mpfr-4.2.0-b/VERSION 2023-04-17 21:19:02.032530276 +0000
@@ -1 +1 @@
-4.2.0-p3
+4.2.0-p4
diff -Naurd mpfr-4.2.0-a/src/mpfr.h mpfr-4.2.0-b/src/mpfr.h
--- mpfr-4.2.0-a/src/mpfr.h 2023-04-17 21:18:26.900579128 +0000
+++ mpfr-4.2.0-b/src/mpfr.h 2023-04-17 21:19:02.032530276 +0000
@@ -27,7 +27,7 @@
#define MPFR_VERSION_MAJOR 4
#define MPFR_VERSION_MINOR 2
#define MPFR_VERSION_PATCHLEVEL 0
-#define MPFR_VERSION_STRING "4.2.0-p3"
+#define MPFR_VERSION_STRING "4.2.0-p4"
/* User macros:
MPFR_USE_FILE: Define it to make MPFR define functions dealing
diff -Naurd mpfr-4.2.0-a/src/rec_sqrt.c mpfr-4.2.0-b/src/rec_sqrt.c
--- mpfr-4.2.0-a/src/rec_sqrt.c 2023-01-05 17:09:48.000000000 +0000
+++ mpfr-4.2.0-b/src/rec_sqrt.c 2023-04-17 21:19:02.024530287 +0000
@@ -463,6 +463,7 @@
int s, cy, inex;
mpfr_limb_ptr x;
MPFR_TMP_DECL(marker);
+ MPFR_ZIV_DECL (loop);
MPFR_LOG_FUNC
(("x[%Pu]=%.*Rg rnd=%d", mpfr_get_prec (u), mpfr_log_prec, u, rnd_mode),
@@ -530,6 +531,7 @@
wp = rp + 11;
if (wp < rn * GMP_NUMB_BITS)
wp = rn * GMP_NUMB_BITS;
+ MPFR_ZIV_INIT (loop, wp);
for (;;)
{
MPFR_TMP_MARK (marker);
@@ -561,8 +563,9 @@
}
MPFR_TMP_FREE(marker);
- wp += GMP_NUMB_BITS;
+ MPFR_ZIV_NEXT (loop, wp);
}
+ MPFR_ZIV_FREE (loop);
cy = mpfr_round_raw (MPFR_MANT(r), x, wp, 0, rp, rnd_mode, &inex);
MPFR_EXP(r) = - (MPFR_EXP(u) - 1 - s) / 2;
if (MPFR_UNLIKELY(cy != 0))
diff -Naurd mpfr-4.2.0-a/src/version.c mpfr-4.2.0-b/src/version.c
--- mpfr-4.2.0-a/src/version.c 2023-04-17 21:18:26.904579122 +0000
+++ mpfr-4.2.0-b/src/version.c 2023-04-17 21:19:02.032530276 +0000
@@ -25,5 +25,5 @@
const char *
mpfr_get_version (void)
{
- return "4.2.0-p3";
+ return "4.2.0-p4";
}
diff -Naurd mpfr-4.2.0-a/tests/trec_sqrt.c mpfr-4.2.0-b/tests/trec_sqrt.c
--- mpfr-4.2.0-a/tests/trec_sqrt.c 2023-01-05 17:09:48.000000000 +0000
+++ mpfr-4.2.0-b/tests/trec_sqrt.c 2023-04-17 21:19:02.028530282 +0000
@@ -242,6 +242,8 @@
data_check ("data/rec_sqrt", mpfr_rec_sqrt, "mpfr_rec_sqrt");
bad_cases (mpfr_rec_sqrt, pm2, "mpfr_rec_sqrt", 0, -256, 255, 4, 128,
800, 50);
+ bad_cases (mpfr_rec_sqrt, pm2, "mpfr_rec_sqrt", 0, -256, 255, 9999, 9999,
+ 120000, 1);
end:
tests_end_mpfr ();

View File

@ -1,3 +1,18 @@
-------------------------------------------------------------------
Tue Apr 18 08:13:21 UTC 2023 - Richard Biener <rguenther@suse.com>
- Add mpfr-4.2.0-cummulative.patch, cummulative patches for
mpfr 4.2.0:
* A test of the thousands separator in tsprintf.c is based on the
output from the GNU C Library up to 2.36, which is incorrect.
* The mpfr_ui_pow_ui function has infinite loop in case of overflow.
* The tfprintf and tprintf tests may fail in locales where decimal_point
has several bytes, such as ps_AF.
* In particular cases that are very hard to round, mpfr_rec_sqrt may yield
a stack overflow due to many small allocations in the stack, based on
alloca().
- Remove tests-tsprintf.patch that's included in the above set.
-------------------------------------------------------------------
Tue Jan 31 15:58:22 UTC 2023 - Andreas Schwab <schwab@suse.de>

View File

@ -27,7 +27,7 @@ Source0: https://www.mpfr.org/mpfr-%{version}/mpfr-%{version}.tar.xz
Source1: https://www.mpfr.org/mpfr-%{version}/mpfr-%{version}.tar.xz.asc
Source2: %{name}.keyring
Source3: baselibs.conf
Patch0: tests-tsprintf.patch
Patch0: mpfr-4.2.0-cummulative.patch
BuildRequires: gmp-devel
BuildRequires: pkgconfig

View File

@ -1,56 +0,0 @@
From 5172494c09718ffcb7ef1f19b3b211e3bce8781a Mon Sep 17 00:00:00 2001
From: Vincent Lefevre <vincent@vinc17.net>
Date: Tue, 10 Jan 2023 17:05:17 +0100
Subject: [PATCH] [tests/tsprintf.c] Modified a buggy test of the thousands
separator.
The test
check_vsprintf ("+01,234,567 :", "%0+ -'13.10Pd:", (mpfr_prec_t) 1234567);
is based on the output from glibc up to 2.36, which is incorrect:
https://sourceware.org/bugzilla/show_bug.cgi?id=23432
The GNU C Library has apparently been partially fixed in its Git
repository for the future 2.37, since a tsprintf failure has been
reported (this is a bug in this test, not in the MPFR library):
https://sympa.inria.fr/sympa/arc/mpfr/2023-01/msg00001.html
So, modified the test to avoid the particular case of leading zeros
due to the precision field larger than the number of digits. This
case has already been tested without the thousands separator (where
there are no issues with the C libraries), so that we do not miss
much testing. Added a comment explaining the issue and a possible
solution for future testing of this particular case (if need be).
---
tests/tsprintf.c | 12 +++++++++++-
1 file changed, 11 insertions(+), 1 deletion(-)
diff --git a/tests/tsprintf.c b/tests/tsprintf.c
index c68b2ba71..c0182503b 100644
--- a/tests/tsprintf.c
+++ b/tests/tsprintf.c
@@ -1719,7 +1719,17 @@ test_locale (void)
check_sprintf ("000000001,000", "%'013.4Rg", x);
#ifdef PRINTF_GROUPFLAG
- check_vsprintf ("+01,234,567 :", "%0+ -'13.10Pd:", (mpfr_prec_t) 1234567);
+ /* Do not test the thousands separator with a precision field larger
+ than the number of digits (thus needing leading zeros), such as
+ "%0+ -'13.10Pd:" (used up to MPFR 4.2.0), since the GNU libc is
+ buggy: https://sourceware.org/bugzilla/show_bug.cgi?id=23432
+ We don't know about the other implementations.
+ If we wanted to check that and avoid a failure of the test because of
+ a buggy C library (while MPFR would be consistent with the C library),
+ we could compare the MPFR output with both the correct output and the
+ output from the C library (possibly buggy). But to do that in a clean
+ way, this would require a change in the check_vsprintf() call. */
+ check_vsprintf ("+1,234,567 :", "%0+ -'13Pd:", (mpfr_prec_t) 1234567);
#endif
mpfr_clear (x);
--
2.39.1