1.\"- 2.\" Copyright (c) 2000 Poul Henning Kamp and Dag-Erling Co�dan Sm�rgrav 3.\" All rights reserved. 4.\" 5.\" Redistribution and use in source and binary forms, with or without 6.\" modification, are permitted provided that the following conditions 7.\" are met: 8.\" 1. Redistributions of source code must retain the above copyright 9.\" notice, this list of conditions and the following disclaimer. 10.\" 2. Redistributions in binary form must reproduce the above copyright 11.\" notice, this list of conditions and the following disclaimer in the 12.\" documentation and/or other materials provided with the distribution. 13.\" 14.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 15.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 16.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 17.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 18.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 19.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 20.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 21.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 22.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 23.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 24.\" SUCH DAMAGE. 25.\" 26.\" $FreeBSD$ 27.\" 28.Dd July 9, 2004 29.Dt SBUF 9 30.Os 31.Sh NAME 32.Nm sbuf , 33.Nm sbuf_new , 34.Nm sbuf_clear , 35.Nm sbuf_setpos , 36.Nm sbuf_bcat , 37.Nm sbuf_bcopyin , 38.Nm sbuf_bcpy , 39.Nm sbuf_cat , 40.Nm sbuf_copyin , 41.Nm sbuf_cpy , 42.Nm sbuf_printf , 43.Nm sbuf_vprintf , 44.Nm sbuf_putc , 45.Nm sbuf_trim , 46.Nm sbuf_overflowed , 47.Nm sbuf_finish , 48.Nm sbuf_data , 49.Nm sbuf_len , 50.Nm sbuf_done , 51.Nm sbuf_delete 52.Nd safe string formatting 53.Sh SYNOPSIS 54.In sys/types.h 55.In sys/sbuf.h 56.Ft struct sbuf * 57.Fn sbuf_new "struct sbuf *s" "char *buf" "int length" "int flags" 58.Ft void 59.Fn sbuf_clear "struct sbuf *s" 60.Ft int 61.Fn sbuf_setpos "struct sbuf *s" "int pos" 62.Ft int 63.Fn sbuf_bcat "struct sbuf *s" "const void *buf" "size_t len" 64.Ft int 65.Fn sbuf_bcopyin "struct sbuf *s" "const void *uaddr" "size_t len" 66.Ft int 67.Fn sbuf_bcpy "struct sbuf *s" "const void *buf" "size_t len" 68.Ft int 69.Fn sbuf_cat "struct sbuf *s" "const char *str" 70.Ft int 71.Fn sbuf_copyin "struct sbuf *s" "const void *uaddr" "size_t len" 72.Ft int 73.Fn sbuf_cpy "struct sbuf *s" "const char *str" 74.Ft int 75.Fn sbuf_printf "struct sbuf *s" "const char *fmt" "..." 76.Ft int 77.Fn sbuf_vprintf "struct sbuf *s" "const char *fmt" "va_list ap" 78.Ft int 79.Fn sbuf_putc "struct sbuf *s" "int c" 80.Ft int 81.Fn sbuf_trim "struct sbuf *s" 82.Ft int 83.Fn sbuf_overflowed "struct sbuf *s" 84.Ft void 85.Fn sbuf_finish "struct sbuf *s" 86.Ft char * 87.Fn sbuf_data "struct sbuf *s" 88.Ft int 89.Fn sbuf_len "struct sbuf *s" 90.Ft int 91.Fn sbuf_done "struct sbuf *s" 92.Ft void 93.Fn sbuf_delete "struct sbuf *s" 94.Sh DESCRIPTION 95The 96.Nm 97family of functions allows one to safely allocate, construct and 98release bounded null-terminated strings in kernel space. 99Instead of arrays of characters, these functions operate on structures 100called 101.Fa sbufs , 102defined in 103.In sys/sbuf.h . 104.Pp 105The 106.Fn sbuf_new 107function initializes the 108.Fa sbuf 109pointed to by its first argument. 110If that pointer is 111.Dv NULL , 112.Fn sbuf_new 113allocates a 114.Vt struct sbuf 115using 116.Xr malloc 9 . 117The 118.Fa buf 119argument is a pointer to a buffer in which to store the actual string; 120if it is 121.Dv NULL , 122.Fn sbuf_new 123will allocate one using 124.Xr malloc 9 . 125The 126.Fa length 127is the initial size of the storage buffer. 128The fourth argument, 129.Fa flags , 130may be comprised of the following flags: 131.Bl -tag -width ".Dv SBUF_AUTOEXTEND" 132.It Dv SBUF_FIXEDLEN 133The storage buffer is fixed at its initial size. 134Attempting to extend the sbuf beyond this size results in an overflow condition. 135.It Dv SBUF_AUTOEXTEND 136This indicates that the storage buffer may be extended as necessary, so long 137as resources allow, to hold additional data. 138.El 139.Pp 140Note that if 141.Fa buf 142is not 143.Dv NULL , 144it must point to an array of at least 145.Fa length 146characters. 147The result of accessing that array directly while it is in use by the 148sbuf is undefined. 149.Pp 150The 151.Fn sbuf_delete 152function clears the 153.Fa sbuf 154and frees any memory allocated for it. 155There must be a call to 156.Fn sbuf_delete 157for every call to 158.Fn sbuf_new . 159Any attempt to access the sbuf after it has been deleted will fail. 160.Pp 161The 162.Fn sbuf_clear 163function invalidates the contents of the 164.Fa sbuf 165and resets its position to zero. 166.Pp 167The 168.Fn sbuf_setpos 169function sets the 170.Fa sbuf Ns 's 171end position to 172.Fa pos , 173which is a value between zero and one less than the size of the 174storage buffer. 175This effectively truncates the sbuf at the new position. 176.Pp 177The 178.Fn sbuf_bcat 179function appends the first 180.Fa len 181bytes from the buffer 182.Fa buf 183to the 184.Fa sbuf . 185.Pp 186The 187.Fn sbuf_bcopyin 188function copies 189.Fa len 190bytes from the specified userland address into the 191.Fa sbuf . 192.Pp 193The 194.Fn sbuf_bcpy 195function replaces the contents of the 196.Fa sbuf 197with the first 198.Fa len 199bytes from the buffer 200.Fa buf . 201.Pp 202The 203.Fn sbuf_cat 204function appends the NUL-terminated string 205.Fa str 206to the 207.Fa sbuf 208at the current position. 209.Pp 210The 211.Fn sbuf_copyin 212function copies a NUL-terminated string from the specified userland 213address into the 214.Fa sbuf . 215If the 216.Fa len 217argument is non-zero, no more than 218.Fa len 219characters (not counting the terminating NUL) are copied; otherwise 220the entire string, or as much of it as can fit in the 221.Fa sbuf , 222is copied. 223.Pp 224The 225.Fn sbuf_cpy 226function replaces the contents of the 227.Fa sbuf 228with those of the NUL-terminated string 229.Fa str . 230This is equivalent to calling 231.Fn sbuf_cat 232with a fresh 233.Fa sbuf 234or one which position has been reset to zero with 235.Fn sbuf_clear 236or 237.Fn sbuf_setpos . 238.Pp 239The 240.Fn sbuf_printf 241function formats its arguments according to the format string pointed 242to by 243.Fa fmt 244and appends the resulting string to the 245.Fa sbuf 246at the current position. 247.Pp 248The 249.Fn sbuf_vprintf 250function behaves the same as 251.Fn sbuf_printf 252except that the arguments are obtained from the variable-length argument list 253.Fa ap . 254.Pp 255The 256.Fn sbuf_putc 257function appends the character 258.Fa c 259to the 260.Fa sbuf 261at the current position. 262.Pp 263The 264.Fn sbuf_trim 265function removes trailing whitespace from the 266.Fa sbuf . 267.Pp 268The 269.Fn sbuf_overflowed 270function returns a non-zero value if the 271.Fa sbuf 272overflowed. 273.Pp 274The 275.Fn sbuf_finish 276function null-terminates the 277.Fa sbuf 278and marks it as finished, which means that it may no longer be 279modified using 280.Fn sbuf_setpos , 281.Fn sbuf_cat , 282.Fn sbuf_cpy , 283.Fn sbuf_printf 284or 285.Fn sbuf_putc . 286.Pp 287The 288.Fn sbuf_data 289and 290.Fn sbuf_len 291functions return the actual string and its length, respectively; 292.Fn sbuf_data 293only works on a finished 294.Fa sbuf . 295.Fn sbuf_done 296returns non-zero if the sbuf is finished. 297.Sh NOTES 298If an operation caused an 299.Fa sbuf 300to overflow, most subsequent operations on it will fail until the 301.Fa sbuf 302is finished using 303.Fn sbuf_finish 304or reset using 305.Fn sbuf_clear , 306or its position is reset to a value between 0 and one less than the 307size of its storage buffer using 308.Fn sbuf_setpos , 309or it is reinitialized to a sufficiently short string using 310.Fn sbuf_cpy . 311.Sh RETURN VALUES 312The 313.Fn sbuf_new 314function returns 315.Dv NULL 316if it failed to allocate a storage buffer, and a pointer to the new 317.Fa sbuf 318otherwise. 319.Pp 320The 321.Fn sbuf_setpos 322function returns \-1 if 323.Fa pos 324was invalid, and zero otherwise. 325.Pp 326The 327.Fn sbuf_cat , 328.Fn sbuf_cpy , 329.Fn sbuf_printf , 330.Fn sbuf_putc , 331and 332.Fn sbuf_trim 333functions 334all return \-1 if the buffer overflowed, and zero otherwise. 335.Pp 336The 337.Fn sbuf_overflowed 338function 339returns a non-zero value if the buffer overflowed, and zero otherwise. 340.Pp 341The 342.Fn sbuf_data 343and 344.Fn sbuf_len 345functions return 346.Dv NULL 347and \-1, respectively, if the buffer overflowed. 348.Pp 349The 350.Fn sbuf_copyin 351function 352returns \-1 if copying string from userland failed, and number of bytes 353copied otherwise. 354.Sh SEE ALSO 355.Xr printf 3 , 356.Xr strcat 3 , 357.Xr strcpy 3 , 358.Xr copyin 9 , 359.Xr copyinstr 9 , 360.Xr printf 9 361.Sh HISTORY 362The 363.Nm 364family of functions first appeared in 365.Fx 4.4 . 366.Sh AUTHORS 367.An -nosplit 368The 369.Nm 370family of functions was designed by 371.An Poul-Henning Kamp Aq phk@FreeBSD.org 372and implemented by 373.An Dag-Erling Sm\(/orgrav Aq des@FreeBSD.org . 374Additional improvements were suggested by 375.An Justin T. Gibbs Aq gibbs@FreeBSD.org . 376Auto-extend support added by 377.An Kelly Yancey Aq kbyanc@FreeBSD.org . 378.Pp 379This manual page was written by 380.An Dag-Erling Sm\(/orgrav Aq des@FreeBSD.org . 381