diff --git a/allpatches b/allpatches index 2f9fa04..e73d95a 100644 --- a/allpatches +++ b/allpatches @@ -1830,3 +1830,853 @@ diff -Naurd mpfr-4.1.0-a/tests/tj1.c mpfr-4.1.0-b/tests/tj1.c test_small (); mpfr_init (x); +diff -Naurd mpfr-4.1.0-a/PATCHES mpfr-4.1.0-b/PATCHES +--- mpfr-4.1.0-a/PATCHES 2021-03-09 13:55:43.183158946 +0000 ++++ mpfr-4.1.0-b/PATCHES 2021-03-09 13:55:43.223158508 +0000 +@@ -0,0 +1 @@ ++macros +diff -Naurd mpfr-4.1.0-a/VERSION mpfr-4.1.0-b/VERSION +--- mpfr-4.1.0-a/VERSION 2021-02-17 17:25:46.440981068 +0000 ++++ mpfr-4.1.0-b/VERSION 2021-03-09 13:55:43.223158508 +0000 +@@ -1 +1 @@ +-4.1.0-p9 ++4.1.0-p10 +diff -Naurd mpfr-4.1.0-a/doc/mpfr.info mpfr-4.1.0-b/doc/mpfr.info +--- mpfr-4.1.0-a/doc/mpfr.info 2020-07-10 11:59:13.000000000 +0000 ++++ mpfr-4.1.0-b/doc/mpfr.info 2021-03-09 13:55:51.167071327 +0000 +@@ -3217,7 +3217,11 @@ + + Each function in this interface is also implemented as a macro for + efficiency reasons: for example ‘mpfr_custom_init (s, p)’ uses the +-macro, while ‘(mpfr_custom_init) (s, p)’ uses the function. ++macro, while ‘(mpfr_custom_init) (s, p)’ uses the function. Note that ++the macro may evaluate arguments multiple times (or none). Moreover, ++macros implementing functions with the ‘void’ return type may not be ++used in contexts where an expression is expected, e.g., inside ++‘for(...)’ or before a comma operator. + + Note 1: MPFR functions may still initialize temporary floating-point + numbers using ‘mpfr_init’ and similar functions. See Custom Allocation +@@ -4579,13 +4583,13 @@ + (line 115) + * mpfr_csch: Transcendental Functions. + (line 180) +-* mpfr_custom_get_exp: Custom Interface. (line 76) +-* mpfr_custom_get_kind: Custom Interface. (line 66) +-* mpfr_custom_get_significand: Custom Interface. (line 71) +-* mpfr_custom_get_size: Custom Interface. (line 37) +-* mpfr_custom_init: Custom Interface. (line 41) +-* mpfr_custom_init_set: Custom Interface. (line 48) +-* mpfr_custom_move: Custom Interface. (line 85) ++* mpfr_custom_get_exp: Custom Interface. (line 80) ++* mpfr_custom_get_kind: Custom Interface. (line 70) ++* mpfr_custom_get_significand: Custom Interface. (line 75) ++* mpfr_custom_get_size: Custom Interface. (line 41) ++* mpfr_custom_init: Custom Interface. (line 45) ++* mpfr_custom_init_set: Custom Interface. (line 52) ++* mpfr_custom_move: Custom Interface. (line 89) + * MPFR_DECL_INIT: Initialization Functions. + (line 77) + * mpfr_digamma: Transcendental Functions. +@@ -5165,19 +5169,19 @@ + Node: Memory Handling Functions155904 + Node: Compatibility with MPF157792 + Node: Custom Interface160961 +-Node: Internals165592 +-Node: API Compatibility167136 +-Node: Type and Macro Changes169084 +-Node: Added Functions172267 +-Node: Changed Functions177074 +-Node: Removed Functions184433 +-Node: Other Changes185163 +-Node: MPFR and the IEEE 754 Standard186864 +-Node: Contributors189481 +-Node: References192620 +-Node: GNU Free Documentation License194501 +-Node: Concept Index217095 +-Node: Function and Type Index223168 ++Node: Internals165852 ++Node: API Compatibility167396 ++Node: Type and Macro Changes169344 ++Node: Added Functions172527 ++Node: Changed Functions177334 ++Node: Removed Functions184693 ++Node: Other Changes185423 ++Node: MPFR and the IEEE 754 Standard187124 ++Node: Contributors189741 ++Node: References192880 ++Node: GNU Free Documentation License194761 ++Node: Concept Index217355 ++Node: Function and Type Index223428 +  + End Tag Table + +diff -Naurd mpfr-4.1.0-a/doc/mpfr.texi mpfr-4.1.0-b/doc/mpfr.texi +--- mpfr-4.1.0-a/doc/mpfr.texi 2020-07-10 11:52:33.000000000 +0000 ++++ mpfr-4.1.0-b/doc/mpfr.texi 2021-03-09 13:55:43.211158639 +0000 +@@ -3817,6 +3817,12 @@ + Each function in this interface is also implemented as a macro for + efficiency reasons: for example @code{mpfr_custom_init (s, p)} + uses the macro, while @code{(mpfr_custom_init) (s, p)} uses the function. ++Note that the macro may evaluate arguments multiple times (or none). ++Moreover, macros implementing functions with the @code{void} return type ++may not be used in contexts where an expression is expected, e.g., inside ++@code{for(...)} or before a comma operator. ++@c These limitations with macros cannot be avoided in a C90 compatible way. ++@c In the future, inline functions could be used. + + Note 1: MPFR functions may still initialize temporary floating-point numbers + using @code{mpfr_init} and similar functions. See Custom Allocation (GNU MP)@. +diff -Naurd mpfr-4.1.0-a/src/mpfr.h mpfr-4.1.0-b/src/mpfr.h +--- mpfr-4.1.0-a/src/mpfr.h 2021-02-17 17:25:46.436981105 +0000 ++++ mpfr-4.1.0-b/src/mpfr.h 2021-03-09 13:55:43.223158508 +0000 +@@ -27,7 +27,7 @@ + #define MPFR_VERSION_MAJOR 4 + #define MPFR_VERSION_MINOR 1 + #define MPFR_VERSION_PATCHLEVEL 0 +-#define MPFR_VERSION_STRING "4.1.0-p9" ++#define MPFR_VERSION_STRING "4.1.0-p10" + + /* User macros: + MPFR_USE_FILE: Define it to make MPFR define functions dealing +@@ -833,23 +833,39 @@ + even if it produces faster and smaller code. */ + #ifndef MPFR_USE_NO_MACRO + +-/* Inlining these functions is both faster and smaller */ +-#define mpfr_nan_p(_x) ((_x)->_mpfr_exp == __MPFR_EXP_NAN) +-#define mpfr_inf_p(_x) ((_x)->_mpfr_exp == __MPFR_EXP_INF) +-#define mpfr_zero_p(_x) ((_x)->_mpfr_exp == __MPFR_EXP_ZERO) +-#define mpfr_regular_p(_x) ((_x)->_mpfr_exp > __MPFR_EXP_INF) ++/* In the implementation of these macros, we need to make sure that the ++ arguments are evaluated one time exactly and that type conversion is ++ done as it would be with a function. Tests should be added to ensure ++ that. ++ Note that the macros for the custom interface are not concerned; the ++ MPFR manual has been clarified. */ ++ ++/* Prevent x from being used as an lvalue. ++ Thanks to Wojtek Lerch and Tim Rentsch for the idea. */ ++#define MPFR_VALUE_OF(x) (0 ? (x) : (x)) ++ ++/* The following macro converts the argument to mpfr_srcptr, as in type ++ conversion for function parameters. But it will detect disallowed ++ implicit conversions, e.g. when the argument has an integer type. */ ++#define MPFR_SRCPTR(x) ((mpfr_srcptr) (0 ? (x) : (mpfr_srcptr) (x))) ++#define MPFR_GET_SIGN(_x) MPFR_VALUE_OF(MPFR_SIGN(MPFR_SRCPTR(_x))) ++ ++#define mpfr_nan_p(_x) (MPFR_SRCPTR(_x)->_mpfr_exp == __MPFR_EXP_NAN) ++#define mpfr_inf_p(_x) (MPFR_SRCPTR(_x)->_mpfr_exp == __MPFR_EXP_INF) ++#define mpfr_zero_p(_x) (MPFR_SRCPTR(_x)->_mpfr_exp == __MPFR_EXP_ZERO) ++#define mpfr_regular_p(_x) (MPFR_SRCPTR(_x)->_mpfr_exp > __MPFR_EXP_INF) ++ ++/* mpfr_sgn is documented as a macro, thus the following code is fine. ++ But it would be safer to regard it as a function in some future ++ MPFR version. */ + #define mpfr_sgn(_x) \ + ((_x)->_mpfr_exp < __MPFR_EXP_INF ? \ + (mpfr_nan_p (_x) ? mpfr_set_erangeflag () : (mpfr_void) 0), 0 : \ + MPFR_SIGN (_x)) + +-/* Prevent them from using as lvalues */ +-#define MPFR_VALUE_OF(x) (0 ? (x) : (x)) +-#define mpfr_get_prec(_x) MPFR_VALUE_OF((_x)->_mpfr_prec) +-#define mpfr_get_exp(_x) MPFR_VALUE_OF((_x)->_mpfr_exp) +-/* Note 1: If need be, the MPFR_VALUE_OF can be used for other expressions +- (of any type). Thanks to Wojtek Lerch and Tim Rentsch for the idea. +- Note 2: Defining mpfr_get_exp() as a macro has the effect to disable ++#define mpfr_get_prec(_x) MPFR_VALUE_OF(MPFR_SRCPTR(_x)->_mpfr_prec) ++#define mpfr_get_exp(_x) MPFR_VALUE_OF(MPFR_SRCPTR(_x)->_mpfr_exp) ++/* Note: Defining mpfr_get_exp() as a macro has the effect to disable + the check that the argument is a pure FP number (done in the function); + this increases the risk of undetected error and makes debugging more + complex. Is it really worth in practice? (Potential FIXME) */ +@@ -861,11 +877,17 @@ + + #define mpfr_cmp_ui(b,i) mpfr_cmp_ui_2exp((b),(i),0) + #define mpfr_cmp_si(b,i) mpfr_cmp_si_2exp((b),(i),0) +-#define mpfr_set(a,b,r) mpfr_set4(a,b,r,MPFR_SIGN(b)) ++#if __GNUC__ > 2 || __GNUC_MINOR__ >= 95 ++#define mpfr_set(a,b,r) \ ++ __extension__ ({ \ ++ mpfr_srcptr _p = (b); \ ++ mpfr_set4(a,_p,r,MPFR_SIGN(_p)); \ ++ }) ++#endif + #define mpfr_abs(a,b,r) mpfr_set4(a,b,r,1) +-#define mpfr_copysign(a,b,c,r) mpfr_set4(a,b,r,MPFR_SIGN(c)) ++#define mpfr_copysign(a,b,c,r) mpfr_set4(a,b,r,MPFR_GET_SIGN(c)) + #define mpfr_setsign(a,b,s,r) mpfr_set4(a,b,r,(s) ? -1 : 1) +-#define mpfr_signbit(x) (MPFR_SIGN(x) < 0) ++#define mpfr_signbit(x) (MPFR_GET_SIGN(x) < 0) + #define mpfr_cmp(b, c) mpfr_cmp3(b, c, 1) + #define mpfr_mul_2exp(y,x,n,r) mpfr_mul_2ui((y),(x),(n),(r)) + #define mpfr_div_2exp(y,x,n,r) mpfr_div_2ui((y),(x),(n),(r)) +diff -Naurd mpfr-4.1.0-a/src/ubf.c mpfr-4.1.0-b/src/ubf.c +--- mpfr-4.1.0-a/src/ubf.c 2020-02-12 01:38:57.000000000 +0000 ++++ mpfr-4.1.0-b/src/ubf.c 2021-03-09 13:55:43.211158639 +0000 +@@ -78,7 +78,7 @@ + mpfr_get_prec (b), mpfr_log_prec, b, + mpfr_get_prec (c), mpfr_log_prec, c), + ("a[%Pu]=%.*Rg", +- mpfr_get_prec (a), mpfr_log_prec, a)); ++ mpfr_get_prec ((mpfr_ptr) a), mpfr_log_prec, a)); + + MPFR_ASSERTD ((mpfr_ptr) a != b); + MPFR_ASSERTD ((mpfr_ptr) a != c); +diff -Naurd mpfr-4.1.0-a/src/version.c mpfr-4.1.0-b/src/version.c +--- mpfr-4.1.0-a/src/version.c 2021-02-17 17:25:46.440981068 +0000 ++++ mpfr-4.1.0-b/src/version.c 2021-03-09 13:55:43.223158508 +0000 +@@ -25,5 +25,5 @@ + const char * + mpfr_get_version (void) + { +- return "4.1.0-p9"; ++ return "4.1.0-p10"; + } +diff -Naurd mpfr-4.1.0-a/tests/mpfr-test.h mpfr-4.1.0-b/tests/mpfr-test.h +--- mpfr-4.1.0-a/tests/mpfr-test.h 2021-02-17 17:25:46.424981219 +0000 ++++ mpfr-4.1.0-b/tests/mpfr-test.h 2021-03-09 13:55:43.211158639 +0000 +@@ -92,6 +92,32 @@ + #define STRINGIZE(S) #S + #define MAKE_STR(S) STRINGIZE(S) + ++/* In C (but not C++), mpfr_ptr and mpfr_srcptr arguments can be provided ++ in a different pointer type, such as void *. For functions implemented ++ as macros, the type conversion for the function parameters will not be ++ done by the compiler, which means potential bugs in these implementations ++ if we forget to take these unusual cases into account. So we need to test ++ such arguments, in order to make sure that the arguments are converted to ++ the expected type when needed. ++ ++ However, at least when the function is not implemented as a macro (which ++ is the case when MPFR_USE_NO_MACRO is defined), such tests with void * ++ arguments are not valid in C++; therefore, we will not do the cast to ++ void * if the __cplusplus macro is defined. And with GCC compilers (and ++ compatible), we will ignore the -Wc++-compat option around these tests. ++ ++ Note: in the future, inline functions could be used instead of macros, ++ and such tests would become useless (except to detect compiler bugs). ++*/ ++#if defined (__cplusplus) ++#define VOIDP_CAST(X) (X) ++#else ++#define VOIDP_CAST(X) ((void *) (X)) ++#if defined (__GNUC__) ++#define IGNORE_CPP_COMPAT ++#endif ++#endif ++ + #if defined (__cplusplus) + extern "C" { + #endif +diff -Naurd mpfr-4.1.0-a/tests/tcopysign.c mpfr-4.1.0-b/tests/tcopysign.c +--- mpfr-4.1.0-a/tests/tcopysign.c 2020-01-08 18:11:13.000000000 +0000 ++++ mpfr-4.1.0-b/tests/tcopysign.c 2021-03-09 13:55:43.211158639 +0000 +@@ -26,26 +26,72 @@ + copysign_variant (mpfr_ptr z, mpfr_srcptr x, mpfr_srcptr y, + mpfr_rnd_t rnd_mode, int k) + { ++ mpfr_srcptr p; ++ int a = 0, b = 0, c = 0; ++ ++ /* invalid sign, to test that the sign is always correctly set */ ++ MPFR_SIGN (z) = 0; ++ ++ if (k >= 8) ++ { ++ MPFR_ASSERTN (MPFR_PREC (z) >= MPFR_PREC (x)); ++ mpfr_set (z, x, MPFR_RNDN); ++ p = z; ++ k -= 8; ++ } ++ else ++ p = x; ++ + mpfr_clear_flags (); + switch (k) + { + case 0: +- mpfr_copysign (z, x, y, MPFR_RNDN); ++ mpfr_copysign (z, p, y, rnd_mode); + return; + case 1: +- (mpfr_copysign) (z, x, y, MPFR_RNDN); ++ (mpfr_copysign) (z, p, y, rnd_mode); + return; + case 2: +- mpfr_setsign (z, x, mpfr_signbit (y), MPFR_RNDN); ++#ifdef IGNORE_CPP_COMPAT ++#pragma GCC diagnostic push ++#pragma GCC diagnostic ignored "-Wc++-compat" ++#endif ++ mpfr_copysign ((a++, VOIDP_CAST(z)), ++ (b++, VOIDP_CAST(p)), ++ (c++, VOIDP_CAST(y)), rnd_mode); ++#ifdef IGNORE_CPP_COMPAT ++#pragma GCC diagnostic pop ++#endif ++ MPFR_ASSERTN (a == 1); ++ MPFR_ASSERTN (b == 1); ++ MPFR_ASSERTN (c == 1); + return; + case 3: +- mpfr_setsign (z, x, (mpfr_signbit) (y), MPFR_RNDN); ++ mpfr_setsign (z, p, mpfr_signbit (y), rnd_mode); + return; + case 4: +- (mpfr_setsign) (z, x, mpfr_signbit (y), MPFR_RNDN); ++ mpfr_setsign (z, p, (mpfr_signbit) (y), rnd_mode); + return; + case 5: +- (mpfr_setsign) (z, x, (mpfr_signbit) (y), MPFR_RNDN); ++ (mpfr_setsign) (z, p, mpfr_signbit (y), rnd_mode); ++ return; ++ case 6: ++ (mpfr_setsign) (z, p, (mpfr_signbit) (y), rnd_mode); ++ return; ++ case 7: ++#ifdef IGNORE_CPP_COMPAT ++#pragma GCC diagnostic push ++#pragma GCC diagnostic ignored "-Wc++-compat" ++#endif ++ mpfr_setsign ((a++, VOIDP_CAST(z)), ++ (b++, VOIDP_CAST(p)), ++ mpfr_signbit ((c++, VOIDP_CAST(y))), rnd_mode); ++#ifdef IGNORE_CPP_COMPAT ++#pragma GCC diagnostic pop ++#endif ++ MPFR_ASSERTN (a == 1); ++ MPFR_ASSERTN (b == 1); ++ MPFR_ASSERTN (c == 1); + return; + } + } +@@ -64,7 +110,7 @@ + + for (i = 0; i <= 1; i++) + for (j = 0; j <= 1; j++) +- for (k = 0; k <= 5; k++) ++ for (k = 0; k < 16; k++) + { + mpfr_set_nan (x); + i ? MPFR_SET_NEG (x) : MPFR_SET_POS (x); +diff -Naurd mpfr-4.1.0-a/tests/texceptions.c mpfr-4.1.0-b/tests/texceptions.c +--- mpfr-4.1.0-a/tests/texceptions.c 2020-01-08 18:11:13.000000000 +0000 ++++ mpfr-4.1.0-b/tests/texceptions.c 2021-03-09 13:55:43.211158639 +0000 +@@ -103,10 +103,26 @@ + check_get_prec (void) + { + mpfr_t x; ++ int i = 0; + + mpfr_init2 (x, 17); +- if (mpfr_get_prec (x) != 17 || (mpfr_get_prec)(x) != 17) ++ ++ if (mpfr_get_prec (x) != 17 || (mpfr_get_prec) (x) != 17) + PRINT_ERROR ("mpfr_get_prec"); ++ ++#ifdef IGNORE_CPP_COMPAT ++#pragma GCC diagnostic push ++#pragma GCC diagnostic ignored "-Wc++-compat" ++#endif ++ ++ if (mpfr_get_prec ((i++, VOIDP_CAST(x))) != 17) ++ PRINT_ERROR ("mpfr_get_prec (2)"); ++ ++#ifdef IGNORE_CPP_COMPAT ++#pragma GCC diagnostic pop ++#endif ++ ++ MPFR_ASSERTN (i == 1); + mpfr_clear (x); + } + +diff -Naurd mpfr-4.1.0-a/tests/tisnan.c mpfr-4.1.0-b/tests/tisnan.c +--- mpfr-4.1.0-a/tests/tisnan.c 2020-01-08 18:11:13.000000000 +0000 ++++ mpfr-4.1.0-b/tests/tisnan.c 2021-03-09 13:55:43.211158639 +0000 +@@ -27,180 +27,235 @@ + main (void) + { + mpfr_t x; ++ int i = 0, j = 0; ++ ++ /* We need to check that when the function is implemented by a macro, ++ it behaves correctly. */ ++#define ARG (i++, VOIDP_CAST(x)) ++#define CHECK MPFR_ASSERTN (i == ++j) + + tests_start_mpfr (); + + mpfr_init (x); + ++#if 0 ++ /* The following should yield a compilation error when the functions ++ are implemented as macros. Change 0 to 1 above in order to test. */ ++ (void) (mpfr_nan_p (1L)); ++ (void) (mpfr_inf_p (1L)); ++ (void) (mpfr_number_p (1L)); ++ (void) (mpfr_zero_p (1L)); ++ (void) (mpfr_regular_p (1L)); ++#endif ++ ++#ifdef IGNORE_CPP_COMPAT ++#pragma GCC diagnostic push ++#pragma GCC diagnostic ignored "-Wc++-compat" ++#endif ++ + /* check +infinity gives non-zero for mpfr_inf_p only */ + mpfr_set_ui (x, 1L, MPFR_RNDZ); + mpfr_div_ui (x, x, 0L, MPFR_RNDZ); +- if (mpfr_nan_p (x) || (mpfr_nan_p) (x) ) ++ if (mpfr_nan_p (x) || (mpfr_nan_p) (x) || mpfr_nan_p (ARG)) + { + printf ("Error: mpfr_nan_p(+Inf) gives non-zero\n"); + exit (1); + } +- if (mpfr_inf_p (x) == 0) ++ CHECK; ++ if (!mpfr_inf_p (x) || !(mpfr_inf_p) (x) || !mpfr_inf_p (ARG)) + { + printf ("Error: mpfr_inf_p(+Inf) gives zero\n"); + exit (1); + } +- if (mpfr_number_p (x) || (mpfr_number_p) (x) ) ++ CHECK; ++ if (mpfr_number_p (x) || (mpfr_number_p) (x) || mpfr_number_p (ARG)) + { + printf ("Error: mpfr_number_p(+Inf) gives non-zero\n"); + exit (1); + } +- if (mpfr_zero_p (x) || (mpfr_zero_p) (x) ) ++ CHECK; ++ if (mpfr_zero_p (x) || (mpfr_zero_p) (x) || mpfr_zero_p (ARG)) + { + printf ("Error: mpfr_zero_p(+Inf) gives non-zero\n"); + exit (1); + } +- if (mpfr_regular_p (x) || (mpfr_regular_p) (x) ) ++ CHECK; ++ if (mpfr_regular_p (x) || (mpfr_regular_p) (x) || mpfr_regular_p (ARG)) + { + printf ("Error: mpfr_regular_p(+Inf) gives non-zero\n"); + exit (1); + } ++ CHECK; + + /* same for -Inf */ + mpfr_neg (x, x, MPFR_RNDN); +- if (mpfr_nan_p (x) || (mpfr_nan_p(x))) ++ if (mpfr_nan_p (x) || (mpfr_nan_p) (x) || mpfr_nan_p (ARG)) + { + printf ("Error: mpfr_nan_p(-Inf) gives non-zero\n"); + exit (1); + } +- if (mpfr_inf_p (x) == 0) ++ CHECK; ++ if (!mpfr_inf_p (x) || !(mpfr_inf_p) (x) || !mpfr_inf_p (ARG)) + { + printf ("Error: mpfr_inf_p(-Inf) gives zero\n"); + exit (1); + } +- if (mpfr_number_p (x) || (mpfr_number_p)(x) ) ++ CHECK; ++ if (mpfr_number_p (x) || (mpfr_number_p) (x) || mpfr_number_p (ARG)) + { + printf ("Error: mpfr_number_p(-Inf) gives non-zero\n"); + exit (1); + } +- if (mpfr_zero_p (x) || (mpfr_zero_p)(x) ) ++ CHECK; ++ if (mpfr_zero_p (x) || (mpfr_zero_p) (x) || mpfr_zero_p (ARG)) + { + printf ("Error: mpfr_zero_p(-Inf) gives non-zero\n"); + exit (1); + } +- if (mpfr_regular_p (x) || (mpfr_regular_p) (x) ) ++ CHECK; ++ if (mpfr_regular_p (x) || (mpfr_regular_p) (x) || mpfr_regular_p (ARG)) + { + printf ("Error: mpfr_regular_p(-Inf) gives non-zero\n"); + exit (1); + } ++ CHECK; + + /* same for NaN */ + mpfr_sub (x, x, x, MPFR_RNDN); +- if (mpfr_nan_p (x) == 0) ++ if (!mpfr_nan_p (x) || !(mpfr_nan_p) (x) || !mpfr_nan_p (ARG)) + { + printf ("Error: mpfr_nan_p(NaN) gives zero\n"); + exit (1); + } +- if (mpfr_inf_p (x) || (mpfr_inf_p)(x) ) ++ CHECK; ++ if (mpfr_inf_p (x) || (mpfr_inf_p) (x) || mpfr_inf_p (ARG)) + { + printf ("Error: mpfr_inf_p(NaN) gives non-zero\n"); + exit (1); + } +- if (mpfr_number_p (x) || (mpfr_number_p) (x) ) ++ CHECK; ++ if (mpfr_number_p (x) || (mpfr_number_p) (x) || mpfr_number_p (ARG)) + { + printf ("Error: mpfr_number_p(NaN) gives non-zero\n"); + exit (1); + } +- if (mpfr_zero_p (x) || (mpfr_zero_p)(x) ) ++ CHECK; ++ if (mpfr_zero_p (x) || (mpfr_zero_p) (x) || mpfr_zero_p (ARG)) + { + printf ("Error: mpfr_number_p(NaN) gives non-zero\n"); + exit (1); + } +- if (mpfr_regular_p (x) || (mpfr_regular_p) (x) ) ++ CHECK; ++ if (mpfr_regular_p (x) || (mpfr_regular_p) (x) || mpfr_regular_p (ARG)) + { + printf ("Error: mpfr_regular_p(NaN) gives non-zero\n"); + exit (1); + } ++ CHECK; + + /* same for a regular number */ + mpfr_set_ui (x, 1, MPFR_RNDN); +- if (mpfr_nan_p (x) || (mpfr_nan_p)(x)) ++ if (mpfr_nan_p (x) || (mpfr_nan_p) (x) || mpfr_nan_p (ARG)) + { + printf ("Error: mpfr_nan_p(1) gives non-zero\n"); + exit (1); + } +- if (mpfr_inf_p (x) || (mpfr_inf_p)(x) ) ++ CHECK; ++ if (mpfr_inf_p (x) || (mpfr_inf_p) (x) || mpfr_inf_p (ARG)) + { + printf ("Error: mpfr_inf_p(1) gives non-zero\n"); + exit (1); + } +- if (mpfr_number_p (x) == 0) ++ CHECK; ++ if (!mpfr_number_p (x) || !(mpfr_number_p) (x) || !mpfr_number_p (ARG)) + { + printf ("Error: mpfr_number_p(1) gives zero\n"); + exit (1); + } +- if (mpfr_zero_p (x) || (mpfr_zero_p) (x) ) ++ CHECK; ++ if (mpfr_zero_p (x) || (mpfr_zero_p) (x) || mpfr_zero_p (ARG)) + { + printf ("Error: mpfr_zero_p(1) gives non-zero\n"); + exit (1); + } +- if (mpfr_regular_p (x) == 0 || (mpfr_regular_p) (x) == 0) ++ CHECK; ++ if (!mpfr_regular_p (x) || !(mpfr_regular_p) (x) || !mpfr_regular_p (ARG)) + { + printf ("Error: mpfr_regular_p(1) gives zero\n"); + exit (1); + } ++ CHECK; + + /* Same for +0 */ + mpfr_set_ui (x, 0, MPFR_RNDN); +- if (mpfr_nan_p (x) || (mpfr_nan_p)(x)) ++ if (mpfr_nan_p (x) || (mpfr_nan_p) (x) || mpfr_nan_p (ARG)) + { + printf ("Error: mpfr_nan_p(+0) gives non-zero\n"); + exit (1); + } +- if (mpfr_inf_p (x) || (mpfr_inf_p)(x) ) ++ CHECK; ++ if (mpfr_inf_p (x) || (mpfr_inf_p) (x) || mpfr_inf_p (ARG)) + { + printf ("Error: mpfr_inf_p(+0) gives non-zero\n"); + exit (1); + } +- if (mpfr_number_p (x) == 0) ++ CHECK; ++ if (!mpfr_number_p (x) || !(mpfr_number_p) (x) || !mpfr_number_p (ARG)) + { + printf ("Error: mpfr_number_p(+0) gives zero\n"); + exit (1); + } +- if (mpfr_zero_p (x) == 0 ) ++ CHECK; ++ if (!mpfr_zero_p (x) || !(mpfr_zero_p) (x) || !mpfr_zero_p (ARG)) + { + printf ("Error: mpfr_zero_p(+0) gives zero\n"); + exit (1); + } +- if (mpfr_regular_p (x) || (mpfr_regular_p) (x) ) ++ CHECK; ++ if (mpfr_regular_p (x) || (mpfr_regular_p) (x) || mpfr_regular_p (ARG)) + { + printf ("Error: mpfr_regular_p(+0) gives non-zero\n"); + exit (1); + } ++ CHECK; + + /* Same for -0 */ + mpfr_set_ui (x, 0, MPFR_RNDN); + mpfr_neg (x, x, MPFR_RNDN); +- if (mpfr_nan_p (x) || (mpfr_nan_p)(x)) ++ if (mpfr_nan_p (x) || (mpfr_nan_p) (x) || mpfr_nan_p (ARG)) + { + printf ("Error: mpfr_nan_p(-0) gives non-zero\n"); + exit (1); + } +- if (mpfr_inf_p (x) || (mpfr_inf_p)(x) ) ++ CHECK; ++ if (mpfr_inf_p (x) || (mpfr_inf_p) (x) || mpfr_inf_p (ARG)) + { + printf ("Error: mpfr_inf_p(-0) gives non-zero\n"); + exit (1); + } +- if (mpfr_number_p (x) == 0) ++ CHECK; ++ if (!mpfr_number_p (x) || !(mpfr_number_p) (x) || !mpfr_number_p (ARG)) + { + printf ("Error: mpfr_number_p(-0) gives zero\n"); + exit (1); + } +- if (mpfr_zero_p (x) == 0 ) ++ CHECK; ++ if (!mpfr_zero_p (x) || !(mpfr_zero_p) (x) || !mpfr_zero_p (ARG)) + { + printf ("Error: mpfr_zero_p(-0) gives zero\n"); + exit (1); + } +- if (mpfr_regular_p (x) || (mpfr_regular_p) (x) ) ++ CHECK; ++ if (mpfr_regular_p (x) || (mpfr_regular_p) (x) || mpfr_regular_p (ARG)) + { + printf ("Error: mpfr_regular_p(-0) gives non-zero\n"); + exit (1); + } ++ CHECK; ++ ++#ifdef IGNORE_CPP_COMPAT ++#pragma GCC diagnostic pop ++#endif + + mpfr_clear (x); + +diff -Naurd mpfr-4.1.0-a/tests/tset.c mpfr-4.1.0-b/tests/tset.c +--- mpfr-4.1.0-a/tests/tset.c 2020-01-08 18:11:13.000000000 +0000 ++++ mpfr-4.1.0-b/tests/tset.c 2021-03-09 13:55:43.207158683 +0000 +@@ -207,7 +207,7 @@ + static void + check_ternary_value (void) + { +- int p, q, rnd; ++ int k, p, q, rnd; + int inexact, cmp; + mpfr_t x, y; + +@@ -226,28 +226,45 @@ + { + if (rnd == MPFR_RNDF) /* the test below makes no sense */ + continue; +- inexact = mpfr_set (y, x, (mpfr_rnd_t) rnd); +- cmp = mpfr_cmp (y, x); +- if (((inexact == 0) && (cmp != 0)) || +- ((inexact > 0) && (cmp <= 0)) || +- ((inexact < 0) && (cmp >= 0))) +- { +- printf ("Wrong ternary value in mpfr_set for %s: expected" +- " %d, got %d\n", +- mpfr_print_rnd_mode ((mpfr_rnd_t) rnd), cmp, +- inexact); +- exit (1); +- } +- /* Test mpfr_set function too */ +- inexact = (mpfr_set) (y, x, (mpfr_rnd_t) rnd); +- cmp = mpfr_cmp (y, x); +- if (((inexact == 0) && (cmp != 0)) || +- ((inexact > 0) && (cmp <= 0)) || +- ((inexact < 0) && (cmp >= 0))) ++ for (k = 0; k < 3; k++) + { +- printf ("Wrong ternary value in mpfr_set(2): expected %d," +- " got %d\n", cmp, inexact); +- exit (1); ++ int a = 0, b = 0, c = 0; ++ ++ switch (k) ++ { ++ case 0: ++ inexact = mpfr_set (y, x, (mpfr_rnd_t) rnd); ++ break; ++ case 1: ++ inexact = (mpfr_set) (y, x, (mpfr_rnd_t) rnd); ++ break; ++ case 2: ++#ifdef IGNORE_CPP_COMPAT ++#pragma GCC diagnostic push ++#pragma GCC diagnostic ignored "-Wc++-compat" ++#endif ++ inexact = mpfr_set ((a++, VOIDP_CAST(y)), ++ (b++, VOIDP_CAST(x)), ++ (c++, (mpfr_rnd_t) rnd)); ++#ifdef IGNORE_CPP_COMPAT ++#pragma GCC diagnostic pop ++#endif ++ MPFR_ASSERTN (a == 1); ++ MPFR_ASSERTN (b == 1); ++ MPFR_ASSERTN (c == 1); ++ break; ++ } ++ cmp = mpfr_cmp (y, x); ++ if (((inexact == 0) && (cmp != 0)) || ++ ((inexact > 0) && (cmp <= 0)) || ++ ((inexact < 0) && (cmp >= 0))) ++ { ++ printf ("Wrong ternary value in mpfr_set for %s (%d):" ++ " expected %d, got %d\n", ++ mpfr_print_rnd_mode ((mpfr_rnd_t) rnd), ++ k, cmp, inexact); ++ exit (1); ++ } + } + } + } +diff -Naurd mpfr-4.1.0-a/tests/tset_exp.c mpfr-4.1.0-b/tests/tset_exp.c +--- mpfr-4.1.0-a/tests/tset_exp.c 2020-01-08 18:11:13.000000000 +0000 ++++ mpfr-4.1.0-b/tests/tset_exp.c 2021-03-09 13:55:43.211158639 +0000 +@@ -28,6 +28,7 @@ + mpfr_t x; + int ret; + mpfr_exp_t emin, emax, e; ++ int i = 0; + + tests_start_mpfr (); + +@@ -63,6 +64,17 @@ + e = (mpfr_get_exp) (x); + MPFR_ASSERTN (e == emin); + ++#ifdef IGNORE_CPP_COMPAT ++#pragma GCC diagnostic push ++#pragma GCC diagnostic ignored "-Wc++-compat" ++#endif ++ e = mpfr_get_exp ((i++, VOIDP_CAST(x))); ++#ifdef IGNORE_CPP_COMPAT ++#pragma GCC diagnostic pop ++#endif ++ MPFR_ASSERTN (e == emin); ++ MPFR_ASSERTN (i == 1); ++ + ret = mpfr_set_exp (x, -1); + MPFR_ASSERTN (ret == 0 && mpfr_cmp_ui_2exp (x, 1, -2) == 0); + +diff -Naurd mpfr-4.1.0-a/PATCHES mpfr-4.1.0-b/PATCHES +--- mpfr-4.1.0-a/PATCHES 2021-03-09 13:58:00.889650773 +0000 ++++ mpfr-4.1.0-b/PATCHES 2021-03-09 13:58:00.937650249 +0000 +@@ -0,0 +1 @@ ++tset_sij +diff -Naurd mpfr-4.1.0-a/VERSION mpfr-4.1.0-b/VERSION +--- mpfr-4.1.0-a/VERSION 2021-03-09 13:55:43.223158508 +0000 ++++ mpfr-4.1.0-b/VERSION 2021-03-09 13:58:00.937650249 +0000 +@@ -1 +1 @@ +-4.1.0-p10 ++4.1.0-p11 +diff -Naurd mpfr-4.1.0-a/src/mpfr.h mpfr-4.1.0-b/src/mpfr.h +--- mpfr-4.1.0-a/src/mpfr.h 2021-03-09 13:55:43.223158508 +0000 ++++ mpfr-4.1.0-b/src/mpfr.h 2021-03-09 13:58:00.933650293 +0000 +@@ -27,7 +27,7 @@ + #define MPFR_VERSION_MAJOR 4 + #define MPFR_VERSION_MINOR 1 + #define MPFR_VERSION_PATCHLEVEL 0 +-#define MPFR_VERSION_STRING "4.1.0-p10" ++#define MPFR_VERSION_STRING "4.1.0-p11" + + /* User macros: + MPFR_USE_FILE: Define it to make MPFR define functions dealing +diff -Naurd mpfr-4.1.0-a/src/version.c mpfr-4.1.0-b/src/version.c +--- mpfr-4.1.0-a/src/version.c 2021-03-09 13:55:43.223158508 +0000 ++++ mpfr-4.1.0-b/src/version.c 2021-03-09 13:58:00.933650293 +0000 +@@ -25,5 +25,5 @@ + const char * + mpfr_get_version (void) + { +- return "4.1.0-p10"; ++ return "4.1.0-p11"; + } +diff -Naurd mpfr-4.1.0-a/tests/tset_si.c mpfr-4.1.0-b/tests/tset_si.c +--- mpfr-4.1.0-a/tests/tset_si.c 2020-03-26 11:51:33.000000000 +0000 ++++ mpfr-4.1.0-b/tests/tset_si.c 2021-03-09 13:58:00.917650467 +0000 +@@ -127,27 +127,29 @@ + power of 2 is exact, unless underflow/overflow occurs. + The tests on the exponent below avoid integer overflows + (ep[i] may take extreme values). */ +- e = mpfr_get_exp (x1); + mpfr_clear_flags (); +- if (j != 0 && ep[i] < __gmpfr_emin - e) /* underflow */ ++ if (j == 0) ++ goto zero; ++ e = MPFR_GET_EXP (x1); ++ if (ep[i] < __gmpfr_emin - e) /* underflow */ + { + mpfr_rnd_t r = + (rnd == MPFR_RNDN && +- (ep[i] < __gmpfr_emin - mpfr_get_exp (y) - 1 || ++ (ep[i] < __gmpfr_emin - MPFR_GET_EXP (y) - 1 || + IS_POW2 (sign * j))) ? + MPFR_RNDZ : (mpfr_rnd_t) rnd; + inex1 = mpfr_underflow (x1, r, sign); + flags1 = __gmpfr_flags; + } +- else if (j != 0 && ep[i] > __gmpfr_emax - e) /* overflow */ ++ else if (ep[i] > __gmpfr_emax - e) /* overflow */ + { + inex1 = mpfr_overflow (x1, (mpfr_rnd_t) rnd, sign); + flags1 = __gmpfr_flags; + } + else + { +- if (j != 0) +- mpfr_set_exp (x1, ep[i] + e); ++ mpfr_set_exp (x1, ep[i] + e); ++ zero: + flags1 = inex1 != 0 ? MPFR_FLAGS_INEXACT : 0; + } + +diff -Naurd mpfr-4.1.0-a/tests/tset_sj.c mpfr-4.1.0-b/tests/tset_sj.c +--- mpfr-4.1.0-a/tests/tset_sj.c 2020-06-01 10:39:52.000000000 +0000 ++++ mpfr-4.1.0-b/tests/tset_sj.c 2021-03-09 13:58:00.917650467 +0000 +@@ -225,27 +225,29 @@ + power of 2 is exact, unless underflow/overflow occurs. + The tests on the exponent below avoid integer overflows + (ep[i] may take extreme values). */ +- e = mpfr_get_exp (x1); + mpfr_clear_flags (); +- if (j != 0 && ep[i] < __gmpfr_emin - e) /* underflow */ ++ if (j == 0) ++ goto zero; ++ e = MPFR_GET_EXP (x1); ++ if (ep[i] < __gmpfr_emin - e) /* underflow */ + { + mpfr_rnd_t r = + (rnd == MPFR_RNDN && +- (ep[i] < __gmpfr_emin - mpfr_get_exp (y) - 1 || ++ (ep[i] < __gmpfr_emin - MPFR_GET_EXP (y) - 1 || + IS_POW2 (sign * j))) ? + MPFR_RNDZ : (mpfr_rnd_t) rnd; + inex1 = mpfr_underflow (x1, r, sign); + flags1 = __gmpfr_flags; + } +- else if (j != 0 && ep[i] > __gmpfr_emax - e) /* overflow */ ++ else if (ep[i] > __gmpfr_emax - e) /* overflow */ + { + inex1 = mpfr_overflow (x1, (mpfr_rnd_t) rnd, sign); + flags1 = __gmpfr_flags; + } + else + { +- if (j != 0) +- mpfr_set_exp (x1, ep[i] + e); ++ mpfr_set_exp (x1, ep[i] + e); ++ zero: + flags1 = inex1 != 0 ? MPFR_FLAGS_INEXACT : 0; + } + } diff --git a/mpfr.spec b/mpfr.spec index 272dfc9..005bf29 100644 --- a/mpfr.spec +++ b/mpfr.spec @@ -1,11 +1,14 @@ Summary: C library for multiple-precision floating-point computations Name: mpfr Version: 4.1.0 -Release: 5%{?dist} +Release: 6%{?dist} URL: https://www.mpfr.org/ License: LGPLv3+ -BuildRequires: gmp-devel gcc make +BuildRequires: gcc +BuildRequires: gmp-devel +BuildRequires: make +BuildRequires: texinfo Source0: https://www.mpfr.org/%{name}-%{version}/%{name}-%{version}.tar.xz @@ -19,6 +22,8 @@ Source0: https://www.mpfr.org/%{name}-%{version}/%{name}-%{version}.tar.xz # - jn-interm-zero.patch # - digamma-interm-zero2.patch # - jyn-asympt-interm-zero.patch +# - macros.patch +# - tset_sij.patch Patch0: https://www.mpfr.org/%{name}-%{version}/allpatches # This can be removed when F32 reaches EOL @@ -107,6 +112,9 @@ export LD_LIBRARY_PATH=%{buildroot}%{_libdir} %{_infodir}/mpfr.info* %changelog +* Tue Apr 13 2021 Jerry James - 4.1.0-6 +- Add upstream patches 10-11 + * Tue Mar 9 2021 Jerry James - 4.1.0-5 - Add upstream patches 8-9