https://gcc.gnu.org/bugzilla/show_bug.cgi?id=104854

Martin Sebor <msebor at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |msebor at gcc dot gnu.org
            Summary|[11/12 Regression]          |-Wstringop-overread should
                   |-Wstringop-overread should  |not warn for strnlen and
                   |not warn for strnlen and    |strndup
                   |strndup                     |

--- Comment #3 from Martin Sebor <msebor at gcc dot gnu.org> ---
The same warning is also issued for some calls to memchr(), strncmp() and
probably other built-in functions as well.  For example:

  const char a[] = "123";

  char* f (int i)
  {
    return __builtin_memchr (a + i, '3', 7);
  }

  warning: ‘__builtin_memchr’ specified bound 7 exceeds source size 4
[-Wstringop-overread]
      5 |   return __builtin_memchr (a + i, '3', 7);
        |          ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  y.c:1:12: note: source object allocated here
      1 | const char a[] = "123";
        |            ^

In all these cases the warnings are intentional (i.e., it's a feature, and so
not a regression).  Their purpose is to point out what could be a coding
mistake.  With strndup(), since the use case for it rather than strdup() is to
copy an initial substring, specifying a bound that's larger than the length of
the string is pointless.

In general, the GCC manual documents warnings as

  diagnostic messages that report constructions that are not inherently
erroneous but that are risky or suggest there may have been an error. 

So not all instances of any warning should be expected to indicate errors.  In
fact, many are known to be benign by design (for example, all instances of
-Wchar-subscripts are benign when -funsigned-char is used; many instance of
-Waddress are also benign, as are many -Wparentheses, etc.).  And although most
middle end warnings tend to be designed to trigger only for invalid statements
(i.e., statements that have undefined behavior if reached during execution),
some do also trigger for code that's strictly valid but suspect.  Besides the
-Wstringop-overread examples here, other such warnings include dynamic
allocation calls with sizes in excess of PTRDIFF_MAX
(-Walloc-size-larger-than), returning the address of a local variable
(-Wreturn-local-addr), or in GCC 12, storing the address of a local variable in
an extern pointer (-Wdangling-pointer).

Deciding what code is suspect enough to warn and under what option (-Wall or
-Wextra) is a judgment call; different people have very different ideas.

Reply via email to