static void regular (void) { mpfr_t x, y, r; mpfr_inits (x, y, r, (mpfr_ptr) 0); /* remainder = 0 */ mpfr_set_str (y, "FEDCBA987654321p-64", 16, MPFR_RNDN); mpfr_pow_ui (x, y, 42, MPFR_RNDN); check (r, x, y, MPFR_RNDN); /* x < y */ mpfr_set_ui_2exp (x, 64723, -19, MPFR_RNDN); mpfr_mul (x, x, y, MPFR_RNDN); check (r, x, y, MPFR_RNDN); /* sign(x) = sign (r) */ mpfr_set_ui (x, 123798, MPFR_RNDN); mpfr_set_ui (y, 10, MPFR_RNDN); check (r, x, y, MPFR_RNDN); /* huge difference between precisions */ mpfr_set_prec (x, 314); mpfr_set_prec (y, 8); mpfr_set_prec (r, 123); mpfr_const_pi (x, MPFR_RNDD); /* x = pi */ mpfr_set_ui_2exp (y, 1, 3, MPFR_RNDD); /* y = 1/8 */ check (r, x, y, MPFR_RNDD); mpfr_clears (x, y, r, (mpfr_ptr) 0); }
/* Test case bk == 0 in add1.c (b has entirely been read and c hasn't been taken into account). */ static void coverage_bk_eq_0 (void) { mpfr_t a, b, c; int inex; mpfr_init2 (a, GMP_NUMB_BITS); mpfr_init2 (b, 2 * GMP_NUMB_BITS); mpfr_init2 (c, GMP_NUMB_BITS); mpfr_set_ui_2exp (b, 1, 2 * GMP_NUMB_BITS, MPFR_RNDN); mpfr_sub_ui (b, b, 1, MPFR_RNDN); /* b = 111...111 (in base 2) where the 1's fit 2 whole limbs */ mpfr_set_ui_2exp (c, 1, -1, MPFR_RNDN); /* c = 1/2 */ inex = mpfr_add (a, b, c, MPFR_RNDU); mpfr_set_ui_2exp (c, 1, 2 * GMP_NUMB_BITS, MPFR_RNDN); if (! mpfr_equal_p (a, c)) { printf ("Error in coverage_bk_eq_0\n"); printf ("Expected "); mpfr_dump (c); printf ("Got "); mpfr_dump (a); exit (1); } MPFR_ASSERTN (inex > 0); mpfr_clear (a); mpfr_clear (b); mpfr_clear (c); }
/* bug found in nightly tests */ static void test20071214 (void) { mpfr_t a, b; int inex; mpfr_init2 (a, 4); mpfr_init2 (b, 4); mpfr_set_ui_2exp (a, 3, -4, MPFR_RNDN); inex = mpfr_sin_cos (a, b, a, MPFR_RNDD); MPFR_ASSERTN(mpfr_cmp_ui_2exp (a, 11, -6) == 0); MPFR_ASSERTN(mpfr_cmp_ui_2exp (b, 15, -4) == 0); MPFR_ASSERTN(inex == 10); mpfr_set_ui_2exp (a, 3, -4, MPFR_RNDN); inex = mpfr_sin_cos (a, b, a, MPFR_RNDU); MPFR_ASSERTN(mpfr_cmp_ui_2exp (a, 3, -4) == 0); MPFR_ASSERTN(mpfr_cmp_ui (b, 1) == 0); MPFR_ASSERTN(inex == 5); mpfr_set_ui_2exp (a, 3, -4, MPFR_RNDN); inex = mpfr_sin_cos (a, b, a, MPFR_RNDN); MPFR_ASSERTN(mpfr_cmp_ui_2exp (a, 3, -4) == 0); MPFR_ASSERTN(mpfr_cmp_ui (b, 1) == 0); MPFR_ASSERTN(inex == 5); mpfr_clear (a); mpfr_clear (b); }
/* Bug found by Jakub Jelinek * http://bugzilla.redhat.com/643657 * https://gforge.inria.fr/tracker/index.php?func=detail&aid=11301 * The consequence can be either an assertion failure (i = 2 in the * testcase below, in debug mode) or an incorrectly rounded value. */ static void bug20101017 (void) { mpfr_t a, b, c; int inex; int i; mpfr_init2 (a, GMP_NUMB_BITS * 2); mpfr_init2 (b, GMP_NUMB_BITS); mpfr_init2 (c, GMP_NUMB_BITS); /* a = 2^(2N) + k.2^(2N-1) + 2^N and b = 1 with N = GMP_NUMB_BITS and k = 0 or 1. c = a - b should round to the same value as a. */ for (i = 2; i <= 3; i++) { mpfr_set_ui_2exp (a, i, GMP_NUMB_BITS - 1, MPFR_RNDN); mpfr_add_ui (a, a, 1, MPFR_RNDN); mpfr_mul_2ui (a, a, GMP_NUMB_BITS, MPFR_RNDN); mpfr_set_ui (b, 1, MPFR_RNDN); inex = mpfr_sub (c, a, b, MPFR_RNDN); mpfr_set (b, a, MPFR_RNDN); if (! mpfr_equal_p (c, b)) { printf ("Error in bug20101017 for i = %d.\n", i); printf ("Expected "); mpfr_out_str (stdout, 16, 0, b, MPFR_RNDN); putchar ('\n'); printf ("Got "); mpfr_out_str (stdout, 16, 0, c, MPFR_RNDN); putchar ('\n'); exit (1); } if (inex >= 0) { printf ("Error in bug20101017 for i = %d: bad inex value.\n", i); printf ("Expected negative, got %d.\n", inex); exit (1); } } mpfr_set_prec (a, 64); mpfr_set_prec (b, 129); mpfr_set_prec (c, 2); mpfr_set_str_binary (b, "0.100000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000001E65"); mpfr_set_str_binary (c, "0.10E1"); inex = mpfr_sub (a, b, c, MPFR_RNDN); if (mpfr_cmp_ui_2exp (a, 1, 64) != 0 || inex >= 0) { printf ("Error in mpfr_sub for b-c for b=2^64+1+2^(-64), c=1\n"); printf ("Expected result 2^64 with inex < 0\n"); printf ("Got "); mpfr_print_binary (a); printf (" with inex=%d\n", inex); exit (1); } mpfr_clears (a, b, c, (mpfr_ptr) 0); }
/* tests intermediate underflow; WONTFIX */ static int test_underflow (void) { mpc_t z; mpfr_exp_t emin = mpfr_get_emin (); mpfr_set_emin (-10); mpc_init2 (z, 21); mpfr_set_si (mpc_realref(z), -1, GMP_RNDZ); mpfr_set_ui_2exp (mpc_imagref(z), 1, 20, GMP_RNDZ); mpfr_add_ui (mpc_imagref(z), mpc_imagref(z), 1, GMP_RNDZ); mpfr_div_2exp (mpc_imagref(z), mpc_imagref(z), 20, GMP_RNDZ); mpc_atan (z, z, MPC_RNDNN); if (mpfr_cmp_si_2exp (mpc_realref(z), -1066635, 20) != 0 || mpfr_cmp_si_2exp (mpc_imagref(z), 1687619, 22)) { printf ("Error in test_coverage\n"); printf ("expected (-1066635/2^20 1687619/2^22)\n"); printf ("got "); mpc_out_str (stdout, 10, 20, z, MPC_RNDNN); printf ("\n"); exit (1); } mpc_clear (z); mpfr_set_emin (emin); }
/* From a bug reported by Joseph S. Myers https://sympa.inria.fr/sympa/arc/mpfr/2012-08/msg00005.html */ static void bug20120814 (void) { mpfr_exp_t emin = -30, e; mpfr_t x, y; int r; char s[64], *p; mpfr_init2 (x, 2); mpfr_set_ui_2exp (x, 3, emin - 2, MPFR_RNDN); mpfr_get_str (s + 1, &e, 10, 19, x, MPFR_RNDD); s[0] = s[1]; s[1] = '.'; for (p = s; *p != 0; p++) ; *p = 'e'; sprintf (p + 1, "%d", (int) e - 1); mpfr_init2 (y, 4); r = mpfr_strtofr (y, s, NULL, 0, MPFR_RNDN); if (r <= 0 || ! mpfr_equal_p (x, y)) { printf ("Error in bug20120814\n"); printf ("mpfr_strtofr failed on string \"%s\"\n", s); printf ("Expected inex > 0 and y = 0.1100E%d\n", (int) emin); printf ("Got inex = %-6d and y = ", r); mpfr_dump (y); exit (1); } mpfr_clear (x); mpfr_clear (y); }
static void reuse_bug (void) { /* bug found by the automatic builds on http://hydra.nixos.org/build/1469029/log/raw */ mpc_t x, y, z; mp_prec_t prec = 2; for (prec = 2; prec <= 20; prec ++) { mpc_init2 (x, prec); mpc_init2 (y, prec); mpc_init2 (z, prec); mpfr_set_ui (mpc_realref (x), 0ul, MPFR_RNDN); mpfr_set_ui_2exp (mpc_imagref (x), 3ul, -2, MPFR_RNDN); mpc_set_ui (y, 8ul, MPC_RNDNN); mpc_pow (z, x, y, MPC_RNDNN); mpc_pow (y, x, y, MPC_RNDNN); if (mpfr_signbit (mpc_imagref (y)) != mpfr_signbit (mpc_imagref (z))) { printf ("Error: regression, reuse_bug reproduced\n"); exit (1); } mpc_clear (x); mpc_clear (y); mpc_clear (z); } }
static void atan2_pow_of_2 (void) { mpfr_t x, y, r, g; int i; int d[] = { 0, -1, 1 }; int ntests = sizeof (d) / sizeof (int); mpfr_init2 (x, 53); mpfr_init2 (y, 53); mpfr_init2 (r, 53); mpfr_init2 (g, 53); /* atan(42) */ mpfr_set_str_binary (g, "1100011000000011110011111001100110101000011010010011E-51"); for (i = 0; i < ntests; ++i) { mpfr_set_ui (y, 42, MPFR_RNDN); mpfr_mul_2si (y, y, d[i], MPFR_RNDN); mpfr_set_ui_2exp (x, 1, d[i], MPFR_RNDN); mpfr_atan2 (r, y, x, MPFR_RNDN); if (mpfr_equal_p (r, g) == 0) { printf ("Error in mpfr_atan2 (5)\n"); printf ("Expected "); mpfr_print_binary (g); printf ("\n"); printf ("Got "); mpfr_print_binary (r); printf ("\n"); exit (1); } } mpfr_clear (x); mpfr_clear (y); mpfr_clear (r); mpfr_clear (g); }
/* bug reported by Eric Veach */ static void bug20090519 (void) { mpfr_t x, y, r; int inexact; mpfr_inits2 (100, x, y, r, (mpfr_ptr) 0); mpfr_set_prec (x, 3); mpfr_set_prec (y, 3); mpfr_set_prec (r, 3); mpfr_set_si (x, 8, MPFR_RNDN); mpfr_set_si (y, 7, MPFR_RNDN); check (r, x, y, MPFR_RNDN); mpfr_set_prec (x, 10); mpfr_set_prec (y, 10); mpfr_set_prec (r, 10); mpfr_set_ui_2exp (x, 3, 26, MPFR_RNDN); mpfr_set_si (y, (1 << 9) - 1, MPFR_RNDN); check (r, x, y, MPFR_RNDN); mpfr_set_prec (x, 100); mpfr_set_prec (y, 100); mpfr_set_prec (r, 100); mpfr_set_str (x, "3.5", 10, MPFR_RNDN); mpfr_set_str (y, "1.1", 10, MPFR_RNDN); check (r, x, y, MPFR_RNDN); /* double check, with a pre-computed value */ { mpfr_t er; mpfr_init2 (er, 100); mpfr_set_str (er, "CCCCCCCCCCCCCCCCCCCCCCCC8p-102", 16, MPFR_RNDN); inexact = mpfr_fmod (r, x, y, MPFR_RNDN); if (!mpfr_equal_p (r, er) || inexact != 0) test_failed (er, r, 0, inexact, x, y, MPFR_RNDN); mpfr_clear (er); } mpfr_set_si (x, 20, MPFR_RNDN); mpfr_set_ui_2exp (y, 1, 1, MPFR_RNDN); /* exact */ mpfr_sin (y, y, MPFR_RNDN); check (r, x, y, MPFR_RNDN); mpfr_clears(r, x, y, (mpfr_ptr) 0); }
int main (int argc, char *argv[]) { int dmax, n, p; mpfr_t VARS; if (argc != 3 && argc != 4) { fprintf (stderr, "Usage: divworst <dmax> <n> [ <p> ]\n"); exit (EXIT_FAILURE); } dmax = atoi (argv[1]); n = atoi (argv[2]); p = argc == 3 ? n : atoi (argv[3]); if (p < n) { fprintf (stderr, "divworst: p must be greater or equal to n\n"); exit (EXIT_FAILURE); } mpfr_inits2 (n, PRECN, (mpfr_ptr) 0); mpfr_init2 (t, p); for (mpfr_set_ui_2exp (x, 1, -1, MPFR_RNDN); mpfr_get_exp (x) <= dmax; mpfr_nextabove (x)) for (mpfr_set_ui_2exp (y, 1, -1, MPFR_RNDN); mpfr_get_exp (y) == 0; mpfr_nextabove (y)) { unsigned long rz, rn; if (mpfr_sub (z, x, y, MPFR_RNDZ) != 0) continue; /* x - y is not representable in precision n */ rz = eval (x, y, z, t, MPFR_RNDZ); rn = eval (x, y, z, t, MPFR_RNDN); if (rz == rn) continue; mpfr_printf ("x = %.*Rb ; y = %.*Rb ; Z: %lu ; N: %lu\n", n - 1, x, n - 1, y, rz, rn); } mpfr_clears (VARS, (mpfr_ptr) 0); return 0; }
/* bug found by Kevin P. Rauch on 22 Oct 2007 */ static void check3 (void) { mpfr_t x, y, z; int tern; mpfr_exp_t emin; emin = mpfr_get_emin (); mpfr_init2 (x, 32); mpfr_init2 (y, 32); mpfr_init2 (z, 32); mpfr_set_ui (x, 0xBFFFFFFFU, MPFR_RNDN); /* 3221225471/2^32 */ mpfr_set_ui (y, 0x80000001U, MPFR_RNDN); /* 2147483649/2^32 */ mpfr_set_exp (x, 0); mpfr_set_exp (y, 0); mpfr_set_emin (-1); /* the exact product is 6917529028714823679/2^64, which is rounded to 3/8 = 0.375, which is smaller, thus tern < 0 */ tern = mpfr_mul (z, x, y, MPFR_RNDN); MPFR_ASSERTN (tern < 0 && mpfr_cmp_ui_2exp (z, 3, -3) == 0); tern = mpfr_subnormalize (z, tern, MPFR_RNDN); /* since emin = -1, and EXP(z)=-1, z should be rounded to precision EXP(z)-emin+1 = 1, i.e., z should be a multiple of the smallest possible positive representable value with emin=-1, which is 1/4. The two possible values are 1/4 and 2/4, which are at equal distance of z. But since tern < 0, we should choose the largest value, i.e., 2/4. */ MPFR_ASSERTN (tern > 0 && mpfr_cmp_ui_2exp (z, 1, -1) == 0); /* here is another test for the alternate case, where z was rounded up first, thus we have to round down */ mpfr_set_str_binary (x, "0.11111111111010110101011011011011"); mpfr_set_str_binary (y, "0.01100000000001111100000000001110"); tern = mpfr_mul (z, x, y, MPFR_RNDN); MPFR_ASSERTN (tern > 0 && mpfr_cmp_ui_2exp (z, 3, -3) == 0); tern = mpfr_subnormalize (z, tern, MPFR_RNDN); MPFR_ASSERTN (tern < 0 && mpfr_cmp_ui_2exp (z, 1, -2) == 0); /* finally the case where z was exact, which we simulate here */ mpfr_set_ui_2exp (z, 3, -3, MPFR_RNDN); tern = mpfr_subnormalize (z, 0, MPFR_RNDN); MPFR_ASSERTN (tern > 0 && mpfr_cmp_ui_2exp (z, 1, -1) == 0); mpfr_clear (x); mpfr_clear (y); mpfr_clear (z); MPFR_ASSERTN (mpfr_get_emin () == -1); set_emin (emin); }
static int mpfr_pow275 (mpfr_t y, mpfr_t x, mp_rnd_t r) { mpfr_t z; int inex; mpfr_init2 (z, 4); mpfr_set_ui_2exp (z, 11, -2, GMP_RNDN); inex = mpfr_pow (y, x, z, GMP_RNDN); mpfr_clear (z); return inex; }
/* return add = 1 + floor(log(c^3*(13+m1))/log(2)) where c = (1+eps)*(1+eps*max(8,m1)), m1 = 1 + max(1/eps,2*sd)*(1+eps), eps = 2^(-precz-14) sd = abs(s-1) */ static long compute_add (mpfr_srcptr s, mpfr_prec_t precz) { mpfr_t t, u, m1; long add; mpfr_inits2 (64, t, u, m1, (mpfr_ptr) 0); if (mpfr_cmp_ui (s, 1) >= 0) mpfr_sub_ui (t, s, 1, MPFR_RNDU); else mpfr_ui_sub (t, 1, s, MPFR_RNDU); /* now t = sd = abs(s-1), rounded up */ mpfr_set_ui_2exp (u, 1, - precz - 14, MPFR_RNDU); /* u = eps */ /* since 1/eps = 2^(precz+14), if EXP(sd) >= precz+14, then sd >= 1/2*2^(precz+14) thus 2*sd >= 2^(precz+14) >= 1/eps */ if (mpfr_get_exp (t) >= precz + 14) mpfr_mul_2exp (t, t, 1, MPFR_RNDU); else mpfr_set_ui_2exp (t, 1, precz + 14, MPFR_RNDU); /* now t = max(1/eps,2*sd) */ mpfr_add_ui (u, u, 1, MPFR_RNDU); /* u = 1+eps, rounded up */ mpfr_mul (t, t, u, MPFR_RNDU); /* t = max(1/eps,2*sd)*(1+eps) */ mpfr_add_ui (m1, t, 1, MPFR_RNDU); if (mpfr_get_exp (m1) <= 3) mpfr_set_ui (t, 8, MPFR_RNDU); else mpfr_set (t, m1, MPFR_RNDU); /* now t = max(8,m1) */ mpfr_div_2exp (t, t, precz + 14, MPFR_RNDU); /* eps*max(8,m1) */ mpfr_add_ui (t, t, 1, MPFR_RNDU); /* 1+eps*max(8,m1) */ mpfr_mul (t, t, u, MPFR_RNDU); /* t = c */ mpfr_add_ui (u, m1, 13, MPFR_RNDU); /* 13+m1 */ mpfr_mul (u, u, t, MPFR_RNDU); /* c*(13+m1) */ mpfr_sqr (t, t, MPFR_RNDU); /* c^2 */ mpfr_mul (u, u, t, MPFR_RNDU); /* c^3*(13+m1) */ add = mpfr_get_exp (u); mpfr_clears (t, u, m1, (mpfr_ptr) 0); return add; }
/* Since r10377, the following test causes a "too much memory" error when MPFR is built with Debian's tcc 0.9.27~git20151227.933c223-1 on x86_64. The problem came from __gmpfr_ceil_log2, now fixed in r10443 (according to the integer promotion rules, this appeared to be a bug in tcc, not in MPFR; however relying on such an obscure rule was not a good idea). */ static void tcc_bug20160606 (void) { mpfr_t x, y; int sign; mpfr_init2 (x, 53); mpfr_init2 (y, 53); mpfr_set_ui_2exp (x, 1, -1, MPFR_RNDN); mpfr_lgamma (y, &sign, x, MPFR_RNDN); mpfr_clear (x); mpfr_clear (y); }
static void bug_20090316 (FILE *fout) { mpfr_t x; mpfr_init2 (x, 53); /* bug 20090316: fixed in r6112 */ mpfr_set_ui_2exp (x, 0x60fa2916, -30, GMP_RNDN); check (fout, "%-#.4095RDg\n", x); mpfr_clear (x); }
/* With pow.c r5497, the following test fails on a 64-bit Linux machine * due to a double-rounding problem when rescaling the result: * Error with underflow_up2 and extended exponent range * x = 7.fffffffffffffff0@-1, * y = 4611686018427387904, MPFR_RNDN * Expected 1.0000000000000000@-1152921504606846976, inex = 1, flags = 9 * Got 0, inex = -1, flags = 9 * With pow_ui.c r5423, the following test fails on a 64-bit Linux machine * as underflows and overflows are not handled correctly (the approximation * error is ignored): * Error with mpfr_pow_ui, flags cleared * x = 7.fffffffffffffff0@-1, * y = 4611686018427387904, MPFR_RNDN * Expected 1.0000000000000000@-1152921504606846976, inex = 1, flags = 9 * Got 0, inex = -1, flags = 9 */ static void underflow_up2 (void) { mpfr_t x, y, z, z0, eps; mpfr_exp_t n; int inex; int rnd; n = 1 - mpfr_get_emin (); MPFR_ASSERTN (n > 1); if (n > ULONG_MAX) return; mpfr_init2 (eps, 2); mpfr_set_ui_2exp (eps, 1, -1, MPFR_RNDN); /* 1/2 */ mpfr_div_ui (eps, eps, n, MPFR_RNDZ); /* 1/(2n) rounded toward zero */ mpfr_init2 (x, sizeof (unsigned long) * CHAR_BIT + 1); inex = mpfr_ui_sub (x, 1, eps, MPFR_RNDN); MPFR_ASSERTN (inex == 0); /* since n < 2^(size_of_long_in_bits) */ inex = mpfr_div_2ui (x, x, 1, MPFR_RNDN); /* 1/2 - eps/2 exactly */ MPFR_ASSERTN (inex == 0); mpfr_init2 (y, sizeof (unsigned long) * CHAR_BIT); inex = mpfr_set_ui (y, n, MPFR_RNDN); MPFR_ASSERTN (inex == 0); /* 0 < eps < 1 / (2n), thus (1 - eps)^n > 1/2, and 1/2 (1/2)^n < (1/2 - eps/2)^n < (1/2)^n. */ mpfr_inits2 (64, z, z0, (mpfr_ptr) 0); RND_LOOP (rnd) { unsigned int ufinex = MPFR_FLAGS_UNDERFLOW | MPFR_FLAGS_INEXACT; int expected_inex; char sy[256]; mpfr_set_ui (z0, 0, MPFR_RNDN); expected_inex = rnd == MPFR_RNDN || rnd == MPFR_RNDU || rnd == MPFR_RNDA ? (mpfr_nextabove (z0), 1) : -1; sprintf (sy, "%lu", (unsigned long) n); mpfr_clear_flags (); inex = mpfr_pow (z, x, y, (mpfr_rnd_t) rnd); cmpres (0, x, sy, (mpfr_rnd_t) rnd, z0, expected_inex, z, inex, ufinex, "underflow_up2", "mpfr_pow"); test_others (NULL, sy, (mpfr_rnd_t) rnd, x, y, z, inex, ufinex, "underflow_up2"); } mpfr_clears (x, y, z, z0, eps, (mpfr_ptr) 0); }
bool almostEqual(const M2::ARingRRR& R, int nbits, const M2::ARingRRR::ElementType& a, const M2::ARingRRR::ElementType& b) { mpfr_t epsilon; mpfr_init2(epsilon, R.get_precision()); mpfr_set_ui_2exp(epsilon, 1, -nbits, GMP_RNDN); M2::ARingRRR::ElementType c; R.init(c); R.subtract(c,a,b); bool ret = mpfr_cmpabs(&c,epsilon) < 0; R.clear(c); mpfr_clear(epsilon); return ret; }
/* With MPFR 2.3.0, this yields an assertion failure in mpfr_acosh. */ static void bug20070831 (void) { mpfr_t x, y, z; int inex; mpfr_init2 (x, 256); mpfr_init2 (y, 32); mpfr_init2 (z, 32); mpfr_set_ui (x, 1, GMP_RNDN); mpfr_nextabove (x); inex = mpfr_acosh (y, x, GMP_RNDZ); mpfr_set_ui_2exp (z, 1, -127, GMP_RNDN); mpfr_nextbelow (z); if (!mpfr_equal_p (y, z)) { printf ("Error in bug20070831 (1):\nexpected "); mpfr_dump (z); printf ("got "); mpfr_dump (y); exit (1); } MPFR_ASSERTN (inex < 0); mpfr_nextabove (x); mpfr_set_prec (y, 29); inex = mpfr_acosh (y, x, GMP_RNDN); mpfr_set_str_binary (z, "1.011010100000100111100110011E-127"); if (!mpfr_equal_p (y, z)) { printf ("Error in bug20070831 (2):\nexpected "); mpfr_dump (z); printf ("got "); mpfr_dump (y); exit (1); } MPFR_ASSERTN (inex < 0); mpfr_clears (x, y, z, (mpfr_ptr) 0); }
static void huge (void) { mpfr_t x, y, z; int inex; /* TODO: extend the exponent range and use mpfr_get_emax (). */ mpfr_inits2 (32, x, y, z, (mpfr_ptr) 0); mpfr_set_ui_2exp (x, 1, 1073741822, GMP_RNDN); inex = mpfr_acosh (y, x, GMP_RNDN); mpfr_set_str_binary (z, "0.10110001011100100001011111110101E30"); if (!mpfr_equal_p (y, z)) { printf ("Error in huge:\nexpected "); mpfr_dump (z); printf ("got "); mpfr_dump (y); exit (1); } MPFR_ASSERTN (inex < 0); mpfr_clears (x, y, z, (mpfr_ptr) 0); }
static void x_near_one (void) { mpfr_t x, y, z; int inex; mpfr_init2 (x, 32); mpfr_init2 (y, 4); mpfr_init2 (z, 33); mpfr_set_ui (x, 1, GMP_RNDN); mpfr_nextbelow (x); mpfr_set_ui_2exp (y, 11, -2, GMP_RNDN); inex = mpfr_pow (z, x, y, GMP_RNDN); if (mpfr_cmp_str (z, "0.111111111111111111111111111111011E0", 2, GMP_RNDN) || inex <= 0) { printf ("Failure in x_near_one, got inex = %d and\nz = ", inex); mpfr_dump (z); } mpfr_clears (x, y, z, (void *) 0); }
int mpfr_set_ui (mpfr_ptr x, unsigned long i, mpfr_rnd_t rnd_mode) { return mpfr_set_ui_2exp (x, i, 0, rnd_mode); }
static void overflowed_sec0 (void) { mpfr_t x, y; int emax, i, inex, rnd, err = 0; mpfr_exp_t old_emax; old_emax = mpfr_get_emax (); mpfr_init2 (x, 8); mpfr_init2 (y, 8); for (emax = -1; emax <= 0; emax++) { mpfr_set_ui_2exp (y, 1, emax, MPFR_RNDN); mpfr_nextbelow (y); set_emax (emax); /* 1 is not representable. */ for (i = -1; i <= 1; i++) RND_LOOP (rnd) { mpfr_set_si_2exp (x, i, -512 * ABS (i), MPFR_RNDN); mpfr_clear_flags (); inex = mpfr_sec (x, x, (mpfr_rnd_t) rnd); if (! mpfr_overflow_p ()) { printf ("Error in overflowed_sec0 (i = %d, rnd = %s):\n" " The overflow flag is not set.\n", i, mpfr_print_rnd_mode ((mpfr_rnd_t) rnd)); err = 1; } if (rnd == MPFR_RNDZ || rnd == MPFR_RNDD) { if (inex >= 0) { printf ("Error in overflowed_sec0 (i = %d, rnd = %s):\n" " The inexact value must be negative.\n", i, mpfr_print_rnd_mode ((mpfr_rnd_t) rnd)); err = 1; } if (! mpfr_equal_p (x, y)) { printf ("Error in overflowed_sec0 (i = %d, rnd = %s):\n" " Got ", i, mpfr_print_rnd_mode ((mpfr_rnd_t) rnd)); mpfr_print_binary (x); printf (" instead of 0.11111111E%d.\n", emax); err = 1; } } else { if (inex <= 0) { printf ("Error in overflowed_sec0 (i = %d, rnd = %s):\n" " The inexact value must be positive.\n", i, mpfr_print_rnd_mode ((mpfr_rnd_t) rnd)); err = 1; } if (! (mpfr_inf_p (x) && MPFR_SIGN (x) > 0)) { printf ("Error in overflowed_sec0 (i = %d, rnd = %s):\n" " Got ", i, mpfr_print_rnd_mode ((mpfr_rnd_t) rnd)); mpfr_print_binary (x); printf (" instead of +Inf.\n"); err = 1; } } } set_emax (old_emax); } if (err) exit (1); mpfr_clear (x); mpfr_clear (y); }
int main (int argc, char *argv[]) { mpfr_t x, y, r; long q[1]; if (argc == 3) /* usage: tremquo x y (rnd=MPFR_RNDN implicit) */ { mpfr_init2 (x, GMP_NUMB_BITS); mpfr_init2 (y, GMP_NUMB_BITS); mpfr_init2 (r, GMP_NUMB_BITS); mpfr_set_str (x, argv[1], 10, MPFR_RNDN); mpfr_set_str (y, argv[2], 10, MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); printf ("r="); mpfr_out_str (stdout, 10, 0, r, MPFR_RNDN); printf (" q=%ld\n", q[0]); mpfr_clear (x); mpfr_clear (y); mpfr_clear (r); return 0; } tests_start_mpfr (); bug20090227 (); mpfr_init (x); mpfr_init (y); mpfr_init (r); /* special values */ mpfr_set_nan (x); mpfr_set_ui (y, 1, MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN(mpfr_nan_p (r)); mpfr_set_ui (x, 1, MPFR_RNDN); mpfr_set_nan (y); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN(mpfr_nan_p (r)); mpfr_set_inf (x, 1); /* +Inf */ mpfr_set_ui (y, 1, MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_nan_p (r)); mpfr_set_inf (x, 1); /* +Inf */ mpfr_set_ui (y, 0, MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_nan_p (r)); mpfr_set_inf (x, 1); /* +Inf */ mpfr_set_inf (y, 1); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_nan_p (r)); mpfr_set_ui (x, 0, MPFR_RNDN); mpfr_set_inf (y, 1); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp_ui (r, 0) == 0 && MPFR_IS_POS (r)); MPFR_ASSERTN (q[0] == (long) 0); mpfr_set_ui (x, 0, MPFR_RNDN); mpfr_neg (x, x, MPFR_RNDN); /* -0 */ mpfr_set_inf (y, 1); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp_ui (r, 0) == 0 && MPFR_IS_NEG (r)); MPFR_ASSERTN (q[0] == (long) 0); mpfr_set_ui (x, 17, MPFR_RNDN); mpfr_set_inf (y, 1); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp (r, x) == 0); MPFR_ASSERTN (q[0] == (long) 0); mpfr_set_ui (x, 17, MPFR_RNDN); mpfr_set_ui (y, 0, MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_nan_p (r)); mpfr_set_ui (x, 0, MPFR_RNDN); mpfr_set_ui (y, 17, MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp_ui (r, 0) == 0 && MPFR_IS_POS (r)); MPFR_ASSERTN (q[0] == (long) 0); mpfr_set_ui (x, 0, MPFR_RNDN); mpfr_neg (x, x, MPFR_RNDN); mpfr_set_ui (y, 17, MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp_ui (r, 0) == 0 && MPFR_IS_NEG (r)); MPFR_ASSERTN (q[0] == (long) 0); mpfr_set_prec (x, 53); mpfr_set_prec (y, 53); /* check four possible sign combinations */ mpfr_set_ui (x, 42, MPFR_RNDN); mpfr_set_ui (y, 17, MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp_ui (r, 8) == 0); MPFR_ASSERTN (q[0] == (long) 2); mpfr_set_si (x, -42, MPFR_RNDN); mpfr_set_ui (y, 17, MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp_si (r, -8) == 0); MPFR_ASSERTN (q[0] == (long) -2); mpfr_set_si (x, -42, MPFR_RNDN); mpfr_set_si (y, -17, MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp_si (r, -8) == 0); MPFR_ASSERTN (q[0] == (long) 2); mpfr_set_ui (x, 42, MPFR_RNDN); mpfr_set_si (y, -17, MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp_ui (r, 8) == 0); MPFR_ASSERTN (q[0] == (long) -2); mpfr_set_prec (x, 100); mpfr_set_prec (y, 50); mpfr_set_ui (x, 42, MPFR_RNDN); mpfr_nextabove (x); /* 42 + 2^(-94) */ mpfr_set_ui (y, 21, MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp_ui_2exp (r, 1, -94) == 0); MPFR_ASSERTN (q[0] == (long) 2); mpfr_set_prec (x, 50); mpfr_set_prec (y, 100); mpfr_set_ui (x, 42, MPFR_RNDN); mpfr_nextabove (x); /* 42 + 2^(-44) */ mpfr_set_ui (y, 21, MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp_ui_2exp (r, 1, -44) == 0); MPFR_ASSERTN (q[0] == (long) 2); mpfr_set_prec (x, 100); mpfr_set_prec (y, 50); mpfr_set_ui (x, 42, MPFR_RNDN); mpfr_set_ui (y, 21, MPFR_RNDN); mpfr_nextabove (y); /* 21 + 2^(-45) */ mpfr_remquo (r, q, x, y, MPFR_RNDN); /* r should be 42 - 2*(21 + 2^(-45)) = -2^(-44) */ MPFR_ASSERTN (mpfr_cmp_si_2exp (r, -1, -44) == 0); MPFR_ASSERTN (q[0] == (long) 2); mpfr_set_prec (x, 50); mpfr_set_prec (y, 100); mpfr_set_ui (x, 42, MPFR_RNDN); mpfr_set_ui (y, 21, MPFR_RNDN); mpfr_nextabove (y); /* 21 + 2^(-95) */ mpfr_remquo (r, q, x, y, MPFR_RNDN); /* r should be 42 - 2*(21 + 2^(-95)) = -2^(-94) */ MPFR_ASSERTN (mpfr_cmp_si_2exp (r, -1, -94) == 0); MPFR_ASSERTN (q[0] == (long) 2); /* exercise large quotient */ mpfr_set_ui_2exp (x, 1, 65, MPFR_RNDN); mpfr_set_ui (y, 1, MPFR_RNDN); /* quotient is 2^65 */ mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp_si (r, 0) == 0); MPFR_ASSERTN (q[0] % 1073741824L == 0L); /* another large quotient */ mpfr_set_prec (x, 65); mpfr_set_prec (y, 65); mpfr_const_pi (x, MPFR_RNDN); mpfr_mul_2exp (x, x, 63, MPFR_RNDN); mpfr_const_log2 (y, MPFR_RNDN); mpfr_set_prec (r, 10); mpfr_remquo (r, q, x, y, MPFR_RNDN); /* q should be 41803643793084085130, r should be 605/2048 */ MPFR_ASSERTN (mpfr_cmp_ui_2exp (r, 605, -11) == 0); MPFR_ASSERTN ((q[0] > 0) && ((q[0] % 1073741824L) == 733836170L)); /* check cases where quotient is 1.5 +/- eps */ mpfr_set_prec (x, 65); mpfr_set_prec (y, 65); mpfr_set_prec (r, 63); mpfr_set_ui (x, 3, MPFR_RNDN); mpfr_set_ui (y, 2, MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); /* x/y = 1.5, quotient should be 2 (even rule), remainder should be -1 */ MPFR_ASSERTN (mpfr_cmp_si (r, -1) == 0); MPFR_ASSERTN (q[0] == 2L); mpfr_set_ui (x, 3, MPFR_RNDN); mpfr_nextabove (x); /* 3 + 2^(-63) */ mpfr_set_ui (y, 2, MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); /* x/y = 1.5 + 2^(-64), quo should be 2, r should be -1 + 2^(-63) */ MPFR_ASSERTN (mpfr_add_ui (r, r, 1, MPFR_RNDN) == 0); MPFR_ASSERTN (mpfr_cmp_ui_2exp (r, 1, -63) == 0); MPFR_ASSERTN (q[0] == 2L); mpfr_set_ui (x, 3, MPFR_RNDN); mpfr_set_ui (y, 2, MPFR_RNDN); mpfr_nextabove (y); /* 2 + 2^(-63) */ mpfr_remquo (r, q, x, y, MPFR_RNDN); /* x/y = 1.5 - eps, quo should be 1, r should be 1 - 2^(-63) */ MPFR_ASSERTN (mpfr_sub_ui (r, r, 1, MPFR_RNDN) == 0); MPFR_ASSERTN (mpfr_cmp_si_2exp (r, -1, -63) == 0); MPFR_ASSERTN (q[0] == 1L); /* bug founds by Kaveh Ghazi, 3 May 2007 */ mpfr_set_ui (x, 2, MPFR_RNDN); mpfr_set_ui (y, 3, MPFR_RNDN); mpfr_remainder (r, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp_si (r, -1) == 0); mpfr_set_si (x, -1, MPFR_RNDN); mpfr_set_ui (y, 1, MPFR_RNDN); mpfr_remainder (r, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp_si (r, 0) == 0 && MPFR_SIGN (r) < 0); /* check argument reuse */ mpfr_set_si (x, -1, MPFR_RNDN); mpfr_set_ui (y, 1, MPFR_RNDN); mpfr_remainder (x, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp_si (x, 0) == 0 && MPFR_SIGN (x) < 0); mpfr_set_ui_2exp (x, 1, mpfr_get_emax () - 1, MPFR_RNDN); mpfr_set_ui_2exp (y, 1, mpfr_get_emin (), MPFR_RNDN); mpfr_remquo (r, q, x, y, MPFR_RNDN); MPFR_ASSERTN (mpfr_zero_p (r) && MPFR_SIGN (r) > 0); MPFR_ASSERTN (q[0] == 0); mpfr_clear (x); mpfr_clear (y); mpfr_clear (r); tests_end_mpfr (); return 0; }
/* Don't need to save/restore exponent range: the cache does it */ int mpfr_const_pi_internal (mpfr_ptr x, mpfr_rnd_t rnd_mode) { mpfr_t a, A, B, D, S; mpfr_prec_t px, p, cancel, k, kmax; MPFR_ZIV_DECL (loop); int inex; MPFR_LOG_FUNC (("rnd_mode=%d", rnd_mode), ("x[%Pu]=%.*Rg inexact=%d", mpfr_get_prec(x), mpfr_log_prec, x, inex)); px = MPFR_PREC (x); /* we need 9*2^kmax - 4 >= px+2*kmax+8 */ for (kmax = 2; ((px + 2 * kmax + 12) / 9) >> kmax; kmax ++); p = px + 3 * kmax + 14; /* guarantees no recomputation for px <= 10000 */ mpfr_init2 (a, p); mpfr_init2 (A, p); mpfr_init2 (B, p); mpfr_init2 (D, p); mpfr_init2 (S, p); MPFR_ZIV_INIT (loop, p); for (;;) { mpfr_set_ui (a, 1, MPFR_RNDN); /* a = 1 */ mpfr_set_ui (A, 1, MPFR_RNDN); /* A = a^2 = 1 */ mpfr_set_ui_2exp (B, 1, -1, MPFR_RNDN); /* B = b^2 = 1/2 */ mpfr_set_ui_2exp (D, 1, -2, MPFR_RNDN); /* D = 1/4 */ #define b B #define ap a #define Ap A #define Bp B for (k = 0; ; k++) { /* invariant: 1/2 <= B <= A <= a < 1 */ mpfr_add (S, A, B, MPFR_RNDN); /* 1 <= S <= 2 */ mpfr_div_2ui (S, S, 2, MPFR_RNDN); /* exact, 1/4 <= S <= 1/2 */ mpfr_sqrt (b, B, MPFR_RNDN); /* 1/2 <= b <= 1 */ mpfr_add (ap, a, b, MPFR_RNDN); /* 1 <= ap <= 2 */ mpfr_div_2ui (ap, ap, 1, MPFR_RNDN); /* exact, 1/2 <= ap <= 1 */ mpfr_mul (Ap, ap, ap, MPFR_RNDN); /* 1/4 <= Ap <= 1 */ mpfr_sub (Bp, Ap, S, MPFR_RNDN); /* -1/4 <= Bp <= 3/4 */ mpfr_mul_2ui (Bp, Bp, 1, MPFR_RNDN); /* -1/2 <= Bp <= 3/2 */ mpfr_sub (S, Ap, Bp, MPFR_RNDN); MPFR_ASSERTN (mpfr_cmp_ui (S, 1) < 0); cancel = mpfr_cmp_ui (S, 0) ? (mpfr_uexp_t) -mpfr_get_exp(S) : p; /* MPFR_ASSERTN (cancel >= px || cancel >= 9 * (1 << k) - 4); */ mpfr_mul_2ui (S, S, k, MPFR_RNDN); mpfr_sub (D, D, S, MPFR_RNDN); /* stop when |A_k - B_k| <= 2^(k-p) i.e. cancel >= p-k */ if (cancel + k >= p) break; } #undef b #undef ap #undef Ap #undef Bp mpfr_div (A, B, D, MPFR_RNDN); /* MPFR_ASSERTN(p >= 2 * k + 8); */ if (MPFR_LIKELY (MPFR_CAN_ROUND (A, p - 2 * k - 8, px, rnd_mode))) break; p += kmax; MPFR_ZIV_NEXT (loop, p); mpfr_set_prec (a, p); mpfr_set_prec (A, p); mpfr_set_prec (B, p); mpfr_set_prec (D, p); mpfr_set_prec (S, p); } MPFR_ZIV_FREE (loop); inex = mpfr_set (x, A, rnd_mode); mpfr_clear (a); mpfr_clear (A); mpfr_clear (B); mpfr_clear (D); mpfr_clear (S); return inex; }
static void test_2exp (void) { mpfr_t x; int res; mpfr_init2 (x, 32); mpfr_set_ui_2exp (x, 1, 0, MPFR_RNDN); if (mpfr_cmp_ui(x, 1)) ERROR("(1U,0)"); mpfr_set_ui_2exp (x, 1024, -10, MPFR_RNDN); if (mpfr_cmp_ui(x, 1)) ERROR("(1024U,-10)"); mpfr_set_ui_2exp (x, 1024, 10, MPFR_RNDN); if (mpfr_cmp_ui(x, 1024*1024)) ERROR("(1024U,+10)"); mpfr_set_si_2exp (x, -1024L * 1024L, -10, MPFR_RNDN); if (mpfr_cmp_si(x, -1024)) ERROR("(1M,-10)"); mpfr_set_ui_2exp (x, 0x92345678, 16, MPFR_RNDN); if (mpfr_cmp_str (x, "92345678@4", 16, MPFR_RNDN)) ERROR("(x92345678U,+16)"); mpfr_set_si_2exp (x, -0x1ABCDEF0, -256, MPFR_RNDN); if (mpfr_cmp_str (x, "-1ABCDEF0@-64", 16, MPFR_RNDN)) ERROR("(-x1ABCDEF0,-256)"); mpfr_set_prec (x, 2); res = mpfr_set_si_2exp (x, 7, 10, MPFR_RNDU); if (mpfr_cmp_ui (x, 1<<13) || res <= 0) ERROR ("Prec 2 + si_2exp"); res = mpfr_set_ui_2exp (x, 7, 10, MPFR_RNDU); if (mpfr_cmp_ui (x, 1<<13) || res <= 0) ERROR ("Prec 2 + ui_2exp"); mpfr_clear_flags (); mpfr_set_ui_2exp (x, 17, MPFR_EMAX_MAX, MPFR_RNDN); if (!mpfr_inf_p (x) || MPFR_IS_NEG (x)) ERROR ("mpfr_set_ui_2exp and overflow (bad result)"); if (!mpfr_overflow_p ()) ERROR ("mpfr_set_ui_2exp and overflow (overflow flag not set)"); mpfr_clear_flags (); mpfr_set_si_2exp (x, 17, MPFR_EMAX_MAX, MPFR_RNDN); if (!mpfr_inf_p (x) || MPFR_IS_NEG (x)) ERROR ("mpfr_set_si_2exp (pos) and overflow (bad result)"); if (!mpfr_overflow_p ()) ERROR ("mpfr_set_si_2exp (pos) and overflow (overflow flag not set)"); mpfr_clear_flags (); mpfr_set_si_2exp (x, -17, MPFR_EMAX_MAX, MPFR_RNDN); if (!mpfr_inf_p (x) || MPFR_IS_POS (x)) ERROR ("mpfr_set_si_2exp (neg) and overflow (bad result)"); if (!mpfr_overflow_p ()) ERROR ("mpfr_set_si_2exp (neg) and overflow (overflow flag not set)"); mpfr_clear (x); }
int main (int argc, char *argv[]) { mpfr_t x; long k, z, d, N; unsigned long zl, dl; int inex; int r; mpfr_exp_t emin, emax; int flag; tests_start_mpfr (); mpfr_init2 (x, 100); N = (argc==1) ? 100000 : atol (argv[1]); for (k = 1; k <= N; k++) { z = (long) (randlimb () & LONG_MAX) + LONG_MIN / 2; inex = mpfr_set_si (x, z, MPFR_RNDZ); d = mpfr_get_si (x, MPFR_RNDZ); if (d != z) { printf ("Error in mpfr_set_si: expected %ld got %ld\n", z, d); exit (1); } if (inex) { printf ("Error in mpfr_set_si: inex value incorrect for %ld: %d\n", z, inex); exit (1); } } for (k = 1; k <= N; k++) { zl = randlimb (); inex = mpfr_set_ui (x, zl, MPFR_RNDZ); dl = mpfr_get_ui (x, MPFR_RNDZ); if (dl != zl) { printf ("Error in mpfr_set_ui: expected %lu got %lu\n", zl, dl); exit (1); } if (inex) { printf ("Error in mpfr_set_ui: inex value incorrect for %lu: %d\n", zl, inex); exit (1); } } mpfr_set_prec (x, 2); if (mpfr_set_si (x, 5, MPFR_RNDZ) >= 0) { printf ("Wrong inexact flag for x=5, rnd=MPFR_RNDZ\n"); exit (1); } mpfr_set_prec (x, 2); if (mpfr_set_si (x, -5, MPFR_RNDZ) <= 0) { printf ("Wrong inexact flag for x=-5, rnd=MPFR_RNDZ\n"); exit (1); } mpfr_set_prec (x, 3); inex = mpfr_set_si (x, 77617, MPFR_RNDD); /* should be 65536 */ if (MPFR_MANT(x)[0] != ((mp_limb_t)1 << (mp_bits_per_limb-1)) || inex >= 0) { printf ("Error in mpfr_set_si(x:3, 77617, MPFR_RNDD)\n"); mpfr_print_binary (x); puts (""); exit (1); } inex = mpfr_set_ui (x, 77617, MPFR_RNDD); /* should be 65536 */ if (MPFR_MANT(x)[0] != ((mp_limb_t)1 << (mp_bits_per_limb-1)) || inex >= 0) { printf ("Error in mpfr_set_ui(x:3, 77617, MPFR_RNDD)\n"); mpfr_print_binary (x); puts (""); exit (1); } mpfr_set_prec (x, 2); inex = mpfr_set_si (x, 33096, MPFR_RNDU); if (mpfr_get_si (x, MPFR_RNDZ) != 49152 || inex <= 0) { printf ("Error in mpfr_set_si, exp. 49152, got %ld, inex %d\n", mpfr_get_si (x, MPFR_RNDZ), inex); exit (1); } inex = mpfr_set_ui (x, 33096, MPFR_RNDU); if (mpfr_get_si (x, MPFR_RNDZ) != 49152) { printf ("Error in mpfr_set_ui, exp. 49152, got %ld, inex %d\n", mpfr_get_si (x, MPFR_RNDZ), inex); exit (1); } /* Also test the mpfr_set_ui function (instead of macro). */ inex = (mpfr_set_ui) (x, 33096, MPFR_RNDU); if (mpfr_get_si (x, MPFR_RNDZ) != 49152) { printf ("Error in mpfr_set_ui function, exp. 49152, got %ld, inex %d\n", mpfr_get_si (x, MPFR_RNDZ), inex); exit (1); } for (r = 0 ; r < MPFR_RND_MAX ; r++) { mpfr_set_si (x, -1, (mpfr_rnd_t) r); mpfr_set_ui (x, 0, (mpfr_rnd_t) r); if (MPFR_IS_NEG (x) || mpfr_get_ui (x, (mpfr_rnd_t) r) != 0) { printf ("mpfr_set_ui (x, 0) gives -0 for %s\n", mpfr_print_rnd_mode ((mpfr_rnd_t) r)); exit (1); } mpfr_set_si (x, -1, (mpfr_rnd_t) r); mpfr_set_si (x, 0, (mpfr_rnd_t) r); if (MPFR_IS_NEG (x) || mpfr_get_si (x, (mpfr_rnd_t) r) != 0) { printf ("mpfr_set_si (x, 0) gives -0 for %s\n", mpfr_print_rnd_mode ((mpfr_rnd_t) r)); exit (1); } } /* check potential bug in case mp_limb_t is unsigned */ emax = mpfr_get_emax (); set_emax (0); mpfr_set_si (x, -1, MPFR_RNDN); if (mpfr_sgn (x) >= 0) { printf ("mpfr_set_si (x, -1) fails\n"); exit (1); } set_emax (emax); emax = mpfr_get_emax (); set_emax (5); mpfr_set_prec (x, 2); mpfr_set_si (x, -31, MPFR_RNDN); if (mpfr_sgn (x) >= 0) { printf ("mpfr_set_si (x, -31) fails\n"); exit (1); } set_emax (emax); /* test for get_ui */ mpfr_set_ui (x, 0, MPFR_RNDN); MPFR_ASSERTN(mpfr_get_ui (x, MPFR_RNDN) == 0); mpfr_set_ui (x, ULONG_MAX, MPFR_RNDU); mpfr_nextabove (x); mpfr_get_ui (x, MPFR_RNDU); /* another test for get_ui */ mpfr_set_prec (x, 10); mpfr_set_str_binary (x, "10.101"); dl = mpfr_get_ui (x, MPFR_RNDN); MPFR_ASSERTN (dl == 3); mpfr_set_str_binary (x, "-1.0"); mpfr_get_ui (x, MPFR_RNDN); mpfr_set_str_binary (x, "0.1"); dl = mpfr_get_ui (x, MPFR_RNDN); MPFR_ASSERTN (dl == 0); dl = mpfr_get_ui (x, MPFR_RNDZ); MPFR_ASSERTN (dl == 0); dl = mpfr_get_ui (x, MPFR_RNDD); MPFR_ASSERTN (dl == 0); dl = mpfr_get_ui (x, MPFR_RNDU); MPFR_ASSERTN (dl == 1); /* coverage tests */ mpfr_set_prec (x, 2); mpfr_set_si (x, -7, MPFR_RNDD); MPFR_ASSERTN(mpfr_cmp_si (x, -8) == 0); mpfr_set_prec (x, 2); mpfr_set_ui (x, 7, MPFR_RNDU); MPFR_ASSERTN(mpfr_cmp_ui (x, 8) == 0); emax = mpfr_get_emax (); set_emax (3); mpfr_set_ui (x, 7, MPFR_RNDU); MPFR_ASSERTN(mpfr_inf_p (x) && mpfr_sgn (x) > 0); set_emax (1); MPFR_ASSERTN( mpfr_set_ui (x, 7, MPFR_RNDU) ); MPFR_ASSERTN(mpfr_inf_p (x) && mpfr_sgn (x) > 0); set_emax (emax); mpfr_set_ui_2exp (x, 17, -50, MPFR_RNDN); MPFR_ASSERTN (mpfr_get_ui (x, MPFR_RNDD) == 0); MPFR_ASSERTN (mpfr_get_si (x, MPFR_RNDD) == 0); /* Test for ERANGE flag + correct behaviour if overflow */ mpfr_set_prec (x, 256); mpfr_set_ui (x, ULONG_MAX, MPFR_RNDN); mpfr_clear_erangeflag (); dl = mpfr_get_ui (x, MPFR_RNDN); if (dl != ULONG_MAX || mpfr_erangeflag_p ()) { printf ("ERROR for get_ui + ERANGE + ULONG_MAX (1)\n"); exit (1); } mpfr_add_ui (x, x, 1, MPFR_RNDN); dl = mpfr_get_ui (x, MPFR_RNDN); if (dl != ULONG_MAX || !mpfr_erangeflag_p ()) { printf ("ERROR for get_ui + ERANGE + ULONG_MAX (2)\n"); exit (1); } mpfr_set_si (x, -1, MPFR_RNDN); mpfr_clear_erangeflag (); dl = mpfr_get_ui (x, MPFR_RNDN); if (dl != 0 || !mpfr_erangeflag_p ()) { printf ("ERROR for get_ui + ERANGE + -1 \n"); exit (1); } mpfr_set_si (x, LONG_MAX, MPFR_RNDN); mpfr_clear_erangeflag (); d = mpfr_get_si (x, MPFR_RNDN); if (d != LONG_MAX || mpfr_erangeflag_p ()) { printf ("ERROR for get_si + ERANGE + LONG_MAX (1): %ld\n", d); exit (1); } mpfr_add_ui (x, x, 1, MPFR_RNDN); d = mpfr_get_si (x, MPFR_RNDN); if (d != LONG_MAX || !mpfr_erangeflag_p ()) { printf ("ERROR for get_si + ERANGE + LONG_MAX (2)\n"); exit (1); } mpfr_set_si (x, LONG_MIN, MPFR_RNDN); mpfr_clear_erangeflag (); d = mpfr_get_si (x, MPFR_RNDN); if (d != LONG_MIN || mpfr_erangeflag_p ()) { printf ("ERROR for get_si + ERANGE + LONG_MIN (1)\n"); exit (1); } mpfr_sub_ui (x, x, 1, MPFR_RNDN); d = mpfr_get_si (x, MPFR_RNDN); if (d != LONG_MIN || !mpfr_erangeflag_p ()) { printf ("ERROR for get_si + ERANGE + LONG_MIN (2)\n"); exit (1); } mpfr_set_nan (x); mpfr_clear_erangeflag (); d = mpfr_get_ui (x, MPFR_RNDN); if (d != 0 || !mpfr_erangeflag_p ()) { printf ("ERROR for get_ui + NaN\n"); exit (1); } mpfr_clear_erangeflag (); d = mpfr_get_si (x, MPFR_RNDN); if (d != 0 || !mpfr_erangeflag_p ()) { printf ("ERROR for get_si + NaN\n"); exit (1); } emin = mpfr_get_emin (); mpfr_set_prec (x, 2); mpfr_set_emin (4); mpfr_clear_flags (); mpfr_set_ui (x, 7, MPFR_RNDU); flag = mpfr_underflow_p (); mpfr_set_emin (emin); if (mpfr_cmp_ui (x, 8) != 0) { printf ("Error for mpfr_set_ui (x, 7, MPFR_RNDU), prec = 2, emin = 4\n"); exit (1); } if (flag) { printf ("mpfr_set_ui (x, 7, MPFR_RNDU) should not underflow " "with prec = 2, emin = 4\n"); exit (1); } mpfr_set_emin (4); mpfr_clear_flags (); mpfr_set_si (x, -7, MPFR_RNDD); flag = mpfr_underflow_p (); mpfr_set_emin (emin); if (mpfr_cmp_si (x, -8) != 0) { printf ("Error for mpfr_set_si (x, -7, MPFR_RNDD), prec = 2, emin = 4\n"); exit (1); } if (flag) { printf ("mpfr_set_si (x, -7, MPFR_RNDD) should not underflow " "with prec = 2, emin = 4\n"); exit (1); } mpfr_clear (x); test_2exp (); test_macros (); test_macros_keyword (); tests_end_mpfr (); return 0; }
static int hexadecimal (void) { mpfr_t x, z; mpfr_inits2 (64, x, z, (mpfr_ptr) 0); /* special */ mpfr_set_inf (x, 1); check_sprintf (pinf_str, "%Ra", x); check_sprintf (pinf_str, "%RUa", x); check_sprintf (pinf_str, "%RDa", x); check_sprintf (pinf_uc_str, "%RA", x); check_sprintf (pinf_uc_str, "%RYA", x); check_sprintf (pinf_uc_str, "%RZA", x); check_sprintf (pinf_uc_str, "%RNA", x); mpfr_set_inf (x, -1); check_sprintf (minf_str, "%Ra", x); check_sprintf (minf_str, "%RYa", x); check_sprintf (minf_str, "%RZa", x); check_sprintf (minf_str, "%RNa", x); check_sprintf (minf_uc_str, "%RA", x); check_sprintf (minf_uc_str, "%RUA", x); check_sprintf (minf_uc_str, "%RDA", x); mpfr_set_nan (x); check_sprintf (nan_str, "%Ra", x); check_sprintf (nan_uc_str, "%RA", x); /* regular numbers */ mpfr_set_str (x, "FEDCBA9.87654321", 16, MPFR_RNDN); mpfr_set_ui (z, 0, MPFR_RNDZ); /* simplest case right justified */ check_sprintf (" 0xf.edcba987654321p+24", "%25Ra", x); check_sprintf (" 0xf.edcba987654321p+24", "%25RUa", x); check_sprintf (" 0xf.edcba987654321p+24", "%25RDa", x); check_sprintf (" 0xf.edcba987654321p+24", "%25RYa", x); check_sprintf (" 0xf.edcba987654321p+24", "%25RZa", x); check_sprintf (" 0xf.edcba987654321p+24", "%25RNa", x); check_sprintf (" 0x1p+28", "%25.0Ra", x); check_sprintf (" 0x0p+0", "%25.0Ra", z); /* sign or space, pad with leading zeros */ check_sprintf (" 0X00F.EDCBA987654321P+24", "% 025RA", x); check_sprintf (" 0X000000000000000001P+28", "% 025.0RA", x); check_sprintf (" 0X0000000000000000000P+0", "% 025.0RA", z); /* sign + or -, left justified */ check_sprintf ("+0xf.edcba987654321p+24 ", "%+-25Ra", x); check_sprintf ("+0x1p+28 ", "%+-25.0Ra", x); check_sprintf ("+0x0p+0 ", "%+-25.0Ra", z); /* decimal point, left justified, precision and rounding parameter */ check_vsprintf ("0XF.FP+24 ", "%#-10.*R*A", 1, MPFR_RNDN, x); check_vsprintf ("0X1.P+28 ", "%#-10.*R*A", 0, MPFR_RNDN, x); check_vsprintf ("0X0.P+0 ", "%#-10.*R*A", 0, MPFR_RNDN, z); /* sign or space */ check_sprintf (" 0xf.eddp+24", "% .3RNa", x); check_sprintf (" 0x1p+28", "% .0RNa", x); /* sign + or -, decimal point, pad with leading zeros */ check_sprintf ("+0X0F.EP+24", "%0+#11.1RZA", x); check_sprintf ("+0X00F.P+24", "%0+#11.0RZA", x); check_sprintf ("+0X000.0P+0", "%0+#11.1RZA", z); /* pad with leading zero */ check_sprintf ("0x0000f.edcba987654321p+24", "%026RDa", x); check_sprintf ("0x0000000000000000000fp+24", "%026.0RDa", x); /* sign or space, decimal point, left justified */ check_sprintf (" 0XF.EP+24 " , "%- #11.1RDA", x); check_sprintf (" 0XF.P+24 " , "%- #11.0RDA", x); mpfr_mul_si (x, x, -1, MPFR_RNDD); mpfr_mul_si (z, z, -1, MPFR_RNDD); /* sign + or - */ check_sprintf ("-0xf.ep+24", "%+10.1RUa", x); check_sprintf (" -0xfp+24", "%+10.0RUa", x); check_sprintf (" -0x0p+0", "%+10.0RUa", z); /* rounding bit is zero */ mpfr_set_str (x, "0xF.7", 16, MPFR_RNDN); check_sprintf ("0XFP+0", "%.0RNA", x); /* tie case in round to nearest mode */ mpfr_set_str (x, "0x0.8800000000000000p+3", 16, MPFR_RNDN); check_sprintf ("0x9.p-1", "%#.0RNa", x); mpfr_set_str (x, "-0x0.9800000000000000p+3", 16, MPFR_RNDN); check_sprintf ("-0xap-1", "%.0RNa", x); /* trailing zeros in fractional part */ check_sprintf ("-0X4.C0000000000000000000P+0", "%.20RNA", x); /* rounding bit is one and the first non zero bit is far away */ mpfr_set_prec (x, 1024); mpfr_set_ui_2exp (x, 29, -1, MPFR_RNDN); mpfr_nextabove (x); check_sprintf ("0XFP+0", "%.0RNA", x); /* with more than one limb */ mpfr_set_prec (x, 300); mpfr_set_str (x, "0xf.ffffffffffffffffffffffffffffffffffffffffffffffffffff" "fffffffffffffffff", 16, MPFR_RNDN); check_sprintf ("0x1p+4 [300]", "%.0RNa [300]", x); check_sprintf ("0xfp+0 [300]", "%.0RZa [300]", x); check_sprintf ("0x1p+4 [300]", "%.0RYa [300]", x); check_sprintf ("0xfp+0 [300]", "%.0RDa [300]", x); check_sprintf ("0x1p+4 [300]", "%.0RUa [300]", x); check_sprintf ("0x1.0000000000000000000000000000000000000000p+4", "%.40RNa", x); check_sprintf ("0xf.ffffffffffffffffffffffffffffffffffffffffp+0", "%.40RZa", x); check_sprintf ("0x1.0000000000000000000000000000000000000000p+4", "%.40RYa", x); check_sprintf ("0xf.ffffffffffffffffffffffffffffffffffffffffp+0", "%.40RDa", x); check_sprintf ("0x1.0000000000000000000000000000000000000000p+4", "%.40RUa", x); mpfr_set_str (x, "0xf.7fffffffffffffffffffffffffffffffffffffffffffffffffff" "ffffffffffffffffff", 16, MPFR_RNDN); check_sprintf ("0XFP+0", "%.0RNA", x); check_sprintf ("0XFP+0", "%.0RZA", x); check_sprintf ("0X1P+4", "%.0RYA", x); check_sprintf ("0XFP+0", "%.0RDA", x); check_sprintf ("0X1P+4", "%.0RUA", x); check_sprintf ("0XF.8P+0", "%.1RNA", x); check_sprintf ("0XF.7P+0", "%.1RZA", x); check_sprintf ("0XF.8P+0", "%.1RYA", x); check_sprintf ("0XF.7P+0", "%.1RDA", x); check_sprintf ("0XF.8P+0", "%.1RUA", x); /* do not round up to the next power of the base */ mpfr_set_str (x, "0xf.fffffffffffffffffffffffffffffffffffffeffffffffffffff" "ffffffffffffffffff", 16, MPFR_RNDN); check_sprintf ("0xf.ffffffffffffffffffffffffffffffffffffff00p+0", "%.40RNa", x); check_sprintf ("0xf.fffffffffffffffffffffffffffffffffffffeffp+0", "%.40RZa", x); check_sprintf ("0xf.ffffffffffffffffffffffffffffffffffffff00p+0", "%.40RYa", x); check_sprintf ("0xf.fffffffffffffffffffffffffffffffffffffeffp+0", "%.40RDa", x); check_sprintf ("0xf.ffffffffffffffffffffffffffffffffffffff00p+0", "%.40RUa", x); mpfr_clears (x, z, (mpfr_ptr) 0); return 0; }
static int decimal (void) { mpfr_prec_t p = 128; mpfr_t x; mpfr_t z; mpfr_init (z); mpfr_init2 (x, p); /* specifier 'P' for precision */ check_vsprintf ("128", "%Pu", p); check_vsprintf ("00128", "%.5Pu", p); /* special numbers */ mpfr_set_inf (x, 1); check_sprintf (pinf_str, "%Re", x); check_sprintf (pinf_str, "%RUe", x); check_sprintf (pinf_uc_str, "%RE", x); check_sprintf (pinf_uc_str, "%RDE", x); check_sprintf (pinf_str, "%Rf", x); check_sprintf (pinf_str, "%RYf", x); check_sprintf (pinf_uc_str, "%RF", x); check_sprintf (pinf_uc_str, "%RZF", x); check_sprintf (pinf_str, "%Rg", x); check_sprintf (pinf_str, "%RNg", x); check_sprintf (pinf_uc_str, "%RG", x); check_sprintf (pinf_uc_str, "%RUG", x); check_sprintf (" inf", "%010Re", x); check_sprintf (" inf", "%010RDe", x); mpfr_set_inf (x, -1); check_sprintf (minf_str, "%Re", x); check_sprintf (minf_str, "%RYe", x); check_sprintf (minf_uc_str, "%RE", x); check_sprintf (minf_uc_str, "%RZE", x); check_sprintf (minf_str, "%Rf", x); check_sprintf (minf_str, "%RNf", x); check_sprintf (minf_uc_str, "%RF", x); check_sprintf (minf_uc_str, "%RUF", x); check_sprintf (minf_str, "%Rg", x); check_sprintf (minf_str, "%RDg", x); check_sprintf (minf_uc_str, "%RG", x); check_sprintf (minf_uc_str, "%RYG", x); check_sprintf (" -inf", "%010Re", x); check_sprintf (" -inf", "%010RZe", x); mpfr_set_nan (x); check_sprintf (nan_str, "%Re", x); check_sprintf (nan_str, "%RNe", x); check_sprintf (nan_uc_str, "%RE", x); check_sprintf (nan_uc_str, "%RUE", x); check_sprintf (nan_str, "%Rf", x); check_sprintf (nan_str, "%RDf", x); check_sprintf (nan_uc_str, "%RF", x); check_sprintf (nan_uc_str, "%RYF", x); check_sprintf (nan_str, "%Rg", x); check_sprintf (nan_str, "%RZg", x); check_sprintf (nan_uc_str, "%RG", x); check_sprintf (nan_uc_str, "%RNG", x); check_sprintf (" nan", "%010Re", x); /* positive numbers */ mpfr_set_str (x, "18993474.61279296875", 10, MPFR_RNDN); mpfr_set_ui (z, 0, MPFR_RNDD); /* simplest case right justified */ check_sprintf (" 1.899347461279296875e+07", "%30Re", x); check_sprintf (" 2e+07", "%30.0Re", x); check_sprintf (" 18993474.612793", "%30Rf", x); check_sprintf (" 18993474.6127930", "%30.7Rf", x); check_sprintf (" 1.89935e+07", "%30Rg", x); check_sprintf (" 2e+07", "%30.0Rg", x); check_sprintf (" 18993474.61279296875", "%30.19Rg", x); check_sprintf (" 0e+00", "%30.0Re", z); check_sprintf (" 0", "%30.0Rf", z); check_sprintf (" 0.0000", "%30.4Rf", z); check_sprintf (" 0", "%30.0Rg", z); check_sprintf (" 0", "%30.4Rg", z); /* sign or space, pad with leading zeros */ check_sprintf (" 000001.899347461279296875E+07", "% 030RE", x); check_sprintf (" 0000000000000000001.89935E+07", "% 030RG", x); check_sprintf (" 0000000000000000000000002E+07", "% 030.0RE", x); check_sprintf (" 0000000000000000000000000E+00", "% 030.0RE", z); check_sprintf (" 00000000000000000000000000000", "% 030.0RF", z); /* sign + or -, left justified */ check_sprintf ("+1.899347461279296875e+07 ", "%+-30Re", x); check_sprintf ("+2e+07 ", "%+-30.0Re", x); check_sprintf ("+0e+00 ", "%+-30.0Re", z); check_sprintf ("+0 ", "%+-30.0Rf", z); /* decimal point, left justified, precision and rounding parameter */ check_vsprintf ("1.9E+07 ", "%#-10.*R*E", 1, MPFR_RNDN, x); check_vsprintf ("2.E+07 ", "%#*.*R*E", -10, 0, MPFR_RNDN, x); check_vsprintf ("2.E+07 ", "%#-10.*R*G", 0, MPFR_RNDN, x); check_vsprintf ("0.E+00 ", "%#-10.*R*E", 0, MPFR_RNDN, z); check_vsprintf ("0. ", "%#-10.*R*F", 0, MPFR_RNDN, z); check_vsprintf ("0. ", "%#-10.*R*G", 0, MPFR_RNDN, z); /* sign or space */ check_sprintf (" 1.899e+07", "% .3RNe", x); check_sprintf (" 2e+07", "% .0RNe", x); /* sign + or -, decimal point, pad with leading zeros */ check_sprintf ("+0001.8E+07", "%0+#11.1RZE", x); check_sprintf ("+00001.E+07", "%0+#11.0RZE", x); check_sprintf ("+0000.0E+00", "%0+#11.1RZE", z); check_sprintf ("+00000000.0", "%0+#11.1RZF", z); /* pad with leading zero */ check_sprintf ("0000001.899347461279296875e+07", "%030RDe", x); check_sprintf ("00000000000000000000000001e+07", "%030.0RDe", x); /* sign or space, decimal point, left justified */ check_sprintf (" 1.8E+07 ", "%- #11.1RDE", x); check_sprintf (" 1.E+07 ", "%- #11.0RDE", x); /* negative numbers */ mpfr_mul_si (x, x, -1, MPFR_RNDD); mpfr_mul_si (z, z, -1, MPFR_RNDD); /* sign + or - */ check_sprintf (" -1.8e+07", "%+10.1RUe", x); check_sprintf (" -1e+07", "%+10.0RUe", x); check_sprintf (" -0e+00", "%+10.0RUe", z); check_sprintf (" -0", "%+10.0RUf", z); /* neighborhood of 1 */ mpfr_set_str (x, "0.99993896484375", 10, MPFR_RNDN); check_sprintf ("9.9993896484375E-01 ", "%-20RE", x); check_sprintf ("9.9993896484375E-01 ", "%-20.RE", x); check_sprintf ("1E+00 ", "%-20.0RE", x); check_sprintf ("1.0E+00 ", "%-20.1RE", x); check_sprintf ("1.00E+00 ", "%-20.2RE", x); check_sprintf ("9.999E-01 ", "%-20.3RE", x); check_sprintf ("9.9994E-01 ", "%-20.4RE", x); check_sprintf ("0.999939 ", "%-20RF", x); check_sprintf ("0.999939 ", "%-20.RF", x); check_sprintf ("1 ", "%-20.0RF", x); check_sprintf ("1.0 ", "%-20.1RF", x); check_sprintf ("1.00 ", "%-20.2RF", x); check_sprintf ("1.000 ", "%-20.3RF", x); check_sprintf ("0.9999 ", "%-20.4RF", x); check_sprintf ("0.999939 ", "%-#20RF", x); check_sprintf ("0.999939 ", "%-#20.RF", x); check_sprintf ("1. ", "%-#20.0RF", x); check_sprintf ("1.0 ", "%-#20.1RF", x); check_sprintf ("1.00 ", "%-#20.2RF", x); check_sprintf ("1.000 ", "%-#20.3RF", x); check_sprintf ("0.9999 ", "%-#20.4RF", x); check_sprintf ("1 ", "%-20.0RG", x); check_sprintf ("1 ", "%-20.1RG", x); check_sprintf ("1 ", "%-20.2RG", x); check_sprintf ("1 ", "%-20.3RG", x); check_sprintf ("0.9999 ", "%-20.4RG", x); check_sprintf ("0.999939 ", "%-#20RG", x); check_sprintf ("0.999939 ", "%-#20.RG", x); check_sprintf ("1. ", "%-#20.0RG", x); check_sprintf ("1. ", "%-#20.1RG", x); check_sprintf ("1.0 ", "%-#20.2RG", x); check_sprintf ("1.00 ", "%-#20.3RG", x); check_sprintf ("0.9999 ", "%-#20.4RG", x); /* multiple of 10 */ mpfr_set_str (x, "1e17", 10, MPFR_RNDN); check_sprintf ("1e+17", "%Re", x); check_sprintf ("1.000e+17", "%.3Re", x); check_sprintf ("100000000000000000", "%.0Rf", x); check_sprintf ("100000000000000000.0", "%.1Rf", x); check_sprintf ("100000000000000000.000000", "%'Rf", x); check_sprintf ("100000000000000000.0", "%'.1Rf", x); mpfr_ui_div (x, 1, x, MPFR_RNDN); /* x=1e-17 */ check_sprintf ("1e-17", "%Re", x); check_sprintf ("0.000000", "%Rf", x); check_sprintf ("1e-17", "%Rg", x); check_sprintf ("0.0", "%.1RDf", x); check_sprintf ("0.0", "%.1RZf", x); check_sprintf ("0.1", "%.1RUf", x); check_sprintf ("0.1", "%.1RYf", x); check_sprintf ("0", "%.0RDf", x); check_sprintf ("0", "%.0RZf", x); check_sprintf ("1", "%.0RUf", x); check_sprintf ("1", "%.0RYf", x); /* multiple of 10 with 'g' style */ mpfr_set_str (x, "10", 10, MPFR_RNDN); check_sprintf ("10", "%Rg", x); check_sprintf ("1e+01", "%.0Rg", x); check_sprintf ("1e+01", "%.1Rg", x); check_sprintf ("10", "%.2Rg", x); mpfr_ui_div (x, 1, x, MPFR_RNDN); check_sprintf ("0.1", "%Rg", x); check_sprintf ("0.1", "%.0Rg", x); check_sprintf ("0.1", "%.1Rg", x); mpfr_set_str (x, "1000", 10, MPFR_RNDN); check_sprintf ("1000", "%Rg", x); check_sprintf ("1e+03", "%.0Rg", x); check_sprintf ("1e+03", "%.3Rg", x); check_sprintf ("1000", "%.4Rg", x); mpfr_ui_div (x, 1, x, MPFR_RNDN); check_sprintf ("0.001", "%Rg", x); check_sprintf ("0.001", "%.0Rg", x); check_sprintf ("0.001", "%.1Rg", x); mpfr_set_str (x, "100000", 10, MPFR_RNDN); check_sprintf ("100000", "%Rg", x); check_sprintf ("1e+05", "%.0Rg", x); check_sprintf ("1e+05", "%.5Rg", x); check_sprintf ("100000", "%.6Rg", x); mpfr_ui_div (x, 1, x, MPFR_RNDN); check_sprintf ("1e-05", "%Rg", x); check_sprintf ("1e-05", "%.0Rg", x); check_sprintf ("1e-05", "%.1Rg", x); /* check rounding mode */ mpfr_set_str (x, "0.0076", 10, MPFR_RNDN); check_sprintf ("0.007", "%.3RDF", x); check_sprintf ("0.007", "%.3RZF", x); check_sprintf ("0.008", "%.3RF", x); check_sprintf ("0.008", "%.3RUF", x); check_sprintf ("0.008", "%.3RYF", x); check_vsprintf ("0.008", "%.3R*F", MPFR_RNDA, x); /* check limit between %f-style and %g-style */ mpfr_set_str (x, "0.0000999", 10, MPFR_RNDN); check_sprintf ("0.0001", "%.0Rg", x); check_sprintf ("9e-05", "%.0RDg", x); check_sprintf ("0.0001", "%.1Rg", x); check_sprintf ("0.0001", "%.2Rg", x); check_sprintf ("9.99e-05", "%.3Rg", x); /* trailing zeros */ mpfr_set_si_2exp (x, -1, -15, MPFR_RNDN); /* x=-2^-15 */ check_sprintf ("-3.0517578125e-05", "%.30Rg", x); check_sprintf ("-3.051757812500000000000000000000e-05", "%.30Re", x); check_sprintf ("-3.05175781250000000000000000000e-05", "%#.30Rg", x); check_sprintf ("-0.000030517578125000000000000000", "%.30Rf", x); /* bug 20081023 */ check_sprintf ("-3.0517578125e-05", "%.30Rg", x); mpfr_set_str (x, "1.9999", 10, MPFR_RNDN); check_sprintf ("1.999900 ", "%-#10.7RG", x); check_sprintf ("1.9999 ", "%-10.7RG", x); mpfr_set_ui (x, 1, MPFR_RNDN); check_sprintf ("1.00000000000000000000000000000", "%#.30Rg", x); check_sprintf ("1", "%.30Rg", x); mpfr_set_ui (x, 0, MPFR_RNDN); check_sprintf ("0.000000000000000000000000000000", "%#.30Rg", x); check_sprintf ("0", "%.30Rg", x); /* following tests with precision 53 bits */ mpfr_set_prec (x, 53); /* Exponent zero has a plus sign */ mpfr_set_str (x, "-9.95645044213728791504536275169812142849e-01", 10, MPFR_RNDN); check_sprintf ("-1.0e+00", "%- #0.1Re", x); /* Decimal point and no figure after it with '#' flag and 'G' style */ mpfr_set_str (x, "-9.90597761233942053494e-01", 10, MPFR_RNDN); check_sprintf ("-1.", "%- #0.1RG", x); /* precision zero */ mpfr_set_d (x, 9.5, MPFR_RNDN); check_sprintf ("9", "%.0RDf", x); check_sprintf ("10", "%.0RUf", x); mpfr_set_d (x, 19.5, MPFR_RNDN); check_sprintf ("19", "%.0RDf", x); check_sprintf ("20", "%.0RUf", x); mpfr_set_d (x, 99.5, MPFR_RNDN); check_sprintf ("99", "%.0RDf", x); check_sprintf ("100", "%.0RUf", x); mpfr_set_d (x, -9.5, MPFR_RNDN); check_sprintf ("-10", "%.0RDf", x); check_sprintf ("-10", "%.0RYf", x); check_sprintf ("-10", "%.0Rf", x); check_sprintf ("-1e+01", "%.0Re", x); check_sprintf ("-1e+01", "%.0Rg", x); mpfr_set_ui_2exp (x, 1, -1, MPFR_RNDN); check_sprintf ("0", "%.0Rf", x); check_sprintf ("5e-01", "%.0Re", x); check_sprintf ("0.5", "%.0Rg", x); mpfr_set_ui_2exp (x, 3, -1, MPFR_RNDN); check_sprintf ("2", "%.0Rf", x); mpfr_set_ui_2exp (x, 5, -1, MPFR_RNDN); check_sprintf ("2", "%.0Rf", x); mpfr_set_ui (x, 0x1f, MPFR_RNDN); check_sprintf ("0x1p+5", "%.0Ra", x); mpfr_set_ui (x, 3, MPFR_RNDN); check_sprintf ("1p+2", "%.0Rb", x); /* round to next ten power with %f but not with %g */ mpfr_set_str (x, "-6.64464380544039223686e-02", 10, MPFR_RNDN); check_sprintf ("-0.1", "%.1Rf", x); check_sprintf ("-0.0", "%.1RZf", x); check_sprintf ("-0.07", "%.1Rg", x); check_sprintf ("-0.06", "%.1RZg", x); /* round to next ten power and do not remove trailing zeros */ mpfr_set_str (x, "9.98429393291486722006e-02", 10, MPFR_RNDN); check_sprintf ("0.1", "%#.1Rg", x); check_sprintf ("0.10", "%#.2Rg", x); check_sprintf ("0.099", "%#.2RZg", x); /* Halfway cases */ mpfr_set_str (x, "1.5", 10, MPFR_RNDN); check_sprintf ("2e+00", "%.0Re", x); mpfr_set_str (x, "2.5", 10, MPFR_RNDN); check_sprintf ("2e+00", "%.0Re", x); mpfr_set_str (x, "9.5", 10, MPFR_RNDN); check_sprintf ("1e+01", "%.0Re", x); mpfr_set_str (x, "1.25", 10, MPFR_RNDN); check_sprintf ("1.2e+00", "%.1Re", x); mpfr_set_str (x, "1.75", 10, MPFR_RNDN); check_sprintf ("1.8e+00", "%.1Re", x); mpfr_set_str (x, "-0.5", 10, MPFR_RNDN); check_sprintf ("-0", "%.0Rf", x); mpfr_set_str (x, "1.25", 10, MPFR_RNDN); check_sprintf ("1.2", "%.1Rf", x); mpfr_set_str (x, "1.75", 10, MPFR_RNDN); check_sprintf ("1.8", "%.1Rf", x); mpfr_set_str (x, "1.5", 10, MPFR_RNDN); check_sprintf ("2", "%.1Rg", x); mpfr_set_str (x, "2.5", 10, MPFR_RNDN); check_sprintf ("2", "%.1Rg", x); mpfr_set_str (x, "9.25", 10, MPFR_RNDN); check_sprintf ("9.2", "%.2Rg", x); mpfr_set_str (x, "9.75", 10, MPFR_RNDN); check_sprintf ("9.8", "%.2Rg", x); /* assertion failure in r6320 */ mpfr_set_str (x, "-9.996", 10, MPFR_RNDN); check_sprintf ("-10.0", "%.1Rf", x); /* regression in MPFR 3.1.0 (bug introduced in r7761, fixed in r7931) */ check_sprintf ("-10", "%.2Rg", x); mpfr_clears (x, z, (mpfr_ptr) 0); return 0; }
/* hard test of rounding */ static void check_rounding (void) { mpfr_t a, b, c, res; mpfr_prec_t p; long k, l; int i; #define MAXKL (2 * GMP_NUMB_BITS) for (p = MPFR_PREC_MIN; p <= GMP_NUMB_BITS; p++) { mpfr_init2 (a, p); mpfr_init2 (res, p); mpfr_init2 (b, p + 1 + MAXKL); mpfr_init2 (c, MPFR_PREC_MIN); /* b = 2^p + 1 + 2^(-k), c = 2^(-l) */ for (k = 0; k <= MAXKL; k++) for (l = 0; l <= MAXKL; l++) { mpfr_set_ui_2exp (b, 1, p, MPFR_RNDN); mpfr_add_ui (b, b, 1, MPFR_RNDN); mpfr_mul_2ui (b, b, k, MPFR_RNDN); mpfr_add_ui (b, b, 1, MPFR_RNDN); mpfr_div_2ui (b, b, k, MPFR_RNDN); mpfr_set_ui_2exp (c, 1, -l, MPFR_RNDN); i = mpfr_sub (a, b, c, MPFR_RNDN); /* b - c = 2^p + 1 + 2^(-k) - 2^(-l), should be rounded to 2^p for l <= k, and 2^p+2 for l < k */ if (l <= k) { if (mpfr_cmp_ui_2exp (a, 1, p) != 0) { printf ("Wrong result in check_rounding\n"); printf ("p=%lu k=%ld l=%ld\n", p, k, l); printf ("b="); mpfr_print_binary (b); puts (""); printf ("c="); mpfr_print_binary (c); puts (""); printf ("Expected 2^%lu\n", p); printf ("Got "); mpfr_print_binary (a); puts (""); exit (1); } if (i >= 0) { printf ("Wrong ternary value in check_rounding\n"); printf ("p=%lu k=%ld l=%ld\n", p, k, l); printf ("b="); mpfr_print_binary (b); puts (""); printf ("c="); mpfr_print_binary (c); puts (""); printf ("a="); mpfr_print_binary (a); puts (""); printf ("Expected < 0, got %d\n", i); exit (1); } } else /* l < k */ { mpfr_set_ui_2exp (res, 1, p, MPFR_RNDN); mpfr_add_ui (res, res, 2, MPFR_RNDN); if (mpfr_cmp (a, res) != 0) { printf ("Wrong result in check_rounding\n"); printf ("b="); mpfr_print_binary (b); puts (""); printf ("c="); mpfr_print_binary (c); puts (""); printf ("Expected "); mpfr_print_binary (res); puts (""); printf ("Got "); mpfr_print_binary (a); puts (""); exit (1); } if (i <= 0) { printf ("Wrong ternary value in check_rounding\n"); printf ("b="); mpfr_print_binary (b); puts (""); printf ("c="); mpfr_print_binary (c); puts (""); printf ("Expected > 0, got %d\n", i); exit (1); } } } mpfr_clear (a); mpfr_clear (res); mpfr_clear (b); mpfr_clear (c); } }
static void special (void) { mpfr_t x, y; int i; mpfr_init (x); mpfr_init (y); /* root(NaN) = NaN */ mpfr_set_nan (x); mpfr_root (y, x, 17, GMP_RNDN); if (!mpfr_nan_p (y)) { printf ("Error: root(NaN,17) <> NaN\n"); exit (1); } /* root(+Inf) = +Inf */ mpfr_set_inf (x, 1); mpfr_root (y, x, 42, GMP_RNDN); if (!mpfr_inf_p (y) || mpfr_sgn (y) < 0) { printf ("Error: root(+Inf,42) <> +Inf\n"); exit (1); } /* root(-Inf, 17) = -Inf */ mpfr_set_inf (x, -1); mpfr_root (y, x, 17, GMP_RNDN); if (!mpfr_inf_p (y) || mpfr_sgn (y) > 0) { printf ("Error: root(-Inf,17) <> -Inf\n"); exit (1); } /* root(-Inf, 42) = NaN */ mpfr_set_inf (x, -1); mpfr_root (y, x, 42, GMP_RNDN); if (!mpfr_nan_p (y)) { printf ("Error: root(-Inf,42) <> -Inf\n"); exit (1); } /* root(+/-0) = +/-0 */ mpfr_set_ui (x, 0, GMP_RNDN); mpfr_root (y, x, 17, GMP_RNDN); if (mpfr_cmp_ui (y, 0) || mpfr_sgn (y) < 0) { printf ("Error: root(+0,17) <> +0\n"); exit (1); } mpfr_neg (x, x, GMP_RNDN); mpfr_root (y, x, 42, GMP_RNDN); if (mpfr_cmp_ui (y, 0) || mpfr_sgn (y) > 0) { printf ("Error: root(-0,42) <> -0\n"); exit (1); } mpfr_set_prec (x, 53); mpfr_set_str (x, "8.39005285514734966412e-01", 10, GMP_RNDN); mpfr_root (x, x, 3, GMP_RNDN); if (mpfr_cmp_str1 (x, "9.43166207799662426048e-01")) { printf ("Error in root3 (1)\n"); printf ("expected 9.43166207799662426048e-01\n"); printf ("got "); mpfr_dump (x); exit (1); } mpfr_set_prec (x, 32); mpfr_set_prec (y, 32); mpfr_set_str_binary (x, "0.10000100001100101001001001011001"); mpfr_root (x, x, 3, GMP_RNDN); mpfr_set_str_binary (y, "0.11001101011000100111000111111001"); if (mpfr_cmp (x, y)) { printf ("Error in root3 (2)\n"); exit (1); } mpfr_set_prec (x, 32); mpfr_set_prec (y, 32); mpfr_set_str_binary (x, "-0.1100001110110000010101011001011"); mpfr_root (x, x, 3, GMP_RNDD); mpfr_set_str_binary (y, "-0.11101010000100100101000101011001"); if (mpfr_cmp (x, y)) { printf ("Error in root3 (3)\n"); exit (1); } mpfr_set_prec (x, 82); mpfr_set_prec (y, 27); mpfr_set_str_binary (x, "0.1010001111011101011011000111001011001101100011110110010011011011011010011001100101e-7"); mpfr_root (y, x, 3, GMP_RNDD); mpfr_set_str_binary (x, "0.101011110001110001000100011E-2"); if (mpfr_cmp (x, y)) { printf ("Error in root3 (4)\n"); exit (1); } mpfr_set_prec (x, 204); mpfr_set_prec (y, 38); mpfr_set_str_binary (x, "0.101000000001101000000001100111111011111001110110100001111000100110100111001101100111110001110001011011010110010011100101111001111100001010010100111011101100000011011000101100010000000011000101001010001001E-5"); mpfr_root (y, x, 3, GMP_RNDD); mpfr_set_str_binary (x, "0.10001001111010011011101000010110110010E-1"); if (mpfr_cmp (x, y)) { printf ("Error in root3 (5)\n"); exit (1); } /* Worst case found on 2006-11-25 */ mpfr_set_prec (x, 53); mpfr_set_prec (y, 53); mpfr_set_str_binary (x, "1.0100001101101101001100110001001000000101001101100011E28"); mpfr_root (y, x, 35, GMP_RNDN); mpfr_set_str_binary (x, "1.1100000010110101100011101011000010100001101100100011E0"); if (mpfr_cmp (x, y)) { printf ("Error in mpfr_root (y, x, 35, GMP_RNDN) for\n" "x = 1.0100001101101101001100110001001000000101001101100011E28\n" "Expected "); mpfr_dump (x); printf ("Got "); mpfr_dump (y); exit (1); } /* Worst cases found on 2006-11-26 */ mpfr_set_str_binary (x, "1.1111010011101110001111010110000101110000110110101100E17"); mpfr_root (y, x, 36, GMP_RNDD); mpfr_set_str_binary (x, "1.0110100111010001101001010111001110010100111111000010E0"); if (mpfr_cmp (x, y)) { printf ("Error in mpfr_root (y, x, 36, GMP_RNDD) for\n" "x = 1.1111010011101110001111010110000101110000110110101100E17\n" "Expected "); mpfr_dump (x); printf ("Got "); mpfr_dump (y); exit (1); } mpfr_set_str_binary (x, "1.1100011101101101100010110001000001110001111110010000E23"); mpfr_root (y, x, 36, GMP_RNDU); mpfr_set_str_binary (x, "1.1001010100001110000110111111100011011101110011000100E0"); if (mpfr_cmp (x, y)) { printf ("Error in mpfr_root (y, x, 36, GMP_RNDU) for\n" "x = 1.1100011101101101100010110001000001110001111110010000E23\n" "Expected "); mpfr_dump (x); printf ("Got "); mpfr_dump (y); exit (1); } /* Check for k = 1 */ mpfr_set_ui (x, 17, GMP_RNDN); i = mpfr_root (y, x, 1, GMP_RNDN); if (mpfr_cmp_ui (x, 17) || i != 0) { printf ("Error in root (17^(1/1))\n"); exit (1); } #if 0 /* Check for k == 0: For 0 <= x < 1 => +0. For x = 1 => 1. For x > 1, => +Inf. For x < 0 => NaN. */ i = mpfr_root (y, x, 0, GMP_RNDN); if (!MPFR_IS_INF (y) || !MPFR_IS_POS (y) || i != 0) { printf ("Error in root 17^(1/0)\n"); exit (1); } mpfr_set_ui (x, 1, GMP_RNDN); i = mpfr_root (y, x, 0, GMP_RNDN); if (mpfr_cmp_ui (y, 1) || i != 0) { printf ("Error in root 1^(1/0)\n"); exit (1); } mpfr_set_ui (x, 0, GMP_RNDN); i = mpfr_root (y, x, 0, GMP_RNDN); if (!MPFR_IS_ZERO (y) || !MPFR_IS_POS (y) || i != 0) { printf ("Error in root 0+^(1/0)\n"); exit (1); } MPFR_CHANGE_SIGN (x); i = mpfr_root (y, x, 0, GMP_RNDN); if (!MPFR_IS_ZERO (y) || !MPFR_IS_POS (y) || i != 0) { printf ("Error in root 0-^(1/0)\n"); exit (1); } mpfr_set_ui_2exp (x, 17, -5, GMP_RNDD); i = mpfr_root (y, x, 0, GMP_RNDN); if (!MPFR_IS_ZERO (y) || !MPFR_IS_POS (y) || i != 0) { printf ("Error in root (17/2^5)^(1/0)\n"); exit (1); } #endif mpfr_set_ui (x, 0, GMP_RNDN); i = mpfr_root (y, x, 0, GMP_RNDN); if (!MPFR_IS_NAN (y) || i != 0) { printf ("Error in root 0+^(1/0)\n"); exit (1); } /* Check for k==2 */ mpfr_set_si (x, -17, GMP_RNDD); i = mpfr_root (y, x, 2, GMP_RNDN); if (!MPFR_IS_NAN (y) || i != 0) { printf ("Error in root (-17)^(1/2)\n"); exit (1); } mpfr_clear (x); mpfr_clear (y); }