From 2460d3aa21f04cdf28497683bd3e29183189f779 Mon Sep 17 00:00:00 2001 From: Joseph Myers Date: Wed, 21 Mar 2012 12:14:57 +0000 Subject: Fix pow of zero and infinity to large powers. --- math/libm-test.inc | 207 +++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 207 insertions(+) (limited to 'math') diff --git a/math/libm-test.inc b/math/libm-test.inc index af3d645..64d12a5 100644 --- a/math/libm-test.inc +++ b/math/libm-test.inc @@ -5431,11 +5431,75 @@ pow_test (void) TEST_ff_f (pow, 0, -11, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); check_int ("errno for pow(0,-odd) == ERANGE", errno, ERANGE, 0, 0, 0); errno = 0; + TEST_ff_f (pow, 0, -0xffffff, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(0,-odd) == ERANGE", errno, ERANGE, 0, 0, 0); +#ifndef TEST_FLOAT + errno = 0; + TEST_ff_f (pow, 0, -0x1.fffffffffffffp+52L, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(0,-odd) == ERANGE", errno, ERANGE, 0, 0, 0); +#endif +#ifdef TEST_LDOUBLE +# if LDBL_MANT_DIG >= 64 + errno = 0; + TEST_ff_f (pow, 0, -0x1.fffffffffffffffep+63L, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(0,-odd) == ERANGE", errno, ERANGE, 0, 0, 0); +# endif +# if LDBL_MANT_DIG >= 106 + errno = 0; + TEST_ff_f (pow, 0, -0x1.ffffffffffffffffffffffffff8p+105L, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(0,-odd) == ERANGE", errno, ERANGE, 0, 0, 0); +# endif +# if LDBL_MANT_DIG >= 113 + errno = 0; + TEST_ff_f (pow, 0, -0x1.ffffffffffffffffffffffffffffp+112L, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(0,-odd) == ERANGE", errno, ERANGE, 0, 0, 0); +# endif +#endif TEST_ff_f (pow, minus_zero, -1, minus_infty, DIVIDE_BY_ZERO_EXCEPTION); check_int ("errno for pow(-0,-odd) == ERANGE", errno, ERANGE, 0, 0, 0); errno = 0; TEST_ff_f (pow, minus_zero, -11L, minus_infty, DIVIDE_BY_ZERO_EXCEPTION); check_int ("errno for pow(-0,-odd) == ERANGE", errno, ERANGE, 0, 0, 0); + errno = 0; + TEST_ff_f (pow, minus_zero, -0xffffff, minus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(-0,-odd) == ERANGE", errno, ERANGE, 0, 0, 0); + errno = 0; + TEST_ff_f (pow, minus_zero, -0x1fffffe, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(-0,-even) == ERANGE", errno, ERANGE, 0, 0, 0); +#ifndef TEST_FLOAT + errno = 0; + TEST_ff_f (pow, minus_zero, -0x1.fffffffffffffp+52L, minus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(-0,-odd) == ERANGE", errno, ERANGE, 0, 0, 0); + errno = 0; + TEST_ff_f (pow, minus_zero, -0x1.fffffffffffffp+53L, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(-0,-even) == ERANGE", errno, ERANGE, 0, 0, 0); +#endif +#ifdef TEST_LDOUBLE +# if LDBL_MANT_DIG >= 64 + errno = 0; + TEST_ff_f (pow, minus_zero, -0x1.fffffffffffffffep+63L, minus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(-0,-odd) == ERANGE", errno, ERANGE, 0, 0, 0); + errno = 0; + TEST_ff_f (pow, minus_zero, -0x1.fffffffffffffffep+64L, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(-0,-even) == ERANGE", errno, ERANGE, 0, 0, 0); +# endif +# if LDBL_MANT_DIG >= 106 + errno = 0; + TEST_ff_f (pow, minus_zero, -0x1.ffffffffffffffffffffffffff8p+105L, minus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(-0,-odd) == ERANGE", errno, ERANGE, 0, 0, 0); + errno = 0; + TEST_ff_f (pow, minus_zero, -0x1.ffffffffffffffffffffffffff8p+106L, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(-0,-even) == ERANGE", errno, ERANGE, 0, 0, 0); +# endif +# if LDBL_MANT_DIG >= 113 + errno = 0; + TEST_ff_f (pow, minus_zero, -0x1.ffffffffffffffffffffffffffffp+112L, minus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(-0,-odd) == ERANGE", errno, ERANGE, 0, 0, 0); + errno = 0; + TEST_ff_f (pow, minus_zero, -0x1.ffffffffffffffffffffffffffffp+113L, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(-0,-even) == ERANGE", errno, ERANGE, 0, 0, 0); +# endif +#endif errno = 0; TEST_ff_f (pow, 0, -2, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); @@ -5444,11 +5508,31 @@ pow_test (void) TEST_ff_f (pow, 0, -11.1L, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); check_int ("errno for pow(0,-num) == ERANGE", errno, ERANGE, 0, 0, 0); errno = 0; + TEST_ff_f (pow, 0, -0x1p24, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(0,-num) == ERANGE", errno, ERANGE, 0, 0, 0); + errno = 0; + TEST_ff_f (pow, 0, -0x1p127, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(0,-num) == ERANGE", errno, ERANGE, 0, 0, 0); + errno = 0; + /* Bug 13879: spurious OVERFLOW exception may be present. */ + TEST_ff_f (pow, 0, -max_value, plus_infty, DIVIDE_BY_ZERO_EXCEPTION|OVERFLOW_EXCEPTION_OK); + check_int ("errno for pow(0,-num) == ERANGE", errno, ERANGE, 0, 0, 0); + errno = 0; TEST_ff_f (pow, minus_zero, -2, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); check_int ("errno for pow(-0,-even) == ERANGE", errno, ERANGE, 0, 0, 0); errno = 0; TEST_ff_f (pow, minus_zero, -11.1L, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); check_int ("errno for pow(-0,-num) == ERANGE", errno, ERANGE, 0, 0, 0); + errno = 0; + TEST_ff_f (pow, minus_zero, -0x1p24, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(-0,-num) == ERANGE", errno, ERANGE, 0, 0, 0); + errno = 0; + TEST_ff_f (pow, minus_zero, -0x1p127, plus_infty, DIVIDE_BY_ZERO_EXCEPTION); + check_int ("errno for pow(-0,-num) == ERANGE", errno, ERANGE, 0, 0, 0); + errno = 0; + /* Bug 13879: spurious OVERFLOW exception may be present. */ + TEST_ff_f (pow, minus_zero, -max_value, plus_infty, DIVIDE_BY_ZERO_EXCEPTION|OVERFLOW_EXCEPTION_OK); + check_int ("errno for pow(-0,-num) == ERANGE", errno, ERANGE, 0, 0, 0); TEST_ff_f (pow, 0x1p72L, 0x1p72L, plus_infty, OVERFLOW_EXCEPTION); TEST_ff_f (pow, 10, -0x1p72L, 0); @@ -5487,32 +5571,155 @@ pow_test (void) /* pow (+inf, y) == +inf for y > 0. */ TEST_ff_f (pow, plus_infty, 2, plus_infty); + TEST_ff_f (pow, plus_infty, 0xffffff, plus_infty); +#ifndef TEST_FLOAT + TEST_ff_f (pow, plus_infty, 0x1.fffffffffffffp+52L, plus_infty); +#endif +#ifdef TEST_LDOUBLE +# if LDBL_MANT_DIG >= 64 + TEST_ff_f (pow, plus_infty, 0x1.fffffffffffffffep+63L, plus_infty); +# endif +# if LDBL_MANT_DIG >= 106 + TEST_ff_f (pow, plus_infty, 0x1.ffffffffffffffffffffffffff8p+105L, plus_infty); +# endif +# if LDBL_MANT_DIG >= 113 + TEST_ff_f (pow, plus_infty, 0x1.ffffffffffffffffffffffffffffp+112L, plus_infty); +# endif +#endif + TEST_ff_f (pow, plus_infty, 0x1p24, plus_infty); + TEST_ff_f (pow, plus_infty, 0x1p127, plus_infty); + TEST_ff_f (pow, plus_infty, max_value, plus_infty); /* pow (+inf, y) == +0 for y < 0. */ TEST_ff_f (pow, plus_infty, -1, 0.0); + TEST_ff_f (pow, plus_infty, -0xffffff, 0.0); +#ifndef TEST_FLOAT + TEST_ff_f (pow, plus_infty, -0x1.fffffffffffffp+52L, 0.0); +#endif +#ifdef TEST_LDOUBLE +# if LDBL_MANT_DIG >= 64 + TEST_ff_f (pow, plus_infty, -0x1.fffffffffffffffep+63L, 0.0); +# endif +# if LDBL_MANT_DIG >= 106 + TEST_ff_f (pow, plus_infty, -0x1.ffffffffffffffffffffffffff8p+105L, 0.0); +# endif +# if LDBL_MANT_DIG >= 113 + TEST_ff_f (pow, plus_infty, -0x1.ffffffffffffffffffffffffffffp+112L, 0.0); +# endif +#endif + TEST_ff_f (pow, plus_infty, -0x1p24, 0.0); + TEST_ff_f (pow, plus_infty, -0x1p127, 0.0); + TEST_ff_f (pow, plus_infty, -max_value, 0.0); /* pow (-inf, y) == -inf for y an odd integer > 0. */ TEST_ff_f (pow, minus_infty, 27, minus_infty); + TEST_ff_f (pow, minus_infty, 0xffffff, minus_infty); + TEST_ff_f (pow, minus_infty, 0x1fffffe, plus_infty); +#ifndef TEST_FLOAT + TEST_ff_f (pow, minus_infty, 0x1.fffffffffffffp+52L, minus_infty); + TEST_ff_f (pow, minus_infty, 0x1.fffffffffffffp+53L, plus_infty); +#endif +#ifdef TEST_LDOUBLE +# if LDBL_MANT_DIG >= 64 + TEST_ff_f (pow, minus_infty, 0x1.fffffffffffffffep+63L, minus_infty); + TEST_ff_f (pow, minus_infty, 0x1.fffffffffffffffep+64L, plus_infty); +# endif +# if LDBL_MANT_DIG >= 106 + TEST_ff_f (pow, minus_infty, 0x1.ffffffffffffffffffffffffff8p+105L, minus_infty); + TEST_ff_f (pow, minus_infty, 0x1.ffffffffffffffffffffffffff8p+106L, plus_infty); +# endif +# if LDBL_MANT_DIG >= 113 + TEST_ff_f (pow, minus_infty, 0x1.ffffffffffffffffffffffffffffp+112L, minus_infty); + TEST_ff_f (pow, minus_infty, 0x1.ffffffffffffffffffffffffffffp+113L, plus_infty); +# endif +#endif /* pow (-inf, y) == +inf for y > 0 and not an odd integer. */ TEST_ff_f (pow, minus_infty, 28, plus_infty); + TEST_ff_f (pow, minus_infty, 0x1p24, plus_infty); + TEST_ff_f (pow, minus_infty, 0x1p127, plus_infty); + TEST_ff_f (pow, minus_infty, max_value, plus_infty); /* pow (-inf, y) == -0 for y an odd integer < 0. */ TEST_ff_f (pow, minus_infty, -3, minus_zero); + TEST_ff_f (pow, minus_infty, -0xffffff, minus_zero); + TEST_ff_f (pow, minus_infty, -0x1fffffe, plus_zero); +#ifndef TEST_FLOAT + TEST_ff_f (pow, minus_infty, -0x1.fffffffffffffp+52L, minus_zero); + TEST_ff_f (pow, minus_infty, -0x1.fffffffffffffp+53L, plus_zero); +#endif +#ifdef TEST_LDOUBLE +# if LDBL_MANT_DIG >= 64 + TEST_ff_f (pow, minus_infty, -0x1.fffffffffffffffep+63L, minus_zero); + TEST_ff_f (pow, minus_infty, -0x1.fffffffffffffffep+64L, plus_zero); +# endif +# if LDBL_MANT_DIG >= 106 + TEST_ff_f (pow, minus_infty, -0x1.ffffffffffffffffffffffffff8p+105L, minus_zero); + TEST_ff_f (pow, minus_infty, -0x1.ffffffffffffffffffffffffff8p+106L, plus_zero); +# endif +# if LDBL_MANT_DIG >= 113 + TEST_ff_f (pow, minus_infty, -0x1.ffffffffffffffffffffffffffffp+112L, minus_zero); + TEST_ff_f (pow, minus_infty, -0x1.ffffffffffffffffffffffffffffp+113L, plus_zero); +# endif +#endif /* pow (-inf, y) == +0 for y < 0 and not an odd integer. */ TEST_ff_f (pow, minus_infty, -2.0, 0.0); + TEST_ff_f (pow, minus_infty, -0x1p24, 0.0); + TEST_ff_f (pow, minus_infty, -0x1p127, 0.0); + TEST_ff_f (pow, minus_infty, -max_value, 0.0); /* pow (+0, y) == +0 for y an odd integer > 0. */ TEST_ff_f (pow, 0.0, 27, 0.0); + TEST_ff_f (pow, 0.0, 0xffffff, 0.0); +#ifndef TEST_FLOAT + TEST_ff_f (pow, 0.0, 0x1.fffffffffffffp+52L, 0.0); +#endif +#ifdef TEST_LDOUBLE +# if LDBL_MANT_DIG >= 64 + TEST_ff_f (pow, 0.0, 0x1.fffffffffffffffep+63L, 0.0); +# endif +# if LDBL_MANT_DIG >= 106 + TEST_ff_f (pow, 0.0, 0x1.ffffffffffffffffffffffffff8p+105L, 0.0); +# endif +# if LDBL_MANT_DIG >= 113 + TEST_ff_f (pow, 0.0, 0x1.ffffffffffffffffffffffffffffp+112L, 0.0); +# endif +#endif /* pow (-0, y) == -0 for y an odd integer > 0. */ TEST_ff_f (pow, minus_zero, 27, minus_zero); + TEST_ff_f (pow, minus_zero, 0xffffff, minus_zero); + TEST_ff_f (pow, minus_zero, 0x1fffffe, plus_zero); +#ifndef TEST_FLOAT + TEST_ff_f (pow, minus_zero, 0x1.fffffffffffffp+52L, minus_zero); + TEST_ff_f (pow, minus_zero, 0x1.fffffffffffffp+53L, plus_zero); +#endif +#ifdef TEST_LDOUBLE +# if LDBL_MANT_DIG >= 64 + TEST_ff_f (pow, minus_zero, 0x1.fffffffffffffffep+63L, minus_zero); + TEST_ff_f (pow, minus_zero, 0x1.fffffffffffffffep+64L, plus_zero); +# endif +# if LDBL_MANT_DIG >= 106 + TEST_ff_f (pow, minus_zero, 0x1.ffffffffffffffffffffffffff8p+105L, minus_zero); + TEST_ff_f (pow, minus_zero, 0x1.ffffffffffffffffffffffffff8p+106L, plus_zero); +# endif +# if LDBL_MANT_DIG >= 113 + TEST_ff_f (pow, minus_zero, 0x1.ffffffffffffffffffffffffffffp+112L, minus_zero); + TEST_ff_f (pow, minus_zero, 0x1.ffffffffffffffffffffffffffffp+113L, plus_zero); +# endif +#endif /* pow (+0, y) == +0 for y > 0 and not an odd integer. */ TEST_ff_f (pow, 0.0, 4, 0.0); + TEST_ff_f (pow, 0.0, 0x1p24, 0.0); + TEST_ff_f (pow, 0.0, 0x1p127, 0.0); + TEST_ff_f (pow, 0.0, max_value, 0.0); /* pow (-0, y) == +0 for y > 0 and not an odd integer. */ TEST_ff_f (pow, minus_zero, 4, 0.0); + TEST_ff_f (pow, minus_zero, 0x1p24, 0.0); + TEST_ff_f (pow, minus_zero, 0x1p127, 0.0); + TEST_ff_f (pow, minus_zero, max_value, 0.0); TEST_ff_f (pow, 16, 0.25L, 2); TEST_ff_f (pow, 0x1p64L, 0.125L, 256); -- cgit v1.1