PR middle-end/79496 - call to snprintf with zero size eliminated with -Wformat-truncation=2

gcc/ChangeLog:

	PR middle-end/79496
	* gimple-ssa-sprintf.c (pass_sprintf_length::handle_gimple_call): Avoid
	clearing info.nowrite flag when snprintf size argument is a range.

gcc/testsuite/ChangeLog:

	PR middle-end/79496
	* gcc.dg/tree-ssa/builtin-snprintf-2.c: New test.

From-SVN: r245415
This commit is contained in:
Martin Sebor 2017-02-14 04:38:54 +00:00 committed by Martin Sebor
parent f2348577b2
commit ee75687bc6
4 changed files with 47 additions and 3 deletions

View File

@ -1,3 +1,9 @@
2017-02-13 Martin Sebor <msebor@redhat.com>
PR middle-end/79496
* gimple-ssa-sprintf.c (pass_sprintf_length::handle_gimple_call): Avoid
clearing info.nowrite flag when snprintf size argument is a range.
2017-02-13 Jakub Jelinek <jakub@redhat.com>
* cprop.c (cprop_jump): Add missing space in string literal.

View File

@ -3443,6 +3443,10 @@ pass_sprintf_length::handle_gimple_call (gimple_stmt_iterator *gsi)
info.format = gimple_call_arg (info.callstmt, idx_format);
/* True when the destination size is constant as opposed to the lower
or upper bound of a range. */
bool dstsize_cst_p = true;
if (idx_dstsize == HOST_WIDE_INT_M1U)
{
/* For non-bounded functions like sprintf, determine the size
@ -3483,8 +3487,8 @@ pass_sprintf_length::handle_gimple_call (gimple_stmt_iterator *gsi)
else if (TREE_CODE (size) == SSA_NAME)
{
/* Try to determine the range of values of the argument
and use the greater of the two at -Wformat-level 1 and
the smaller of them at level 2. */
and use the greater of the two at level 1 and the smaller
of them at level 2. */
wide_int min, max;
enum value_range_type range_type
= get_range_info (size, &min, &max);
@ -3495,6 +3499,11 @@ pass_sprintf_length::handle_gimple_call (gimple_stmt_iterator *gsi)
? wi::fits_uhwi_p (max) ? max.to_uhwi () : max.to_shwi ()
: wi::fits_uhwi_p (min) ? min.to_uhwi () : min.to_shwi ());
}
/* The destination size is not constant. If the function is
bounded (e.g., snprintf) a lower bound of zero doesn't
necessarily imply it can be eliminated. */
dstsize_cst_p = false;
}
}
@ -3511,7 +3520,7 @@ pass_sprintf_length::handle_gimple_call (gimple_stmt_iterator *gsi)
without actually producing any. Pretend the size is
unlimited in this case. */
info.objsize = HOST_WIDE_INT_MAX;
info.nowrite = true;
info.nowrite = dstsize_cst_p;
}
else
{

View File

@ -1,3 +1,8 @@
2017-02-13 Martin Sebor <msebor@redhat.com>
PR middle-end/79496
* gcc.dg/tree-ssa/builtin-snprintf-2.c: New test.
2017-02-13 Jakub Jelinek <jakub@redhat.com>
PR sanitizer/79341

View File

@ -0,0 +1,24 @@
/* PR middle-end/79496 - call to snprintf with non-zero size eliminated
with -Wformat-truncation=2
{ dg-do compile }
{ dg-options "-O2 -Wall -Wformat-truncation=2 -fprintf-return-value -fdump-tree-optimized" } */
char d[2];
int test_cst (unsigned n)
{
if (1 < n)
n = 0;
return __builtin_snprintf (d, n, "%d", 1);
}
int test_var (char *d, unsigned n)
{
if (2 < n)
n = 0;
return __builtin_snprintf (d, n, "%i", 1);
}
/* { dg-final { scan-tree-dump-times "snprintf" 2 "optimized"} } */