Commit 741ff2a2 by Jakub Jelinek

strlen: Punt on UB reads past end of string literal [PR94187]

The gcc.dg/pr68785.c test which contains:
int
foo (void)
{
  return *(int *) "";
}
has UB in the program if it is ever called, but causes UB in the compiler
as well as at least in theory non-reproduceable code generation.
The problem is that nbytes is in this case 4, prep is the
TREE_STRING_POINTER of a "" string literal with TREE_STRING_LENGTH of 1 and
we do:
4890              for (const char *p = prep; p != prep + nbytes; ++p)
4891                if (*p)
4892                  {
4893                    *allnul = false;
4894                    break;
4895                  }
and so read the bytes after the STRING_CST payload, which can be random.
I think we should just punt in this case.

2020-03-17  Jakub Jelinek  <jakub@redhat.com>

	PR tree-optimization/94187
	* tree-ssa-strlen.c (count_nonzero_bytes): Punt if
	nchars - offset < nbytes.
parent 7afa3b82
2020-03-17 Jakub Jelinek <jakub@redhat.com> 2020-03-17 Jakub Jelinek <jakub@redhat.com>
PR tree-optimization/94187
* tree-ssa-strlen.c (count_nonzero_bytes): Punt if
nchars - offset < nbytes.
PR middle-end/94189 PR middle-end/94189
* builtins.c (expand_builtin_strnlen): Do return NULL_RTX if we would * builtins.c (expand_builtin_strnlen): Do return NULL_RTX if we would
emit a warning if it was enabled and don't depend on TREE_NO_WARNING emit a warning if it was enabled and don't depend on TREE_NO_WARNING
......
...@@ -4822,6 +4822,8 @@ count_nonzero_bytes (tree exp, unsigned HOST_WIDE_INT offset, ...@@ -4822,6 +4822,8 @@ count_nonzero_bytes (tree exp, unsigned HOST_WIDE_INT offset,
of the access), set it here to the size of the string, including of the access), set it here to the size of the string, including
all internal and trailing nuls if the string has any. */ all internal and trailing nuls if the string has any. */
nbytes = nchars - offset; nbytes = nchars - offset;
else if (nchars - offset < nbytes)
return false;
prep = TREE_STRING_POINTER (exp) + offset; prep = TREE_STRING_POINTER (exp) + offset;
} }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment