re PR middle-end/26898 (Fold does not fold signed + CST1 CMP signed + CST2)
2006-10-21 Richard Guenther <rguenther@suse.de> PR middle-end/26898 * fold-const.c (fold_comparison): Fold signed comparisons of the form X +- C1 CMP Y +- C2. * gcc.dg/torture/pr26898-1.c: New testcase. * gcc.dg/torture/pr26898-2.c: Likewise. From-SVN: r117931
This commit is contained in:
parent
5a4171a01d
commit
8a1eca0803
5 changed files with 80 additions and 0 deletions
|
@ -1,3 +1,9 @@
|
|||
2006-10-21 Richard Guenther <rguenther@suse.de>
|
||||
|
||||
PR middle-end/26898
|
||||
* fold-const.c (fold_comparison): Fold signed comparisons
|
||||
of the form X +- C1 CMP Y +- C2.
|
||||
|
||||
2006-10-21 Richard Guenther <rguenther@suse.de>
|
||||
|
||||
PR target/19116
|
||||
|
|
|
@ -7835,6 +7835,48 @@ fold_comparison (enum tree_code code, tree type, tree op0, tree op1)
|
|||
}
|
||||
}
|
||||
|
||||
/* Transform comparisons of the form X +- C1 CMP Y +- C2 to
|
||||
X CMP Y +- C2 +- C1 for signed X, Y. This is valid if
|
||||
the resulting offset is smaller in absolute value than the
|
||||
original one. */
|
||||
if (!(flag_wrapv || flag_trapv)
|
||||
&& !TYPE_UNSIGNED (TREE_TYPE (arg0))
|
||||
&& (TREE_CODE (arg0) == PLUS_EXPR || TREE_CODE (arg0) == MINUS_EXPR)
|
||||
&& (TREE_CODE (TREE_OPERAND (arg0, 1)) == INTEGER_CST
|
||||
&& !TREE_OVERFLOW (TREE_OPERAND (arg0, 1)))
|
||||
&& (TREE_CODE (arg1) == PLUS_EXPR || TREE_CODE (arg1) == MINUS_EXPR)
|
||||
&& (TREE_CODE (TREE_OPERAND (arg1, 1)) == INTEGER_CST
|
||||
&& !TREE_OVERFLOW (TREE_OPERAND (arg1, 1))))
|
||||
{
|
||||
tree const1 = TREE_OPERAND (arg0, 1);
|
||||
tree const2 = TREE_OPERAND (arg1, 1);
|
||||
tree variable1 = TREE_OPERAND (arg0, 0);
|
||||
tree variable2 = TREE_OPERAND (arg1, 0);
|
||||
tree cst;
|
||||
|
||||
/* Put the constant on the side where it doesn't overflow and is
|
||||
of lower absolute value than before. */
|
||||
cst = int_const_binop (TREE_CODE (arg0) == TREE_CODE (arg1)
|
||||
? MINUS_EXPR : PLUS_EXPR,
|
||||
const2, const1, 0);
|
||||
if (!TREE_OVERFLOW (cst)
|
||||
&& tree_int_cst_compare (const2, cst) == tree_int_cst_sgn (const2))
|
||||
return fold_build2 (code, type,
|
||||
variable1,
|
||||
fold_build2 (TREE_CODE (arg1), TREE_TYPE (arg1),
|
||||
variable2, cst));
|
||||
|
||||
cst = int_const_binop (TREE_CODE (arg0) == TREE_CODE (arg1)
|
||||
? MINUS_EXPR : PLUS_EXPR,
|
||||
const1, const2, 0);
|
||||
if (!TREE_OVERFLOW (cst)
|
||||
&& tree_int_cst_compare (const1, cst) == tree_int_cst_sgn (const1))
|
||||
return fold_build2 (code, type,
|
||||
fold_build2 (TREE_CODE (arg0), TREE_TYPE (arg0),
|
||||
variable1, cst),
|
||||
variable2);
|
||||
}
|
||||
|
||||
if (FLOAT_TYPE_P (TREE_TYPE (arg0)))
|
||||
{
|
||||
tree targ0 = strip_float_extensions (arg0);
|
||||
|
|
|
@ -1,3 +1,9 @@
|
|||
2006-10-21 Richard Guenther <rguenther@suse.de>
|
||||
|
||||
PR middle-end/26898
|
||||
* gcc.dg/torture/pr26898-1.c: New testcase.
|
||||
* gcc.dg/torture/pr26898-2.c: Likewise.
|
||||
|
||||
2006-10-20 Lee Millward <lee.millward@codesourcery.com>
|
||||
|
||||
PR c++/28053
|
||||
|
|
14
gcc/testsuite/gcc.dg/torture/pr26898-1.c
Normal file
14
gcc/testsuite/gcc.dg/torture/pr26898-1.c
Normal file
|
@ -0,0 +1,14 @@
|
|||
/* { dg-do link } */
|
||||
|
||||
#include <limits.h>
|
||||
|
||||
extern void link_error(void);
|
||||
int main()
|
||||
{
|
||||
int i0, i1;
|
||||
if (!(i0 + 1 < i1 + 1 == i0 < i1))
|
||||
link_error ();
|
||||
if (!(i0 + INT_MIN < i1 - INT_MAX == i0 < i1 - -1))
|
||||
link_error ();
|
||||
return 0;
|
||||
}
|
12
gcc/testsuite/gcc.dg/torture/pr26898-2.c
Normal file
12
gcc/testsuite/gcc.dg/torture/pr26898-2.c
Normal file
|
@ -0,0 +1,12 @@
|
|||
/* { dg-do run } */
|
||||
|
||||
#include <limits.h>
|
||||
|
||||
int a = 0, b = INT_MAX - 1;
|
||||
extern void abort(void);
|
||||
int main()
|
||||
{
|
||||
if (a - 1 > b + 1)
|
||||
abort();
|
||||
return 0;
|
||||
}
|
Loading…
Add table
Reference in a new issue