aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRichard Guenther <rguenther@suse.de>2011-05-26 13:01:48 +0000
committerRichard Biener <rguenth@gcc.gnu.org>2011-05-26 13:01:48 +0000
commitac8e18759f24063961458ba1e94ca0bfa3138775 (patch)
tree6ba8d1096dc8083667067ab711fce8126259c02e
parent7e32e6521aa6f699ddc1a00af5f38ceae120cb17 (diff)
downloadgcc-ac8e18759f24063961458ba1e94ca0bfa3138775.zip
gcc-ac8e18759f24063961458ba1e94ca0bfa3138775.tar.gz
gcc-ac8e18759f24063961458ba1e94ca0bfa3138775.tar.bz2
re PR tree-optimization/48702 (optimization regression with gcc-4.6 on x86_64-unknown-linux-gnu)
2011-05-26 Richard Guenther <rguenther@suse.de> PR tree-optimization/48702 * tree-ssa-address.c (create_mem_ref_raw): Create MEM_REFs only when we know the base address is within bounds. * tree-ssa-alias.c (indirect_ref_may_alias_decl_p): Do not assume the base address of TARGET_MEM_REFs is in bounds. * gcc.dg/torture/pr48702.c: New testcase. From-SVN: r174282
-rw-r--r--gcc/ChangeLog8
-rw-r--r--gcc/testsuite/ChangeLog5
-rw-r--r--gcc/testsuite/gcc.dg/torture/pr48702.c47
-rw-r--r--gcc/tree-ssa-address.c7
-rw-r--r--gcc/tree-ssa-alias.c9
5 files changed, 70 insertions, 6 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index f4047ef..ed1dda3 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,11 @@
+2011-05-26 Richard Guenther <rguenther@suse.de>
+
+ PR tree-optimization/48702
+ * tree-ssa-address.c (create_mem_ref_raw): Create MEM_REFs
+ only when we know the base address is within bounds.
+ * tree-ssa-alias.c (indirect_ref_may_alias_decl_p): Do not
+ assume the base address of TARGET_MEM_REFs is in bounds.
+
2011-05-26 Rainer Orth <ro@CeBiTec.Uni-Bielefeld.DE>
PR target/49099
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index 5acf08e..089406d 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,8 @@
+2011-05-26 Richard Guenther <rguenther@suse.de>
+
+ PR tree-optimization/48702
+ * gcc.dg/torture/pr48702.c: New testcase.
+
2011-05-26 Rainer Orth <ro@CeBiTec.Uni-Bielefeld.DE>
PR gcov-profile/48845
diff --git a/gcc/testsuite/gcc.dg/torture/pr48702.c b/gcc/testsuite/gcc.dg/torture/pr48702.c
new file mode 100644
index 0000000..1ec371d
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/pr48702.c
@@ -0,0 +1,47 @@
+/* { dg-do run } */
+
+extern void abort (void);
+
+#define LEN 4
+
+static inline void unpack(int array[LEN])
+{
+ int ii, val;
+ val = 1;
+ for (ii = 0; ii < LEN; ii++) {
+ array[ii] = val % 2;
+ val = val / 2;
+ }
+}
+
+static inline int pack(int array[LEN])
+{
+ int ans, ii;
+ ans = 0;
+ for (ii = LEN-1; ii >= 0; ii--) {
+ ans = 2 * ans + array[ii];
+ }
+ return ans;
+}
+
+int __attribute__((noinline))
+foo()
+{
+ int temp, ans;
+ int array[LEN];
+ unpack(array);
+ temp = array[0];
+ array[0] = array[2];
+ array[2] = temp;
+ ans = pack(array);
+ return ans;
+}
+
+int main(void)
+{
+ int val;
+ val = foo();
+ if (val != 4)
+ abort ();
+ return 0;
+}
diff --git a/gcc/tree-ssa-address.c b/gcc/tree-ssa-address.c
index 07d1d4d..2e6eabc 100644
--- a/gcc/tree-ssa-address.c
+++ b/gcc/tree-ssa-address.c
@@ -361,8 +361,11 @@ create_mem_ref_raw (tree type, tree alias_ptr_type, struct mem_address *addr,
index2 = addr->base;
}
- /* If possible use a plain MEM_REF instead of a TARGET_MEM_REF. */
- if (alias_ptr_type
+ /* If possible use a plain MEM_REF instead of a TARGET_MEM_REF.
+ ??? As IVOPTs does not follow restrictions to where the base
+ pointer may point to create a MEM_REF only if we know that
+ base is valid. */
+ if (TREE_CODE (base) == ADDR_EXPR
&& (!index2 || integer_zerop (index2))
&& (!addr->index || integer_zerop (addr->index)))
return fold_build2 (MEM_REF, type, base, addr->offset);
diff --git a/gcc/tree-ssa-alias.c b/gcc/tree-ssa-alias.c
index 3656b39..02b3ca0 100644
--- a/gcc/tree-ssa-alias.c
+++ b/gcc/tree-ssa-alias.c
@@ -745,11 +745,12 @@ indirect_ref_may_alias_decl_p (tree ref1 ATTRIBUTE_UNUSED, tree base1,
the pointer access is beyond the extent of the variable access.
(the pointer base cannot validly point to an offset less than zero
of the variable).
- They also cannot alias if the pointer may not point to the decl. */
- if ((TREE_CODE (base1) != TARGET_MEM_REF
- || (!TMR_INDEX (base1) && !TMR_INDEX2 (base1)))
+ ??? IVOPTs creates bases that do not honor this restriction,
+ so do not apply this optimization for TARGET_MEM_REFs. */
+ if (TREE_CODE (base1) != TARGET_MEM_REF
&& !ranges_overlap_p (MAX (0, offset1p), -1, offset2p, max_size2))
return false;
+ /* They also cannot alias if the pointer may not point to the decl. */
if (!ptr_deref_may_alias_decl_p (ptr1, base2))
return false;
@@ -799,7 +800,7 @@ indirect_ref_may_alias_decl_p (tree ref1 ATTRIBUTE_UNUSED, tree base1,
if (!ref2)
return true;
- /* If the decl is accressed via a MEM_REF, reconstruct the base
+ /* If the decl is accessed via a MEM_REF, reconstruct the base
we can use for TBAA and an appropriately adjusted offset. */
dbase2 = ref2;
while (handled_component_p (dbase2))