1.\" $NetBSD: strlcpy.3,v 1.22 2024/11/01 16:36:58 nia Exp $ 2.\" from OpenBSD: strlcpy.3,v 1.11 2000/11/16 23:27:41 angelos Exp 3.\" 4.\" Copyright (c) 1998, 2000 Todd C. Miller <Todd.Miller@courtesan.com> 5.\" All rights reserved. 6.\" 7.\" Redistribution and use in source and binary forms, with or without 8.\" modification, are permitted provided that the following conditions 9.\" are met: 10.\" 1. Redistributions of source code must retain the above copyright 11.\" notice, this list of conditions and the following disclaimer. 12.\" 2. Redistributions in binary form must reproduce the above copyright 13.\" notice, this list of conditions and the following disclaimer in the 14.\" documentation and/or other materials provided with the distribution. 15.\" 3. The name of the author may not be used to endorse or promote products 16.\" derived from this software without specific prior written permission. 17.\" 18.\" THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, 19.\" INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY 20.\" AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL 21.\" THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 22.\" EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 23.\" PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; 24.\" OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 25.\" WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR 26.\" OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF 27.\" ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 28.\" 29.Dd November 1, 2024 30.Dt STRLCPY 3 31.Os 32.Sh NAME 33.Nm strlcpy , 34.Nm strlcat 35.Nd size-bounded string copying and concatenation 36.Sh LIBRARY 37.Lb libc 38.Sh SYNOPSIS 39.In string.h 40.Ft size_t 41.Fn strlcpy "char *dst" "const char *src" "size_t size" 42.Ft size_t 43.Fn strlcat "char *dst" "const char *src" "size_t size" 44.Sh DESCRIPTION 45The 46.Fn strlcpy 47and 48.Fn strlcat 49functions copy and concatenate 50.Tn NUL Ns -terminated 51strings respectively. 52.Pp 53The 54.Fn strlcpy 55function copies up to 56.Fa size Li "- 1" 57bytes from the 58.Tn NUL Ns -terminated 59string 60.Fa src 61to 62.Fa dst , 63.Tn NUL Ns -terminating 64the result. 65.Pp 66The 67.Fn strlcat 68function appends the 69.Tn NUL Ns -terminated 70string 71.Fa src 72to the end of 73.Fa dst . 74It will append at most 75.Fa size Li "-" Fn strlen dst Li "- 1" 76bytes, 77.Tn NUL Ns -terminating 78the result. 79.Ss Relation to Xr strncpy 3 and Xr strncat 3 80Unlike 81.Xr strncpy 3 82and 83.Xr strncat 3 , 84.Fn strlcpy 85and 86.Fn strlcat 87are guaranteed to 88.Tn NUL Ns -terminate 89the result (as long as 90.Fa size 91is larger than 0 or, in the case of 92.Fn strlcat , 93as long as there is at least one byte free in 94.Fa dst ) . 95Note that you should include a byte for the 96.Tn NUL 97in 98.Fa size . 99.Pp 100.Sy WARNING : 101Also unlike 102.Xr strncpy 3 103and 104.Xr strncat 3 , 105.Fn strlcpy 106and 107.Fn strlcat 108are not guaranteed to initialize all 109.Fa size 110bytes of 111.Fa dst 112\(em bytes past 113.Fa dst Ns Li "[" Fn strlen src Li "+ 1" Ns Li "]" 114are left uninitialized. 115This can lead to security vulnerabilities such as leaking secrets from 116uninitialized stack or heap buffers. 117.Pp 118.Sy WARNING : 119.Fn strlcpy 120and 121.Fn strlcat 122only operate on true 123.Dq C 124strings. 125This means that for 126.Fn strlcpy 127.Fa src 128must be 129.Tn NUL Ns -terminated 130and for 131.Fn strlcat 132both 133.Fa src 134and 135.Fa dst 136must be 137.Tn NUL Ns -terminated . 138Applications handling fixed-width fields with 139.Pq possibly empty 140.Tn NUL 141padding, instead of 142.Tn NUL Ns -terminated 143C strings, MUST use 144.Xr strncpy 3 145and 146.Xr strncat 3 147instead. 148Attempting to use 149.Fn strlcpy 150or 151.Fn strlcat 152for these cases can lead to crashes or security vulnerabilities from 153buffer overruns. 154.Sh RETURN VALUES 155The 156.Fn strlcpy 157and 158.Fn strlcat 159functions return the total length of the string they tried to create. 160For 161.Fn strlcpy 162that means the length of 163.Fa src . 164For 165.Fn strlcat 166that means the initial length of 167.Fa dst 168plus 169the length of 170.Fa src . 171While this may seem somewhat confusing it was done to make 172truncation detection simple. 173.Pp 174Note however, that if 175.Fn strlcat 176traverses 177.Fa size 178bytes without finding a 179.Tn NUL , 180the length of the string is considered to be 181.Fa size 182and the destination string will not be 183.Tn NUL Ns -terminated 184.Pq since there was no space for the Tn NUL . 185This keeps 186.Fn strlcat 187from running off the end of a string. 188In practice this should not happen (as it means that either 189.Fa size 190is incorrect or that 191.Fa dst 192is not a proper 193.Dq C 194string). 195The check exists to prevent potential security problems in incorrect code. 196.Sh EXAMPLES 197The following code fragment illustrates the simple case: 198.Bd -literal -offset indent 199char *s, *p, buf[BUFSIZ]; 200 201\&... 202 203strlcpy(buf, s, sizeof(buf)); 204strlcat(buf, p, sizeof(buf)); 205.Ed 206.Pp 207To detect truncation, perhaps while building a pathname, something 208like the following might be used: 209.Bd -literal -offset indent 210char *dir, *file, pname[MAXPATHLEN]; 211 212\&... 213 214if (strlcpy(pname, dir, sizeof(pname)) >= sizeof(pname)) 215 goto toolong; 216if (strlcat(pname, file, sizeof(pname)) >= sizeof(pname)) 217 goto toolong; 218.Ed 219.Pp 220Since we know how many bytes we copied the first time, we can 221speed things up a bit by using a copy instead of an append: 222.Bd -literal -offset indent 223char *dir, *file, pname[MAXPATHLEN]; 224size_t n; 225 226\&... 227 228n = strlcpy(pname, dir, sizeof(pname)); 229if (n >= sizeof(pname)) 230 goto toolong; 231if (strlcpy(pname + n, file, sizeof(pname) - n) >= sizeof(pname) - n) 232 goto toolong; 233.Ed 234.Pp 235However, one may question the validity of such optimizations, as they 236defeat the whole purpose of 237.Fn strlcpy 238and 239.Fn strlcat . 240.Sh SEE ALSO 241.Xr snprintf 3 , 242.Xr strncat 3 , 243.Xr strncpy 3 244.Rs 245.%A Todd C. Miller 246.%A Theo de Raadt 247.%T strlcpy and strlcat -- Consistent, Safe, String Copy and Concatenation 248.%I USENIX Association 249.%B Proceedings of the FREENIX Track: 1999 USENIX Annual Technical Conference 250.%D June 6-11, 1999 251.%U http://www.usenix.org/publications/library/proceedings/usenix99/full_papers/millert/millert.pdf 252.Re 253.Sh STANDARDS 254The 255.Fn strlcpy 256and 257.Fn strlcat 258functions conform to 259.St -p1003.1-2024 . 260.Sh HISTORY 261The 262.Fn strlcpy 263and 264.Fn strlcat 265functions first appeared in 266.Ox 2.4 , 267then in 268.Nx 1.4.3 269and 270.Fx 3.3 . 271