[Bug middle-end/71319] New: unnecessary call to __strcat_chk emitted after buffer reset
msebor at gcc dot gnu.org
gcc-bugzilla@gcc.gnu.org
Sat May 28 02:51:00 GMT 2016
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=71319
Bug ID: 71319
Summary: unnecessary call to __strcat_chk emitted after buffer
reset
Product: gcc
Version: 7.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: ---
Similar to bug 71304, in the following test case, since the string in the
destination buffer is truncated at a known offset after it has been copied
there by the checked call, the subsequent strcat call doesn't need to expand to
a checked call because there is enough space in the buffer to append the source
string to its contents. GCC performs this optimization in the first test case
(function f) when the string a truncated by calling strcpy, but it doesn't do
the same thing when the string is truncated by inserting a NUL into the same
position.
$ cat strcat.c && /home/msebor/build/gcc-6-branch/gcc/xgcc
-B/home/msebor/build/gcc-6-branch/gcc -O2 -S -fdump-tree-optimized=/dev/stdout
strcat.c
#define strcat(d, s)\
__builtin___strcat_chk (d, s, __builtin_object_size (d, 0))
#define strcpy(d, s) \
__builtin___strcpy_chk (d, s, __builtin_object_size (d, 0))
void sink (const char*);
int f (const char *s)
{
char a [4] = "1";
strcat (a, "2"); // safe
strcat (a, s); // must be checked
strcpy (a, "1");
strcat (a, "3"); // safe
sink (a);
}
int g (const char *s)
{
char a [4] = "1";
strcat (a, "2"); // safe
strcat (a, s); // must be checked
a [1] = '\0';
strcat (a, "3"); // safe but checked (missing optimization)
sink (a);
}
;; Function f (f, funcdef_no=0, decl_uid=1758, cgraph_uid=0, symbol_order=0)
f (const char * s)
{
char a[4];
<bb 2>:
a = "1";
__builtin___strcpy_chk (&MEM[(void *)&a + 2B], s_4(D), 4);
MEM[(char * {ref-all})&a] = 49;
__builtin_memcpy (&MEM[(void *)&a + 1B], "3", 2);
sink (&a);
a ={v} {CLOBBER};
return;
}
;; Function g (g, funcdef_no=1, decl_uid=1762, cgraph_uid=1, symbol_order=1)
g (const char * s)
{
char a[4];
<bb 2>:
a = "1";
__builtin___strcpy_chk (&MEM[(void *)&a + 2B], s_4(D), 4);
a[1] = 0;
__builtin___strcat_chk (&a, "3", 4);
sink (&a);
a ={v} {CLOBBER};
return;
}
More information about the Gcc-bugs
mailing list