https://gcc.gnu.org/bugzilla/show_bug.cgi?id=124905
Bug ID: 124905
Summary: Wstring-overread warns about defined behavior with
memchr (..., SIZE_MAX)
Product: gcc
Version: 16.0
Status: UNCONFIRMED
Severity: normal
Priority: P3
Component: diagnostics
Assignee: dmalcolm at redhat dot com
Reporter: vries at gcc dot gnu.org
Target Milestone: ---
Consider test-10.c:
...
$ cat test-10.c
#include <stdio.h>
#include <string.h>
static void __attribute__((noinline, noipa, noclone))
foo (const char *s)
{
const void *p;
p = memchr (s, 'a', (size_t)-1);
printf ("%p\n", p);
p = memchr (s, 'z', (size_t)-1);
printf ("%p\n", p);
}
int
main (void)
{
const char *s = "foobar";
foo (s);
}
...
If we compile, we get two Wstringop-overread warnings:
...
$ gcc-16 -Wall test-10.c -O2
test-10.c: In function 'foo':
test-10.c:8:7: warning: 'memchr' specified bound 18446744073709551615 exceeds
maximum object size 9223372036854775807 [-Wstringop-overread]
8 | p = memchr (s, 'a', (size_t)-1);
| ^~~~~~~~~~~~~~~~~~~~~~~~~~~
test-10.c:11:7: warning: 'memchr' specified bound 18446744073709551615 exceeds
maximum object size 9223372036854775807 [-Wstringop-overread]
11 | p = memchr (s, 'z', (size_t)-1);
| ^~~~~~~~~~~~~~~~~~~~~~~~~~~
...
The second warning is for code that has undefined behavior (because 'z' is not
found in "foobar").
The first warning is for code that does have defined behavior (because 'a' is
found in "foobar").
We could consider this a false positive.
We could also say that the documentation should be updated. Currently it
states:
...
Warn for calls to string manipulation functions such as memchr, or strcpy that
are determined to read past the end of the source sequence.
...
Indeed, the code for the first warning is not "determined to read past the end
of the source sequence".
For Wstringop-overflow we have:
...
The option also warns for calls that specify a size in excess of the largest
possible object or at most SIZE_MAX / 2 byte
...
and the current Wstringop-overread behavior would match with such a
description.