Commit 2789efe3 by Steven G. Kargl

arith.c (arith_power): Rework overflow of an integer to an integer exponent.

2019-06-14  Steven G. Kargl  <kargl@gcc.gnu.org>

	* arith.c (arith_power): Rework overflow of an integer to an integer
	exponent.

2019-06-14  Steven G. Kargl  <kargl@gcc.gnu.org>

	* gfortran.dg/integer_exponentiation_4.f90: Update test.
	* gfortran.dg/integer_exponentiation_5.F90: Ditto.
	* gfortran.dg/no_range_check_1.f90: Ditto.

From-SVN: r272320
parent 4e20bd42
2019-06-14 Steven G. Kargl <kargl@gcc.gnu.org>
* arith.c (arith_power): Rework overflow of an integer to an integer
exponent.
2019-06-14 Harald Anlauf <anlauf@gmx.de> 2019-06-14 Harald Anlauf <anlauf@gmx.de>
PR fortran/90577 PR fortran/90577
......
...@@ -848,8 +848,6 @@ arith_power (gfc_expr *op1, gfc_expr *op2, gfc_expr **resultp) ...@@ -848,8 +848,6 @@ arith_power (gfc_expr *op1, gfc_expr *op2, gfc_expr **resultp)
{ {
case BT_INTEGER: case BT_INTEGER:
{ {
int power;
/* First, we simplify the cases of op1 == 1, 0 or -1. */ /* First, we simplify the cases of op1 == 1, 0 or -1. */
if (mpz_cmp_si (op1->value.integer, 1) == 0) if (mpz_cmp_si (op1->value.integer, 1) == 0)
{ {
...@@ -884,29 +882,36 @@ arith_power (gfc_expr *op1, gfc_expr *op2, gfc_expr **resultp) ...@@ -884,29 +882,36 @@ arith_power (gfc_expr *op1, gfc_expr *op2, gfc_expr **resultp)
"exponent of integer has zero " "exponent of integer has zero "
"result at %L", &result->where); "result at %L", &result->where);
} }
else if (gfc_extract_int (op2, &power)) else
{ {
/* If op2 doesn't fit in an int, the exponentiation will /* We have abs(op1) > 1 and op2 > 1.
overflow, because op2 > 0 and abs(op1) > 1. */ If op2 > bit_size(op1), we'll have an out-of-range
mpz_t max; result. */
int i; int k, power;
i = gfc_validate_kind (BT_INTEGER, result->ts.kind, false);
k = gfc_validate_kind (BT_INTEGER, op1->ts.kind, false);
if (flag_range_check) power = gfc_integer_kinds[k].bit_size;
rc = ARITH_OVERFLOW; if (mpz_cmp_si (op2->value.integer, power) < 0)
{
/* Still, we want to give the same value as the gfc_extract_int (op2, &power);
processor. */ mpz_pow_ui (result->value.integer, op1->value.integer,
mpz_init (max); power);
mpz_add_ui (max, gfc_integer_kinds[i].huge, 1); rc = gfc_range_check (result);
mpz_mul_ui (max, max, 2); if (rc == ARITH_OVERFLOW)
mpz_powm (result->value.integer, op1->value.integer, gfc_error_now ("Result of exponentiation at %L "
op2->value.integer, max); "exceeds the range of %s", &op1->where,
mpz_clear (max); gfc_typename (&(op1->ts)));
}
else
{
/* Provide a nonsense value to propagate up. */
mpz_set (result->value.integer,
gfc_integer_kinds[k].huge);
mpz_add_ui (result->value.integer,
result->value.integer, 1);
rc = ARITH_OVERFLOW;
}
} }
else
mpz_pow_ui (result->value.integer, op1->value.integer,
power);
} }
break; break;
......
2019-06-14 Steven G. Kargl <kargl@gcc.gnu.org>
* gfortran.dg/integer_exponentiation_4.f90: Update test.
* gfortran.dg/integer_exponentiation_5.F90: Ditto.
* gfortran.dg/no_range_check_1.f90: Ditto.
2019-06-14 Harald Anlauf <anlauf@gmx.de> 2019-06-14 Harald Anlauf <anlauf@gmx.de>
PR fortran/90577 PR fortran/90577
......
...@@ -21,10 +21,10 @@ program test ...@@ -21,10 +21,10 @@ program test
print *, (-1)**huge(0_8) print *, (-1)**huge(0_8)
print *, (-1)**(-huge(0_8)-1_8) print *, (-1)**(-huge(0_8)-1_8)
print *, 2**huge(0) ! { dg-error "Arithmetic overflow" } print *, 2**huge(0) ! { dg-error "Arithmetic overflow|exceeds the range" }
print *, 2**huge(0_8) ! { dg-error "Arithmetic overflow" } print *, 2**huge(0_8) ! { dg-error "Arithmetic overflow|exceeds the range" }
print *, (-2)**huge(0) ! { dg-error "Arithmetic overflow" } print *, (-2)**huge(0) ! { dg-error "Arithmetic overflow|exceeds the range" }
print *, (-2)**huge(0_8) ! { dg-error "Arithmetic overflow" } print *, (-2)**huge(0_8) ! { dg-error "Arithmetic overflow|exceeds the range" }
print *, 2**(-huge(0)-1) print *, 2**(-huge(0)-1)
print *, 2**(-huge(0_8)-1_8) print *, 2**(-huge(0_8)-1_8)
......
...@@ -67,8 +67,6 @@ program test ...@@ -67,8 +67,6 @@ program test
TEST(3_8,43_8,i8) TEST(3_8,43_8,i8)
TEST(-3_8,43_8,i8) TEST(-3_8,43_8,i8)
TEST(17_8,int(huge(0_4),kind=8)+1,i8)
!!!!! REAL BASE !!!!! !!!!! REAL BASE !!!!!
TEST(0.0,-1,r4) TEST(0.0,-1,r4)
TEST(0.0,-huge(0)-1,r4) TEST(0.0,-huge(0)-1,r4)
......
...@@ -4,11 +4,8 @@ ...@@ -4,11 +4,8 @@
! This testcase arose from PR 31262 ! This testcase arose from PR 31262
integer :: a integer :: a
integer(kind=8) :: b integer(kind=8) :: b
a = -3
b = -huge(b) / 7 b = -huge(b) / 7
a = a ** 73
b = 7894_8 * b - 78941_8 b = 7894_8 * b - 78941_8
if ((-3)**73 /= a) STOP 1
if (7894_8 * (-huge(b) / 7) - 78941_8 /= b) STOP 2 if (7894_8 * (-huge(b) / 7) - 78941_8 /= b) STOP 2
a = 1234789786453123 a = 1234789786453123
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment