From ad0e2567d69760fa7156ef24418b4d10f99def6a Mon Sep 17 00:00:00 2001 From: Richard Guenther Date: Tue, 26 Apr 2011 09:21:44 +0000 Subject: [PATCH] re PR tree-optimization/48694 (possible memory hog bug) 2011-04-26 Richard Guenther PR middle-end/48694 * tree.h (OEP_CONSTANT_ADDRESS_OF): New operand_equal_flag. * fold-const.c (operand_equal_p): For TREE_CONSTANT ADDR_EXPRs compare the operands with OEP_CONSTANT_ADDRESS_OF. Treat trees with TREE_SIDE_EFFECTS equal when OEP_CONSTANT_ADDRESS_OF is set. * gcc.dg/torture/pr48694-1.c: New testcase. * gcc.dg/torture/pr48694-2.c: Likewise. From-SVN: r172954 --- gcc/fold-const.c | 8 ++++++-- gcc/testsuite/ChangeLog | 6 ++++++ gcc/testsuite/gcc.dg/torture/pr48694-1.c | 14 ++++++++++++++ gcc/testsuite/gcc.dg/torture/pr48694-2.c | 20 ++++++++++++++++++++ gcc/tree.h | 3 ++- 5 files changed, 48 insertions(+), 3 deletions(-) create mode 100644 gcc/testsuite/gcc.dg/torture/pr48694-1.c create mode 100644 gcc/testsuite/gcc.dg/torture/pr48694-2.c diff --git a/gcc/fold-const.c b/gcc/fold-const.c index 8f90f6f108a..1aa0dec0011 100644 --- a/gcc/fold-const.c +++ b/gcc/fold-const.c @@ -2473,9 +2473,12 @@ operand_equal_p (const_tree arg0, const_tree arg1, unsigned int flags) equal if they have no side effects. If we have two identical expressions with side effects that should be treated the same due to the only side effects being identical SAVE_EXPR's, that will - be detected in the recursive calls below. */ + be detected in the recursive calls below. + If we are taking an invariant address of two identical objects + they are necessarily equal as well. */ if (arg0 == arg1 && ! (flags & OEP_ONLY_CONST) && (TREE_CODE (arg0) == SAVE_EXPR + || (flags & OEP_CONSTANT_ADDRESS_OF) || (! TREE_SIDE_EFFECTS (arg0) && ! TREE_SIDE_EFFECTS (arg1)))) return 1; @@ -2538,7 +2541,8 @@ operand_equal_p (const_tree arg0, const_tree arg1, unsigned int flags) case ADDR_EXPR: return operand_equal_p (TREE_OPERAND (arg0, 0), TREE_OPERAND (arg1, 0), - 0); + TREE_CONSTANT (arg0) && TREE_CONSTANT (arg1) + ? OEP_CONSTANT_ADDRESS_OF : 0); default: break; } diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index f464fa41619..5efb6b164b5 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,9 @@ +2011-04-26 Richard Guenther + + PR middle-end/48694 + * gcc.dg/torture/pr48694-1.c: New testcase. + * gcc.dg/torture/pr48694-2.c: Likewise. + 2011-04-25 Paolo Carlini * g++.dg/ext/underlying_type1.C: New. diff --git a/gcc/testsuite/gcc.dg/torture/pr48694-1.c b/gcc/testsuite/gcc.dg/torture/pr48694-1.c new file mode 100644 index 00000000000..810366bc8b4 --- /dev/null +++ b/gcc/testsuite/gcc.dg/torture/pr48694-1.c @@ -0,0 +1,14 @@ +/* { dg-do compile } */ + +extern volatile int g_89[5][9]; +extern int g, *gp; +void func_64() +{ + int i; + for (i = 0; i < 1; ) + { + for (g = 0; g < 1; ) + return; + gp = (int *)&g_89[g][0]; + } +} diff --git a/gcc/testsuite/gcc.dg/torture/pr48694-2.c b/gcc/testsuite/gcc.dg/torture/pr48694-2.c new file mode 100644 index 00000000000..4791ac3f70c --- /dev/null +++ b/gcc/testsuite/gcc.dg/torture/pr48694-2.c @@ -0,0 +1,20 @@ +/* { dg-do compile } */ + +extern volatile int g_4[1][4]; +extern int g_7; +void modify(int *); +void func_2() +{ + int l_46 = 4; + if (g_7) + modify(&l_46); + else + { + int i; + for (i = 0; i != 5; i += 1) + { + volatile int *vp = &g_4[0][l_46]; + *vp = 0; + } + } +} diff --git a/gcc/tree.h b/gcc/tree.h index 0bc98cd01b4..8f25832589f 100644 --- a/gcc/tree.h +++ b/gcc/tree.h @@ -5118,7 +5118,8 @@ extern tree fold_fma (location_t, tree, tree, tree, tree); enum operand_equal_flag { OEP_ONLY_CONST = 1, - OEP_PURE_SAME = 2 + OEP_PURE_SAME = 2, + OEP_CONSTANT_ADDRESS_OF = 4 }; extern int operand_equal_p (const_tree, const_tree, unsigned int); -- 2.30.2