mirror of
git://gcc.gnu.org/git/gcc.git
synced 2025-02-24 16:56:02 +08:00
re PR tree-optimization/26180 (wrong code due to VRP and unsigned multiplies with wraps)
PR 26180 * tree-vrp.c (vrp_int_const_binop): Detect overflow when multiplying unsigned values. Tidy comments. testsuite PR 26180 * gcc.dg/tree-ssa/pr26180.c: New test. From-SVN: r110794
This commit is contained in:
parent
e10fbf9639
commit
7dc32197a8
@ -1,3 +1,10 @@
|
||||
2006-02-09 Diego Novillo <dnovillo@redhat.com>
|
||||
|
||||
PR 26180
|
||||
* tree-vrp.c (vrp_int_const_binop): Detect overflow when
|
||||
multiplying unsigned values.
|
||||
Tidy comments.
|
||||
|
||||
2006-02-09 Eric Botcazou <ebotcazou@libertysurf.fr>
|
||||
|
||||
* config/sparc/sparc.c (tls_call_delay): Fix oversight.
|
||||
|
@ -1,3 +1,8 @@
|
||||
2006-02-09 Diego Novillo <dnovillo@redhat.com>
|
||||
|
||||
PR 26180
|
||||
* gcc.dg/tree-ssa/pr26180.c: New test.
|
||||
|
||||
2006-02-08 Jeff Law <law@redhat.com>
|
||||
|
||||
* gcc.dg/tree-ssa/pr21417.c: New test.
|
||||
|
43
gcc/testsuite/gcc.dg/tree-ssa/pr26180.c
Normal file
43
gcc/testsuite/gcc.dg/tree-ssa/pr26180.c
Normal file
@ -0,0 +1,43 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2" } */
|
||||
|
||||
void abort(void);
|
||||
int bar(int x, int y)
|
||||
{
|
||||
int x1, y1;
|
||||
int x2, y2;
|
||||
unsigned int x3, y3, w;
|
||||
int z = 1;
|
||||
|
||||
x1 = (x < (1 << 30));
|
||||
y1 = (y < (1 << 30));
|
||||
if (x1)
|
||||
if (y1) {
|
||||
x2 = ((x > 0)? (x): -(x));
|
||||
y2 = ((y > 0)? (y): -(y));
|
||||
|
||||
x3 = x2;
|
||||
y3 = y2;
|
||||
w = x3 * y3;
|
||||
|
||||
if (w >= (1 << 30)) {
|
||||
z = 1;
|
||||
} else {
|
||||
z = -1;
|
||||
}
|
||||
}
|
||||
|
||||
return z;
|
||||
}
|
||||
|
||||
|
||||
int main()
|
||||
{
|
||||
int x, y, z;
|
||||
x = 536870912; /* 2^29 */
|
||||
y = 2;
|
||||
z = bar(x, y);
|
||||
if (z != 1)
|
||||
abort ();
|
||||
return 0;
|
||||
}
|
@ -1191,22 +1191,24 @@ vrp_int_const_binop (enum tree_code code, tree val1, tree val2)
|
||||
{
|
||||
int checkz = compare_values (res, val1);
|
||||
|
||||
/* Ensure that res = val1 + val2 >= val1
|
||||
/* Ensure that res = val1 [+*] val2 >= val1
|
||||
or that res = val1 - val2 <= val1. */
|
||||
if ((code == PLUS_EXPR && !(checkz == 1 || checkz == 0))
|
||||
|| (code == MINUS_EXPR && !(checkz == 0 || checkz == -1)))
|
||||
if (((code == PLUS_EXPR || code == MULT_EXPR)
|
||||
&& !(checkz == 1 || checkz == 0))
|
||||
|| (code == MINUS_EXPR
|
||||
&& !(checkz == 0 || checkz == -1)))
|
||||
{
|
||||
res = copy_node (res);
|
||||
TREE_OVERFLOW (res) = 1;
|
||||
}
|
||||
}
|
||||
/* If the operation overflowed but neither VAL1 nor VAL2 are
|
||||
overflown, return -INF or +INF depending on the operation
|
||||
and the combination of signs of the operands. */
|
||||
else if (TREE_OVERFLOW (res)
|
||||
&& !TREE_OVERFLOW (val1)
|
||||
&& !TREE_OVERFLOW (val2))
|
||||
{
|
||||
/* If the operation overflowed but neither VAL1 nor VAL2 are
|
||||
overflown, return -INF or +INF depending on the operation
|
||||
and the combination of signs of the operands. */
|
||||
int sgn1 = tree_int_cst_sgn (val1);
|
||||
int sgn2 = tree_int_cst_sgn (val2);
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user