This is the mail archive of the
libc-alpha@sourceware.org
mailing list for the glibc project.
Re: [PATCH v7] Implement strlcpy, strlcat [BZ #178]
- From: Paul Eggert <eggert at cs dot ucla dot edu>
- To: Florian Weimer <fweimer at redhat dot com>
- Cc: GNU C Library <libc-alpha at sourceware dot org>
- Date: Tue, 5 Jan 2016 14:08:19 -0800
- Subject: Re: [PATCH v7] Implement strlcpy, strlcat [BZ #178]
- Authentication-results: sourceware.org; auth=none
- References: <5682DD7E dot 6000301 at redhat dot com> <56839678 dot 8040304 at cs dot ucla dot edu> <568ADC5F dot 5010608 at redhat dot com> <568B1587 dot 4030905 at cs dot ucla dot edu> <568C08E1 dot 2010604 at redhat dot com>
On 01/05/2016 10:18 AM, Florian Weimer wrote:
We need to compatible with as many of the implementation we replace as
possible.
Sure, but any need for bug-for-bug compatibility would not be absolute.
A more-important need would be to support applications that use glibc.
If glibc applications would benefit from better checking for weird
corner cases that BSD man pages say should not happen, the glibc spec
should allow such checking even if the BSD implementations don't happen
to do such checking now, or do it sometimes but not others.
the size-zero buffer is quite clear from the original description of
strlcpy.
No, the original description of strlcpy says "Note that you should
include a byte for the NUL in 'size'.", which means that 'size' should
be nonzero. The original description also says "The strlcpy function
copies up to size - 1 characters from the NUL-terminated string src to
dst, NUL-terminating the result.", which means that the result is
null-terminated. See:
http://cvsweb.openbsd.org/cgi-bin/cvsweb/~checkout~/src/lib/libc/string/strlcpy.3?rev=1.1
The original description also contains some contrary wording elsewhere
"(as long as size is larger than 0)", but the point is that the spec has
*always* been confusing and contradictory in this area. Really, the only
safe way for an application to follow the original spec, is to avoid
calling these functions with zero sizes.
Granted, the description of strlcpy has mutated and there are now
versions floating around that talk about size-zero more consistently,
but it is not at all clear that this was prompted by application needs
or that applications depend on it or should depend on it. It looks more
like a case of library implementers trying to clean up a messy spec
without thinking things through carefully enough.
For strlcpy, we don't care if the destination is a string or not
because we overwrite what's in the destination array.
No, applications that call strlcpy expect it to create a string. For
example, the design intent is for applications to use strlcpy followed
by strlcat, and because strlcat (S, ...) assumes that S is a string,
strlcpy must create a string in S; otherwise the two functions would not
be the companion functions that they're clearly supposed to be.
+The behavior of @code{strlcpy} is undefined if @var{size} is nonzero and
+the source string and the first @var{size} bytes of the destination
+array overlap.
The phrase "@var{size} is nonzero and" is unnecessary, since a
zero-length array cannot overlap anything.
It's okay as far as the formal description of restrict is concerned, but
it's not clear with the informal âoverlapâ.
"overlap" has a standard usage in C11 (one that agrees with the formal
description of 'restrict'). The use of the phrase "@var{size} is nonzero
and" implies that our use of "overlap" has a different meaning. I
suppose we could fix the problem by mentioning somehow that the
wording's nonzero restriction is not intended to imply that size-zero
objects can overlap anything. However, it'd be better to simply disallow
size-zero strlcpy, as in my most-recent proposal.