xref: /openbsd/lib/libc/string/strlcpy.3 (revision d415bd75)
1.\"	$OpenBSD: strlcpy.3,v 1.27 2019/01/25 00:19:25 millert Exp $
2.\"
3.\" Copyright (c) 1998, 2000 Todd C. Miller <millert@openbsd.org>
4.\"
5.\" Permission to use, copy, modify, and distribute this software for any
6.\" purpose with or without fee is hereby granted, provided that the above
7.\" copyright notice and this permission notice appear in all copies.
8.\"
9.\" THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
10.\" WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
11.\" MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
12.\" ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
13.\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
14.\" ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
15.\" OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
16.\"
17.Dd $Mdocdate: January 25 2019 $
18.Dt STRLCPY 3
19.Os
20.Sh NAME
21.Nm strlcpy ,
22.Nm strlcat
23.Nd size-bounded string copying and concatenation
24.Sh SYNOPSIS
25.In string.h
26.Ft size_t
27.Fn strlcpy "char *dst" "const char *src" "size_t dstsize"
28.Ft size_t
29.Fn strlcat "char *dst" "const char *src" "size_t dstsize"
30.Sh DESCRIPTION
31The
32.Fn strlcpy
33and
34.Fn strlcat
35functions copy and concatenate strings with the
36same input parameters and output result as
37.Xr snprintf 3 .
38They are designed to be safer, more consistent, and less error
39prone replacements for the easily misused functions
40.Xr strncpy 3
41and
42.Xr strncat 3 .
43.Pp
44.Fn strlcpy
45and
46.Fn strlcat
47take the full size of the destination buffer and guarantee
48NUL-termination if there is room.
49Note that room for the NUL should be included in
50.Fa dstsize .
51.Pp
52.Fn strlcpy
53copies up to
54.Fa dstsize
55\- 1 characters from the string
56.Fa src
57to
58.Fa dst ,
59NUL-terminating the result if
60.Fa dstsize
61is not 0.
62.Pp
63.Fn strlcat
64appends string
65.Fa src
66to the end of
67.Fa dst .
68It will append at most
69.Fa dstsize
70\- strlen(dst) \- 1 characters.
71It will then NUL-terminate, unless
72.Fa dstsize
73is 0 or the original
74.Fa dst
75string was longer than
76.Fa dstsize
77(in practice this should not happen
78as it means that either
79.Fa dstsize
80is incorrect or that
81.Fa dst
82is not a proper string).
83.Pp
84If the
85.Fa src
86and
87.Fa dst
88strings overlap, the behavior is undefined.
89.Sh RETURN VALUES
90Besides quibbles over the return type
91.Pf ( Va size_t
92versus
93.Va int )
94and signal handler safety
95.Pf ( Xr snprintf 3
96is not entirely safe on some systems), the
97following two are equivalent:
98.Bd -literal -offset indent
99n = strlcpy(dst, src, len);
100n = snprintf(dst, len, "%s", src);
101.Ed
102.Pp
103Like
104.Xr snprintf 3 ,
105the
106.Fn strlcpy
107and
108.Fn strlcat
109functions return the total length of the string they tried to create.
110For
111.Fn strlcpy
112that means the length of
113.Fa src .
114For
115.Fn strlcat
116that means the initial length of
117.Fa dst
118plus
119the length of
120.Fa src .
121.Pp
122If the return value is
123.Cm >=
124.Va dstsize ,
125the output string has been truncated.
126It is the caller's responsibility to handle this.
127.Sh EXAMPLES
128The following code fragment illustrates the simple case:
129.Bd -literal -offset indent
130char *s, *p, buf[BUFSIZ];
131
132\&...
133
134(void)strlcpy(buf, s, sizeof(buf));
135(void)strlcat(buf, p, sizeof(buf));
136.Ed
137.Pp
138To detect truncation, perhaps while building a pathname, something
139like the following might be used:
140.Bd -literal -offset indent
141char *dir, *file, pname[PATH_MAX];
142
143\&...
144
145if (strlcpy(pname, dir, sizeof(pname)) >= sizeof(pname))
146	goto toolong;
147if (strlcat(pname, file, sizeof(pname)) >= sizeof(pname))
148	goto toolong;
149.Ed
150.Pp
151Since it is known how many characters were copied the first time, things
152can be sped up a bit by using a copy instead of an append:
153.Bd -literal -offset indent
154char *dir, *file, pname[PATH_MAX];
155size_t n;
156
157\&...
158
159n = strlcpy(pname, dir, sizeof(pname));
160if (n >= sizeof(pname))
161	goto toolong;
162if (strlcpy(pname + n, file, sizeof(pname) - n) >= sizeof(pname) - n)
163	goto toolong;
164.Ed
165.Pp
166However, one may question the validity of such optimizations, as they
167defeat the whole purpose of
168.Fn strlcpy
169and
170.Fn strlcat .
171As a matter of fact, the first version of this manual page got it wrong.
172.Sh SEE ALSO
173.Xr snprintf 3 ,
174.Xr strncat 3 ,
175.Xr strncpy 3 ,
176.Xr wcslcpy 3
177.Sh HISTORY
178.Fn strlcpy
179and
180.Fn strlcat
181first appeared in
182.Ox 2.4 .
183.Sh AUTHORS
184.Fn strlcpy
185and
186.Fn strlcat
187were created by
188.An Todd C. Miller Aq Mt millert@openbsd.org .
189