https://gcc.gnu.org/bugzilla/show_bug.cgi?id=94195
Bug ID: 94195 Summary: missing warning reading a smaller object via an lvalue of a larger type Product: gcc Version: 10.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 was derived from PR 94187. The past-the-end store in f() is diagnosed by -Wstringop-overflow as expected but the corresponding past-the-end read in g() is not. It's checked by -Warray-bounds but the code there doesn't fully consider the type of the access. $ cat pr94187.c && gcc -O2 -S -Wall -Wextra -Wpedantic -fdump-tree-vrp=/dev/stdout pr94187.c char a[1]; void f (void) { *(int*)a = 0; // -Wstringop-overflow (good) } int g (void) { return *(int*)a; // missing warning (-Warray-bounds) } ;; Function f (f, funcdef_no=0, decl_uid=1931, cgraph_uid=1, symbol_order=1) ;; 1 loops found ;; ;; Loop 0 ;; header 0, latch 1 ;; depth 0, outer -1 ;; nodes: 0 1 2 ;; 2 succs { 1 } Value ranges after VRP: f () { <bb 2> [local count: 1073741824]: MEM[(int *)&a] = 0; return; } pr94187.c: In function âfâ: pr94187.c:5:12: warning: writing 4 bytes into a region of size 1 [-Wstringop-overflow=] 5 | *(int*)a = 0; // -Wstringop-overflow (good) | ~~~~~~~~~^~~ pr94187.c:1:6: note: at offset 0 to object âaâ with size 1 declared here 1 | char a[1]; | ^ ;; Function f (f, funcdef_no=0, decl_uid=1931, cgraph_uid=1, symbol_order=1) ;; 1 loops found ;; ;; Loop 0 ;; header 0, latch 1 ;; depth 0, outer -1 ;; nodes: 0 1 2 ;; 2 succs { 1 } Value ranges after VRP: f () { <bb 2> [local count: 1073741824]: MEM[(int *)&a] = 0; return; } ;; Function g (g, funcdef_no=1, decl_uid=1934, cgraph_uid=2, symbol_order=2) ;; 1 loops found ;; ;; Loop 0 ;; header 0, latch 1 ;; depth 0, outer -1 ;; nodes: 0 1 2 ;; 2 succs { 1 } Value ranges after VRP: _2: int VARYING g () { int _2; <bb 2> [local count: 1073741824]: _2 = MEM[(int *)&a]; return _2; } ;; Function g (g, funcdef_no=1, decl_uid=1934, cgraph_uid=2, symbol_order=2) ;; 1 loops found ;; ;; Loop 0 ;; header 0, latch 1 ;; depth 0, outer -1 ;; nodes: 0 1 2 ;; 2 succs { 1 } Value ranges after VRP: _2: int VARYING g () { int _2; <bb 2> [local count: 1073741824]: _2 = MEM[(int *)&a]; return _2; }