]>
Commit | Line | Data |
---|---|---|
b061a43b | 1 | .\" $OpenBSD: strlcpy.3,v 1.26 2013/09/30 12:02:35 millert Exp $ |
5b2abdfb | 2 | .\" |
1f2f436a | 3 | .\" Copyright (c) 1998, 2000 Todd C. Miller <Todd.Miller@courtesan.com> |
5b2abdfb | 4 | .\" |
1f2f436a A |
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. | |
5b2abdfb A |
16 | .\" |
17 | .\" THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, | |
18 | .\" INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY | |
19 | .\" AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL | |
20 | .\" THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, | |
21 | .\" EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, | |
22 | .\" PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; | |
23 | .\" OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, | |
24 | .\" WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR | |
25 | .\" OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF | |
26 | .\" ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | |
27 | .\" | |
b061a43b | 28 | .\" $FreeBSD$ |
5b2abdfb | 29 | .\" |
b061a43b | 30 | .Dd February 26, 2016 |
5b2abdfb A |
31 | .Dt STRLCPY 3 |
32 | .Os | |
33 | .Sh NAME | |
34 | .Nm strlcpy , | |
35 | .Nm strlcat | |
36 | .Nd size-bounded string copying and concatenation | |
37 | .Sh LIBRARY | |
38 | .Lb libc | |
39 | .Sh SYNOPSIS | |
40 | .In string.h | |
41 | .Ft size_t | |
b061a43b | 42 | .Fn strlcpy "char * restrict dst" "const char * restrict src" "size_t dstsize" |
5b2abdfb | 43 | .Ft size_t |
b061a43b | 44 | .Fn strlcat "char * restrict dst" "const char * restrict src" "size_t dstsize" |
5b2abdfb A |
45 | .Sh DESCRIPTION |
46 | The | |
47 | .Fn strlcpy | |
48 | and | |
49 | .Fn strlcat | |
b061a43b A |
50 | functions copy and concatenate strings with the |
51 | same input parameters and output result as | |
52 | .Xr snprintf 3 . | |
53 | They are designed to be safer, more consistent, and less error | |
54 | prone replacements for the easily misused functions | |
5b2abdfb A |
55 | .Xr strncpy 3 |
56 | and | |
57 | .Xr strncat 3 . | |
b061a43b | 58 | .Pp |
5b2abdfb A |
59 | .Fn strlcpy |
60 | and | |
61 | .Fn strlcat | |
b061a43b A |
62 | take the full size of the destination buffer and guarantee |
63 | NUL-termination if there is room. | |
64 | Note that room for the NUL should be included in | |
65 | .Fa dstsize . | |
5b2abdfb | 66 | .Pp |
5b2abdfb | 67 | .Fn strlcpy |
b061a43b A |
68 | copies up to |
69 | .Fa dstsize | |
70 | \- 1 characters from the string | |
5b2abdfb A |
71 | .Fa src |
72 | to | |
73 | .Fa dst , | |
b061a43b A |
74 | NUL-terminating the result if |
75 | .Fa dstsize | |
76 | is not 0. | |
5b2abdfb | 77 | .Pp |
5b2abdfb | 78 | .Fn strlcat |
b061a43b | 79 | appends string |
5b2abdfb A |
80 | .Fa src |
81 | to the end of | |
82 | .Fa dst . | |
83 | It will append at most | |
b061a43b A |
84 | .Fa dstsize |
85 | \- strlen(dst) \- 1 characters. | |
86 | It will then NUL-terminate, unless | |
87 | .Fa dstsize | |
88 | is 0 or the original | |
89 | .Fa dst | |
90 | string was longer than | |
91 | .Fa dstsize | |
92 | (in practice this should not happen | |
93 | as it means that either | |
94 | .Fa dstsize | |
95 | is incorrect or that | |
96 | .Fa dst | |
97 | is not a proper string). | |
ad3c9f2a | 98 | .Pp |
b061a43b A |
99 | If the |
100 | .Fa src | |
101 | and | |
102 | .Fa dst | |
103 | strings overlap, the behavior is undefined. | |
5b2abdfb | 104 | .Sh RETURN VALUES |
b061a43b A |
105 | Besides quibbles over the return type |
106 | .Pf ( Va size_t | |
107 | versus | |
108 | .Va int ) | |
109 | and signal handler safety | |
110 | .Pf ( Xr snprintf 3 | |
111 | is not entirely safe on some systems), the | |
112 | following two are equivalent: | |
113 | .Bd -literal -offset indent | |
114 | n = strlcpy(dst, src, len); | |
115 | n = snprintf(dst, len, "%s", src); | |
116 | .Ed | |
117 | .Pp | |
118 | Like | |
119 | .Xr snprintf 3 , | |
120 | the | |
5b2abdfb A |
121 | .Fn strlcpy |
122 | and | |
123 | .Fn strlcat | |
b061a43b | 124 | functions return the total length of the string they tried to create. |
3d9156a7 | 125 | For |
5b2abdfb A |
126 | .Fn strlcpy |
127 | that means the length of | |
128 | .Fa src . | |
129 | For | |
130 | .Fn strlcat | |
131 | that means the initial length of | |
132 | .Fa dst | |
133 | plus | |
134 | the length of | |
135 | .Fa src . | |
5b2abdfb | 136 | .Pp |
b061a43b A |
137 | If the return value is |
138 | .Cm >= | |
139 | .Va dstsize , | |
140 | the output string has been truncated. | |
141 | It is the caller's responsibility to handle this. | |
5b2abdfb A |
142 | .Sh EXAMPLES |
143 | The following code fragment illustrates the simple case: | |
144 | .Bd -literal -offset indent | |
145 | char *s, *p, buf[BUFSIZ]; | |
146 | ||
147 | \&... | |
148 | ||
149 | (void)strlcpy(buf, s, sizeof(buf)); | |
150 | (void)strlcat(buf, p, sizeof(buf)); | |
151 | .Ed | |
152 | .Pp | |
153 | To detect truncation, perhaps while building a pathname, something | |
154 | like the following might be used: | |
155 | .Bd -literal -offset indent | |
156 | char *dir, *file, pname[MAXPATHLEN]; | |
157 | ||
158 | \&... | |
159 | ||
160 | if (strlcpy(pname, dir, sizeof(pname)) >= sizeof(pname)) | |
161 | goto toolong; | |
162 | if (strlcat(pname, file, sizeof(pname)) >= sizeof(pname)) | |
163 | goto toolong; | |
164 | .Ed | |
165 | .Pp | |
1f2f436a | 166 | Since it is known how many characters were copied the first time, things |
b061a43b | 167 | can be sped up a bit by using a copy instead of an append: |
5b2abdfb A |
168 | .Bd -literal -offset indent |
169 | char *dir, *file, pname[MAXPATHLEN]; | |
170 | size_t n; | |
171 | ||
172 | \&... | |
173 | ||
174 | n = strlcpy(pname, dir, sizeof(pname)); | |
175 | if (n >= sizeof(pname)) | |
176 | goto toolong; | |
177 | if (strlcpy(pname + n, file, sizeof(pname) - n) >= sizeof(pname) - n) | |
178 | goto toolong; | |
179 | .Ed | |
180 | .Pp | |
181 | However, one may question the validity of such optimizations, as they | |
182 | defeat the whole purpose of | |
183 | .Fn strlcpy | |
184 | and | |
185 | .Fn strlcat . | |
186 | As a matter of fact, the first version of this manual page got it wrong. | |
187 | .Sh SEE ALSO | |
188 | .Xr snprintf 3 , | |
189 | .Xr strncat 3 , | |
1f2f436a A |
190 | .Xr strncpy 3 , |
191 | .Xr wcslcpy 3 | |
5b2abdfb | 192 | .Sh HISTORY |
9385eb3d | 193 | The |
5b2abdfb A |
194 | .Fn strlcpy |
195 | and | |
196 | .Fn strlcat | |
197 | functions first appeared in | |
198 | .Ox 2.4 , | |
b061a43b | 199 | and |
5b2abdfb | 200 | .Fx 3.3 . |