https://gcc.gnu.org/bugzilla/show_bug.cgi?id=86085
Bug ID: 86085 Summary: I/O built-ins considered argument clobbers Product: gcc Version: 8.0 Status: UNCONFIRMED Severity: normal Priority: P3 Component: tree-optimization Assignee: unassigned at gcc dot gnu.org Reporter: msebor at gcc dot gnu.org Target Milestone: --- The buggy test case in pr67610 should be diagnosed by -Wrestrict but isn't. Debugging shows that the strlen pass discards the length information for the array in g() in response to the alias oracle determining that the printf() call might clobber the array argument. Except for printf with the %n directive, standard output functions don't modify their arguments. $ cat z.c && gcc -O2 -S -Wall -Wextra -fdump-tree-optimized=/dev/stdout z.c void f (void) { char s[] = "123"; char d[sizeof s]; __builtin_sprintf (d, "%s", s); // eliminated (transformed to strcpy by sprintf pass) if (__builtin_strlen (s) != 3) // folded __builtin_abort (); if (__builtin_strlen (d) != 3) // also folded __builtin_abort (); } void g (void) { char s[] = "123"; __builtin_puts (s); if (__builtin_strlen (s) != 3) // not folded __builtin_abort (); } ;; Function f (f, funcdef_no=0, decl_uid=1956, cgraph_uid=0, symbol_order=0) f () { <bb 2> [local count: 1073741825]: return; } ;; Function g (g, funcdef_no=1, decl_uid=1961, cgraph_uid=1, symbol_order=1) g () { char s[4]; long unsigned int _1; <bb 2> [local count: 1073741825]: s = "123"; __builtin_puts (&s); _1 = __builtin_strlen (&s); if (_1 != 3) goto <bb 3>; [0.00%] else goto <bb 4>; [99.96%] <bb 3> [count: 0]: __builtin_abort (); <bb 4> [local count: 1073312327]: s ={v} {CLOBBER}; return; }