https://gcc.gnu.org/bugzilla/show_bug.cgi?id=96384
Bug ID: 96384
Summary: [11 Regression] bogus -Wstringop-overflow= storing
into multidimensional array with index in range
Product: gcc
Version: 11.0
Status: UNCONFIRMED
Severity: normal
Priority: P3
Component: middle-end
Assignee: unassigned at gcc dot gnu.org
Reporter: msebor at gcc dot gnu.org
Target Milestone: ---
The following test case triggers a false positive -Wstringop-overflow:
$ cat z.c && gcc -O2 -S -Wall -fdump-tree-strlen-all=/dev/stdout z.c
char a[2][3];
void f (unsigned i)
{
if (i > ~0U - 1)
i = ~0U - 1;
a[i][0] = 0;
}
;; Function f (f, funcdef_no=0, decl_uid=1932, cgraph_uid=1, symbol_order=1)
Pass statistics of "strlen": ----------------
;; 1 loops found
;;
;; Loop 0
;; header 0, latch 1
;; depth 0, outer -1
;; nodes: 0 1 2
;; 2 succs { 1 }
extract_range_from_stmt visiting:
# RANGE [0, 4294967294]
_2 = MIN_EXPR <i_1(D), 4294967294>;
Intersecting
unsigned int [0, 4294967294]
and
unsigned int [0, 4294967294]
to
unsigned int [0, 4294967294]
z.c: In function âfâ:
z.c:7:11: warning: writing 1 byte into a region of size 0
[-Wstringop-overflow=]
7 | a[i][0] = 0;
| ~~~~~~~~^~~
z.c:1:6: note: at offset 0 to object âaâ with size 6 declared here
1 | char a[2][3];
| ^
maybe_invalidate called for a[_2][0] = 0;
maybe_invalidate returns 0
Pass statistics of "strlen": ----------------
f (unsigned intD.9 iD.1931)
{
unsigned intD.9 i_1(D) = iD.1931;
unsigned intD.9 _2;
;; basic block 2, loop depth 0, count 1073741824 (estimated locally), maybe
hot
;; prev block 0, next block 1, flags: (NEW, REACHABLE, VISITED)
;; pred: ENTRY [always] count:1073741824 (estimated locally)
(FALLTHRU,EXECUTABLE)
# RANGE [0, 4294967294]
_2 = MIN_EXPR <i_1(D), 4294967294>;
# .MEM_4 = VDEF <.MEM_3(D)>
aD.1930[_2][0] = 0;
# VUSE <.MEM_4>
return;
;; succ: EXIT [always] count:1073741824 (estimated locally)
(EXECUTABLE)
}