[Bug tree-optimization/45978] [4.6 Regression] bogus "array subscript is above array bounds" warning in extremely simple code with no loops
rguenth at gcc dot gnu.org
gcc-bugzilla@gcc.gnu.org
Tue Feb 8 13:39:00 GMT 2011
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=45978
Richard Guenther <rguenth at gcc dot gnu.org> changed:
What |Removed |Added
----------------------------------------------------------------------------
Priority|P3 |P2
--- Comment #3 from Richard Guenther <rguenth at gcc dot gnu.org> 2011-02-08 13:37:48 UTC ---
Something like
Index: gimple-fold.c
===================================================================
--- gimple-fold.c (revision 169917)
+++ gimple-fold.c (working copy)
@@ -212,6 +212,7 @@ maybe_fold_offset_to_array_ref (location
tree min_idx, idx, idx_type, elt_offset = integer_zero_node;
tree array_type, elt_type, elt_size;
tree domain_type;
+ tree no_warning = false;
/* If BASE is an ARRAY_REF, we can pick up another offset (this time
measured in units of the size of elements type) from that ARRAY_REF).
@@ -308,26 +309,34 @@ maybe_fold_offset_to_array_ref (location
char *(c[4]);
c[3][2];
should not be simplified into (*c)[14] or tree-vrp will
- give false warnings.
- This is only an issue for multi-dimensional arrays. */
- if (TREE_CODE (elt_type) == ARRAY_TYPE
- && domain_type)
+ give false warnings. For multi-dimensional arrays
+ avoid this transformation, for one-dimensional arrays
+ set TREE_NO_WARNING on out-of-bound references. */
+ if (domain_type)
{
+ bool oob = false;
if (TYPE_MAX_VALUE (domain_type)
&& TREE_CODE (TYPE_MAX_VALUE (domain_type)) == INTEGER_CST
&& tree_int_cst_lt (TYPE_MAX_VALUE (domain_type), idx))
- return NULL_TREE;
+ oob = true;
else if (TYPE_MIN_VALUE (domain_type)
&& TREE_CODE (TYPE_MIN_VALUE (domain_type)) == INTEGER_CST
&& tree_int_cst_lt (idx, TYPE_MIN_VALUE (domain_type)))
- return NULL_TREE;
+ oob = true;
else if (compare_tree_int (idx, 0) < 0)
+ oob = true;
+ if (oob)
+ {
+ if (TREE_CODE (elt_type) == ARRAY_TYPE)
return NULL_TREE;
+ no_warning = true;
+ }
}
{
tree t = build4 (ARRAY_REF, elt_type, base, idx, NULL_TREE, NULL_TREE);
SET_EXPR_LOCATION (t, loc);
+ TREE_NO_WARNING (t) = no_warning;
return t;
}
}
fixes this but will cause us to omit all warnings for C array accesses
that are out-of-bounds:
FAIL: gcc.dg/Warray-bounds.c (test for warnings, line 59)
FAIL: gcc.dg/Warray-bounds.c (test for warnings, line 60)
FAIL: gcc.dg/Warray-bounds.c (test for warnings, line 65)
FAIL: gcc.dg/Warray-bounds.c (test for warnings, line 66)
FAIL: gcc.dg/Warray-bounds.c (test for warnings, line 72)
FAIL: gcc.dg/Warray-bounds.c (test for warnings, line 73)
In general I'd say we should not warn from VRP after loop opts, and
for address-taking operations we should have a distinct warning,
eventually looking at object sizes, not only type bounds.
This bug is a regression only because we now vectorize the testcase to
xorps %xmm0, %xmm0
movq %rdi, %rax
movlps %xmm0, (%rdi)
movhps %xmm0, 8(%rdi)
movlps %xmm0, 16(%rdi)
movlps %xmm0, 24(%rdi)
compared to
xorl %edx, %edx
movq %rdi, %rax
movl %edx, (%rdi)
movl %edx, 4(%rdi)
movl %edx, 8(%rdi)
movl %edx, 12(%rdi)
movl %edx, 16(%rdi)
movl %edx, 20(%rdi)
movl %edx, 24(%rdi)
movl %edx, 28(%rdi)
which is a good thing.
Eventually we can mitigate the problem from inside the vectorizer by
not using
vect_p.7_13 = &MEM[(struct Y *)&<retval>].ar[0];
but instead
vect_p.7_13 = &<retval> + off
style initial addresses. Unfortunately that isn't very easy to do.
More information about the Gcc-bugs
mailing list