Ben Pfaff <blp <at> cs.stanford.edu> writes: > >> extern void *memchr (void const *__s, int __c, size_t __n) > >> - __attribute__ ((__pure__)); > >> + __attribute__ ((__pure__)) _GL_ARG_NONNULL ((1)); > > > > This one I'm fuzzy on. On one hand, the POSIX definition is that the function > > reads at most __c bytes, so when __c is 0, it is safe for __s to be NULL. On > > the other hand, glibc already warns here, the gnulib testsuite already jumps > > through hoops to avoid the warning, and the likelihood of meaning to pass NULL > > when __c is 0 is slim. Your call. > > ISO C99 requires that memchr's argument be nonnull even if __c is > zero, as follows. 7.21.1 "String function conventions" says that > pointer arguments must be valid even if the number of bytes is 0: > > Where an argument declared as size_t n specifies the length > of the array for a function, n can have the value zero on a > call to that function. Unless explicitly stated otherwise in > the description of a particular function in this subclause, > pointer arguments on such a call shall still have valid > values, as described in 7.1.4.
But POSIX made the requirement tighter, as an extension to C, and gnulib guarantees the POSIX semantics: http://austingroupbugs.net/view.php?id=110 At the end of the paragraph at line 42164, append a sentence with CX shading: If n is larger than the object pointed to by s, the application shall ensure that an instance of c occurs within the object. Change the rationale at line 42174 from: None. to: Although C99 is silent on the behavior of memchr when s points to an array smaller than n bytes, this specification requires memchr to behave as if it accesses bytes in ascending order, thus making memchr(s,0,n) safe to use as a faster alternative to strnlen(s,n) when determining if the end of a null-terminated string occurs within n bytes. -- Eric Blake