diff options
author | vlefevre <vlefevre@280ebfd0-de03-0410-8827-d642c229c3f4> | 2018-04-26 13:13:57 +0000 |
---|---|---|
committer | vlefevre <vlefevre@280ebfd0-de03-0410-8827-d642c229c3f4> | 2018-04-26 13:13:57 +0000 |
commit | 9b6f4ff7400be62af83e94a365068435d30dbd5b (patch) | |
tree | 0a2a5c68f84b35c0ef2341ed9a1189cd219fd807 /tests/tpow.c | |
parent | 4756a58263c4f3a7b80531293a668642e4c5be87 (diff) | |
download | mpfr-9b6f4ff7400be62af83e94a365068435d30dbd5b.tar.gz |
Merged recent tests from the trunk (r12500-12555,12558,12561).
git-svn-id: svn://scm.gforge.inria.fr/svn/mpfr/branches/4.0@12675 280ebfd0-de03-0410-8827-d642c229c3f4
Diffstat (limited to 'tests/tpow.c')
-rw-r--r-- | tests/tpow.c | 116 |
1 files changed, 116 insertions, 0 deletions
diff --git a/tests/tpow.c b/tests/tpow.c index 10eddbe95..e4f896440 100644 --- a/tests/tpow.c +++ b/tests/tpow.c @@ -1599,6 +1599,121 @@ tst20140422 (void) mpfr_clears (x, y, z1, z2, (mpfr_ptr) 0); } +static void +coverage (void) +{ + mpfr_t x, y, z, t, u; + mpfr_exp_t emin; + int inex; + int i; + + /* check a corner case with prec(z)=1 */ + mpfr_init2 (x, 2); + mpfr_init2 (y, 8); + mpfr_init2 (z, 1); + mpfr_set_ui_2exp (x, 3, -2, MPFR_RNDN); /* x = 3/4 */ + emin = mpfr_get_emin (); + mpfr_set_emin (-40); + mpfr_set_ui_2exp (y, 199, -1, MPFR_RNDN); /* y = 99.5 */ + /* x^y ~ 0.81*2^-41 */ + mpfr_clear_underflow (); + inex = mpfr_pow (z, x, y, MPFR_RNDN); + MPFR_ASSERTN(inex > 0); + MPFR_ASSERTN(mpfr_cmp_ui_2exp (z, 1, -41) == 0); + /* there should be no underflow, since with unbounded exponent range, + and a precision of 1 bit, x^y is rounded to 1.0*2^-41 */ + MPFR_ASSERTN(!mpfr_underflow_p ()); + mpfr_set_ui_2exp (y, 201, -1, MPFR_RNDN); /* y = 100.5 */ + /* x^y ~ 0.61*2^-41 */ + mpfr_clear_underflow (); + inex = mpfr_pow (z, x, y, MPFR_RNDN); + MPFR_ASSERTN(inex > 0); + MPFR_ASSERTN(mpfr_cmp_ui_2exp (z, 1, -41) == 0); + /* there should be an underflow, since with unbounded exponent range, + and a precision of 1 bit, x^y is rounded to 0.5*2^-41 */ + MPFR_ASSERTN(mpfr_underflow_p ()); + mpfr_set_ui_2exp (y, 203, -1, MPFR_RNDN); /* y = 101.5 */ + /* x^y ~ 0.46*2^-41 */ + mpfr_clear_underflow (); + inex = mpfr_pow (z, x, y, MPFR_RNDN); + MPFR_ASSERTN(inex < 0); + MPFR_ASSERTN(mpfr_zero_p (z) && mpfr_signbit (z) == 0); + MPFR_ASSERTN(mpfr_underflow_p ()); + mpfr_clears (x, y, z, (mpfr_ptr) 0); + mpfr_set_emin (emin); + + /* test for x = -2, y an odd integer with EXP(y) > i */ + mpfr_inits2 (10, t, u, (mpfr_ptr) 0); + mpfr_set_ui_2exp (t, 1, 1UL << 8, MPFR_RNDN); + for (i = 8; i <= 300; i++) + { + mpfr_flags_t flags, flags_u; + int inex_u; + + mpfr_mul_si (u, t, -2, MPFR_RNDN); /* u = (-2)^(2^i + 1) */ + mpfr_init2 (x, 10); + mpfr_init2 (y, i+1); + mpfr_init2 (z, 10); + mpfr_set_si (x, -2, MPFR_RNDN); + mpfr_set_ui_2exp (y, 1, i, MPFR_RNDN); + mpfr_nextabove (y); /* y = 2^i + 1 */ + if (MPFR_IS_INF (u)) + { + inex_u = -1; + flags_u = MPFR_FLAGS_OVERFLOW | MPFR_FLAGS_INEXACT; + } + else + { + inex_u = 0; + flags_u = 0; + } + mpfr_clear_flags (); + inex = mpfr_pow (z, x, y, MPFR_RNDN); + flags = __gmpfr_flags; + if (mpfr_cmp0 (z, u) != 0 || + ! SAME_SIGN (inex, inex_u) || + flags != flags_u) + { + printf ("Error in coverage for (-2)^(2^%d + 1):\n", i); + printf ("Expected "); + mpfr_dump (u); + printf (" with inex = %d and flags:", inex_u); + flags_out (flags_u); + printf ("Got "); + mpfr_dump (z); + printf (" with inex = %d and flags:", inex); + flags_out (flags); + exit (1); + } + mpfr_sqr (t, t, MPFR_RNDN); + mpfr_clears (x, y, z, (mpfr_ptr) 0); + } + mpfr_clears (t, u, (mpfr_ptr) 0); + +#if _MPFR_EXP_FORMAT >= 3 && _MPFR_PREC_FORMAT == 3 && MPFR_PREC_BITS == 64 + /* thus an unsigned long has at least 64 bits and x will be finite */ + { + mpfr_exp_t emax; + + emax = mpfr_get_emax (); + mpfr_set_emax ((1UL << 62) - 1); + /* emax = 4611686018427387903 on a 64-bit machine */ + mpfr_init2 (x, 65); + mpfr_init2 (y, 65); + mpfr_init2 (z, 64); + mpfr_set_ui_2exp (x, 512, 3074457345618258593UL, MPFR_RNDN); + mpfr_nextbelow (x); + mpfr_set_str_binary (y, "1.1"); /* y = 3/2 */ + mpfr_nextabove (y); + inex = mpfr_pow (z, x, y, MPFR_RNDN); + MPFR_ASSERTN(inex > 0); + MPFR_ASSERTN(mpfr_inf_p (z)); + mpfr_clears (x, y, z, (mpfr_ptr) 0); + mpfr_set_emax (emax); + } +#endif +} + int main (int argc, char **argv) { @@ -1606,6 +1721,7 @@ main (int argc, char **argv) tests_start_mpfr (); + coverage (); bug20071127 (); special (); particular_cases (); |