chiark / gitweb /
594cbddfd8f1f8fdfe02dbcac843769b51c9950f
[mLib] / struct / buf.3.in
1 .\" -*-nroff-*-
2 .\"
3 .\" Manual for buffer handling
4 .\"
5 .\" (c) 2005, 2007, 2009, 2017, 2023, 2024 Straylight/Edgeware
6 .\"
7 .
8 .\"----- Licensing notice ---------------------------------------------------
9 .\"
10 .\" This file is part of the mLib utilities library.
11 .\"
12 .\" mLib is free software: you can redistribute it and/or modify it under
13 .\" the terms of the GNU Library General Public License as published by
14 .\" the Free Software Foundation; either version 2 of the License, or (at
15 .\" your option) any later version.
16 .\"
17 .\" mLib is distributed in the hope that it will be useful, but WITHOUT
18 .\" ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
19 .\" FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Library General Public
20 .\" License for more details.
21 .\"
22 .\" You should have received a copy of the GNU Library General Public
23 .\" License along with mLib.  If not, write to the Free Software
24 .\" Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
25 .\" USA.
26 .
27 .\"--------------------------------------------------------------------------
28 .so ../defs.man \" @@@PRE@@@
29 .
30 .\"--------------------------------------------------------------------------
31 .TH buf 3mLib "23 September 2005" "Straylight/Edgeware" "mLib utilities library"
32 .\" @BBASE
33 .\" @BLIM
34 .\" @BCUR
35 .\" @BSZ
36 .\" @BLEN
37 .\" @BLEFT
38 .\" @BSTEP
39 .\" @BBAD
40 .\" @BOK
41 .\" @BENSURE
42 .
43 .\" @DBBASE
44 .\" @DBLIM
45 .\" @DBCUR
46 .\" @DBSZ
47 .\" @DBLEN
48 .\" @DBLEFT
49 .\" @DBSTEP
50 .\" @DBBAD
51 .\" @DBOK
52 .\" @DBENSURE
53 .
54 .\" @buf_init
55 .
56 .\" @dbuf_create
57 .\" @dbuf_reset
58 .\" @dbuf_destroy
59 .\" @DBCREATE
60 .\" @DBRESET
61 .\" @DBDESTROY
62 .\" @DBUF_INIT
63 .\" @DBUF_BUF
64 .
65 .\" @buf_break
66 .\" @buf_flip
67 .\" @buf_ensure
68 .\" @buf_tryextend
69 .\" @buf_get
70 .\" @buf_put
71 .\" @buf_fill
72 .\" @dbuf_break
73 .\" @dbuf_flip
74 .\" @dbuf_ensure
75 .\" @dbuf_tryextend
76 .\" @dbuf_get
77 .\" @dbuf_put
78 .\" @dbuf_fill
79 .
80 .\" @buf_getbyte
81 .\" @buf_putbyte
82 .\" @dbuf_getbyte
83 .\" @dbuf_putbyte
84 .
85 .\" @buf_putstrf
86 .\" @buf_vputstrf
87 .\" @dbuf_putstrf
88 .\" @dbuf_vputstrf
89 .\" @buf_printops
90 .
91 .\" @buf_getu8
92 .\" @buf_getu16
93 .\" @buf_getu16b
94 .\" @buf_getu16l
95 .\" @buf_getu24
96 .\" @buf_getu24b
97 .\" @buf_getu24l
98 .\" @buf_getu32
99 .\" @buf_getu32b
100 .\" @buf_getu32l
101 .\" @buf_getu64
102 .\" @buf_getu64b
103 .\" @buf_getu64l
104 .\" @buf_getk64
105 .\" @buf_getk64b
106 .\" @buf_getk64l
107 .\" @dbuf_getu8
108 .\" @dbuf_getu16
109 .\" @dbuf_getu16b
110 .\" @dbuf_getu16l
111 .\" @dbuf_getu24
112 .\" @dbuf_getu24b
113 .\" @dbuf_getu24l
114 .\" @dbuf_getu32
115 .\" @dbuf_getu32b
116 .\" @dbuf_getu32l
117 .\" @dbuf_getu64
118 .\" @dbuf_getu64b
119 .\" @dbuf_getu64l
120 .\" @dbuf_getk64
121 .\" @dbuf_getk64b
122 .\" @dbuf_getk64l
123 .
124 .\" @buf_putu8
125 .\" @buf_putu16
126 .\" @buf_putu16b
127 .\" @buf_putu16l
128 .\" @buf_putu24
129 .\" @buf_putu24b
130 .\" @buf_putu24l
131 .\" @buf_putu32
132 .\" @buf_putu32b
133 .\" @buf_putu32l
134 .\" @buf_putu64
135 .\" @buf_putu64b
136 .\" @buf_putu64l
137 .\" @buf_putk64
138 .\" @buf_putk64b
139 .\" @buf_putk64l
140 .\" @dbuf_putu8
141 .\" @dbuf_putu16
142 .\" @dbuf_putu16b
143 .\" @dbuf_putu16l
144 .\" @dbuf_putu24
145 .\" @dbuf_putu24b
146 .\" @dbuf_putu24l
147 .\" @dbuf_putu32
148 .\" @dbuf_putu32b
149 .\" @dbuf_putu32l
150 .\" @dbuf_putu64
151 .\" @dbuf_putu64b
152 .\" @dbuf_putu64l
153 .\" @dbuf_putk64
154 .\" @dbuf_putk64b
155 .\" @dbuf_putk64l
156 .
157 .\" @buf_getf32
158 .\" @buf_getf32l
159 .\" @buf_getf32b
160 .\" @buf_putf32
161 .\" @buf_putf32l
162 .\" @buf_putf32b
163 .\" @buf_getf64
164 .\" @buf_getf64l
165 .\" @buf_getf64b
166 .\" @buf_putf64
167 .\" @buf_putf64l
168 .\" @buf_putf64b
169 .\" @dbuf_getf32
170 .\" @dbuf_getf32l
171 .\" @dbuf_getf32b
172 .\" @dbuf_putf32
173 .\" @dbuf_putf32l
174 .\" @dbuf_putf32b
175 .\" @dbuf_getf64
176 .\" @dbuf_getf64l
177 .\" @dbuf_getf64b
178 .\" @dbuf_putf64
179 .\" @dbuf_putf64l
180 .\" @dbuf_putf64b
181 .
182 .\" @buf_getbuf8
183 .\" @buf_getbuf16
184 .\" @buf_getbuf16b
185 .\" @buf_getbuf16l
186 .\" @buf_getbuf24
187 .\" @buf_getbuf24b
188 .\" @buf_getbuf24l
189 .\" @buf_getbuf32
190 .\" @buf_getbuf32b
191 .\" @buf_getbuf32l
192 .\" @buf_getbuf64
193 .\" @buf_getbuf64b
194 .\" @buf_getbuf64l
195 .\" @buf_getbufz
196 .\" @dbuf_getbuf8
197 .\" @dbuf_getbuf16
198 .\" @dbuf_getbuf16b
199 .\" @dbuf_getbuf16l
200 .\" @dbuf_getbuf24
201 .\" @dbuf_getbuf24b
202 .\" @dbuf_getbuf24l
203 .\" @dbuf_getbuf32
204 .\" @dbuf_getbuf32b
205 .\" @dbuf_getbuf32l
206 .\" @dbuf_getbuf64
207 .\" @dbuf_getbuf64b
208 .\" @dbuf_getbuf64l
209 .\" @dbuf_getbufz
210 .
211 .\" @buf_putbuf8
212 .\" @buf_putbuf16
213 .\" @buf_putbuf16b
214 .\" @buf_putbuf16l
215 .\" @buf_putbuf24
216 .\" @buf_putbuf24b
217 .\" @buf_putbuf24l
218 .\" @buf_putbuf32
219 .\" @buf_putbuf32b
220 .\" @buf_putbuf32l
221 .\" @buf_putbuf64
222 .\" @buf_putbuf64b
223 .\" @buf_putbuf64l
224 .\" @buf_putbufz
225 .\" @dbuf_putbuf8
226 .\" @dbuf_putbuf16
227 .\" @dbuf_putbuf16b
228 .\" @dbuf_putbuf16l
229 .\" @dbuf_putbuf24
230 .\" @dbuf_putbuf24b
231 .\" @dbuf_putbuf24l
232 .\" @dbuf_putbuf32
233 .\" @dbuf_putbuf32b
234 .\" @dbuf_putbuf32l
235 .\" @dbuf_putbuf64
236 .\" @dbuf_putbuf64b
237 .\" @dbuf_putbuf64l
238 .\" @dbuf_putbufz
239 .
240 .\" @buf_getmem8
241 .\" @buf_getmem16
242 .\" @buf_getmem16b
243 .\" @buf_getmem16l
244 .\" @buf_getmem24
245 .\" @buf_getmem24b
246 .\" @buf_getmem24l
247 .\" @buf_getmem32
248 .\" @buf_getmem32b
249 .\" @buf_getmem32l
250 .\" @buf_getmem64
251 .\" @buf_getmem64b
252 .\" @buf_getmem64l
253 .\" @buf_getmemz
254 .\" @dbuf_getmem8
255 .\" @dbuf_getmem16
256 .\" @dbuf_getmem16b
257 .\" @dbuf_getmem16l
258 .\" @dbuf_getmem24
259 .\" @dbuf_getmem24b
260 .\" @dbuf_getmem24l
261 .\" @dbuf_getmem32
262 .\" @dbuf_getmem32b
263 .\" @dbuf_getmem32l
264 .\" @dbuf_getmem64
265 .\" @dbuf_getmem64b
266 .\" @dbuf_getmem64l
267 .\" @dbuf_getmemz
268 .
269 .\" @buf_putmem8
270 .\" @buf_putmem16
271 .\" @buf_putmem16b
272 .\" @buf_putmem16l
273 .\" @buf_putmem24
274 .\" @buf_putmem24b
275 .\" @buf_putmem24l
276 .\" @buf_putmem32
277 .\" @buf_putmem32b
278 .\" @buf_putmem32l
279 .\" @buf_putmem64
280 .\" @buf_putmem64b
281 .\" @buf_putmem64l
282 .\" @buf_putmemz
283 .\" @dbuf_putmem8
284 .\" @dbuf_putmem16
285 .\" @dbuf_putmem16b
286 .\" @dbuf_putmem16l
287 .\" @dbuf_putmem24
288 .\" @dbuf_putmem24b
289 .\" @dbuf_putmem24l
290 .\" @dbuf_putmem32
291 .\" @dbuf_putmem32b
292 .\" @dbuf_putmem32l
293 .\" @dbuf_putmem64
294 .\" @dbuf_putmem64b
295 .\" @dbuf_putmem64l
296 .\" @dbuf_putmemz
297 .
298 .\" @buf_putstr8
299 .\" @buf_putstr16
300 .\" @buf_putstr16b
301 .\" @buf_putstr16l
302 .\" @buf_putstr24
303 .\" @buf_putstr24b
304 .\" @buf_putstr24l
305 .\" @buf_putstr32
306 .\" @buf_putstr32b
307 .\" @buf_putstr32l
308 .\" @buf_putstr64
309 .\" @buf_putstr64b
310 .\" @buf_putstr64l
311 .\" @buf_putstrz
312 .\" @dbuf_putstr8
313 .\" @dbuf_putstr16
314 .\" @dbuf_putstr16b
315 .\" @dbuf_putstr16l
316 .\" @dbuf_putstr24
317 .\" @dbuf_putstr24b
318 .\" @dbuf_putstr24l
319 .\" @dbuf_putstr32
320 .\" @dbuf_putstr32b
321 .\" @dbuf_putstr32l
322 .\" @dbuf_putstr64
323 .\" @dbuf_putstr64b
324 .\" @dbuf_putstr64l
325 .\" @dbuf_putstrz
326 .
327 .\" @buf_getdstr8
328 .\" @buf_getdstr16
329 .\" @buf_getdstr16b
330 .\" @buf_getdstr16l
331 .\" @buf_getdstr24
332 .\" @buf_getdstr24b
333 .\" @buf_getdstr24l
334 .\" @buf_getdstr32
335 .\" @buf_getdstr32b
336 .\" @buf_getdstr32l
337 .\" @buf_getdstr64
338 .\" @buf_getdstr64b
339 .\" @buf_getdstr64l
340 .\" @buf_getdstrz
341 .\" @dbuf_getdstr8
342 .\" @dbuf_getdstr16
343 .\" @dbuf_getdstr16b
344 .\" @dbuf_getdstr16l
345 .\" @dbuf_getdstr24
346 .\" @dbuf_getdstr24b
347 .\" @dbuf_getdstr24l
348 .\" @dbuf_getdstr32
349 .\" @dbuf_getdstr32b
350 .\" @dbuf_getdstr32l
351 .\" @dbuf_getdstr64
352 .\" @dbuf_getdstr64b
353 .\" @dbuf_getdstr64l
354 .\" @dbuf_getdstrz
355 .
356 .\" @buf_putdstr8
357 .\" @buf_putdstr16
358 .\" @buf_putdstr16b
359 .\" @buf_putdstr16l
360 .\" @buf_putdstr24
361 .\" @buf_putdstr24b
362 .\" @buf_putdstr24l
363 .\" @buf_putdstr32
364 .\" @buf_putdstr32b
365 .\" @buf_putdstr32l
366 .\" @buf_putdstr64
367 .\" @buf_putdstr64b
368 .\" @buf_putdstr64l
369 .\" @buf_putdstrz
370 .\" @dbuf_putdstr8
371 .\" @dbuf_putdstr16
372 .\" @dbuf_putdstr16b
373 .\" @dbuf_putdstr16l
374 .\" @dbuf_putdstr24
375 .\" @dbuf_putdstr24b
376 .\" @dbuf_putdstr24l
377 .\" @dbuf_putdstr32
378 .\" @dbuf_putdstr32b
379 .\" @dbuf_putdstr32l
380 .\" @dbuf_putdstr64
381 .\" @dbuf_putdstr64b
382 .\" @dbuf_putdstr64l
383 .\" @dbuf_putdstrz
384 .
385 .\" @buf_putstrf8
386 .\" @buf_putstrf16
387 .\" @buf_putstrf16b
388 .\" @buf_putstrf16l
389 .\" @buf_putstrf24
390 .\" @buf_putstrf24b
391 .\" @buf_putstrf24l
392 .\" @buf_putstrf32
393 .\" @buf_putstrf32b
394 .\" @buf_putstrf32l
395 .\" @buf_putstrf64
396 .\" @buf_putstrf64b
397 .\" @buf_putstrf64l
398 .\" @buf_putstrfz
399 .\" @buf_vputstrf8
400 .\" @buf_vputstrf16
401 .\" @buf_vputstrf16b
402 .\" @buf_vputstrf16l
403 .\" @buf_vputstrf24
404 .\" @buf_vputstrf24b
405 .\" @buf_vputstrf24l
406 .\" @buf_vputstrf32
407 .\" @buf_vputstrf32b
408 .\" @buf_vputstrf32l
409 .\" @buf_vputstrf64
410 .\" @buf_vputstrf64b
411 .\" @buf_vputstrf64l
412 .\" @buf_vputstrfz
413 .\" @dbuf_putstrf8
414 .\" @dbuf_putstrf16
415 .\" @dbuf_putstrf16b
416 .\" @dbuf_putstrf16l
417 .\" @dbuf_putstrf24
418 .\" @dbuf_putstrf24b
419 .\" @dbuf_putstrf24l
420 .\" @dbuf_putstrf32
421 .\" @dbuf_putstrf32b
422 .\" @dbuf_putstrf32l
423 .\" @dbuf_putstrf64
424 .\" @dbuf_putstrf64b
425 .\" @dbuf_putstrf64l
426 .\" @dbuf_putstrfz
427 .\" @dbuf_vputstrf8
428 .\" @dbuf_vputstrf16
429 .\" @dbuf_vputstrf16b
430 .\" @dbuf_vputstrf16l
431 .\" @dbuf_vputstrf24
432 .\" @dbuf_vputstrf24b
433 .\" @dbuf_vputstrf24l
434 .\" @dbuf_vputstrf32
435 .\" @dbuf_vputstrf32b
436 .\" @dbuf_vputstrf32l
437 .\" @dbuf_vputstrf64
438 .\" @dbuf_vputstrf64b
439 .\" @dbuf_vputstrf64l
440 .\" @dbuf_vputstrfz
441 .
442 .\" @BUF_ENCLOSETAG
443 .\" @BUF_ENCLOSEITAG
444 .\" @BUF_ENCLOSEKTAG
445 .\" @BUF_ENCLOSEZTAG
446 .\" @BUF_ENCLOSE8
447 .\" @BUF_ENCLOSE16
448 .\" @BUF_ENCLOSE16_L
449 .\" @BUF_ENCLOSE16_B
450 .\" @BUF_ENCLOSE24
451 .\" @BUF_ENCLOSE24_L
452 .\" @BUF_ENCLOSE24_B
453 .\" @BUF_ENCLOSE32
454 .\" @BUF_ENCLOSE32_L
455 .\" @BUF_ENCLOSE32_B
456 .\" @BUF_ENCLOSE64
457 .\" @BUF_ENCLOSE64_L
458 .\" @BUF_ENCLOSE64_B
459 .\" @BUF_ENCLOSEZ
460 .\" @DBUF_ENCLOSETAG
461 .\" @DBUF_ENCLOSEITAG
462 .\" @DBUF_ENCLOSEKTAG
463 .\" @DBUF_ENCLOSEZTAG
464 .\" @DBUF_ENCLOSE8
465 .\" @DBUF_ENCLOSE16
466 .\" @DBUF_ENCLOSE16_L
467 .\" @DBUF_ENCLOSE16_B
468 .\" @DBUF_ENCLOSE24
469 .\" @DBUF_ENCLOSE24_L
470 .\" @DBUF_ENCLOSE24_B
471 .\" @DBUF_ENCLOSE32
472 .\" @DBUF_ENCLOSE32_L
473 .\" @DBUF_ENCLOSE32_B
474 .\" @DBUF_ENCLOSE64
475 .\" @DBUF_ENCLOSE64_L
476 .\" @DBUF_ENCLOSE64_B
477 .\" @DBUF_ENCLOSEZ
478 .
479 .\"--------------------------------------------------------------------------
480 .SH NAME
481 buf \- reading and writing stuff in buffers
482 .
483 .\"--------------------------------------------------------------------------
484 .SH SYNOPSIS
485 .
486 .nf
487 .B "#include <mLib/dstr.h>"
488 .PP
489 .B "typedef struct { ...\& } buf;"
490 .B "typedef struct { ...\& } dbuf;"
491 .PP
492 .BI "void buf_init(buf *" b ", void *" p ", size_t " sz );
493 .BI "void dbuf_create(dbuf *" db );
494 .BI "void dbuf_reset(dbuf *" db );
495 .BI "void dbuf_destroy(dbuf *" db );
496 .BI "buf *DBUF_BUF(dbuf *" db );
497 .BI "void DBCREATE(dbuf *" db );
498 .BI "void DBRESET(dbuf *" db );
499 .BI "void DBDESTROY(dbuf *" db );
500 .B "#define DBUF_INIT ..."
501 .PP
502 .fi
503 All of the following functions and macros exist in two variants:
504 one with a name beginning
505 .BR buf_ ,
506 .BR B ,
507 or
508 .BR BUF_ ,
509 and taking a first argument of type
510 .BR "buf *" ;
511 and a corresponding similarly named version with name beginning instead
512 .BR dbuf_ ,
513 .BR DB ,
514 or
515 .BR DBUF_ ,
516 and taking a first argument of type
517 .BR "dbuf *" .
518 .nf
519 .PP
520 .BI "void buf_flip(buf *" b );
521 .BI "octet *BBASE(buf *" b );
522 .BI "octet *BLIM(buf *" b );
523 .BI "octet *BCUR(buf *" b );
524 .BI "ptrdiff_t BSZ(buf *" b );
525 .BI "ptrdiff_t BLEN(buf *" b );
526 .BI "ptrdiff_t BLEFT(buf *" b );
527 .BI "void BFLIP(buf *" b );
528 .PP
529 .BI "int buf_break(buf *" b );
530 .BI "int BBREAK(buf *" b );
531 .BI "int BBAD(buf *" b );
532 .BI "int BOK(buf *" b );
533 .PP
534 .BI "int buf_ensure(buf *" b ", size_t " sz );
535 .BI "int buf_tryextend(buf *" b ", size_t " sz );
536 .BI "int BENSURE(buf *" b ", size_t " sz );
537 .BI "octet *BSTEP(buf *" b ", size_t " sz );
538 .PP
539 .BI "void *buf_get(buf *" b ", size_t " sz );
540 .BI "int buf_put(buf *" b ", const void *" p ", size_t " sz );
541 .BI "int buf_fill(buf *" b ", int " ch ", size_t " sz );
542 .PP
543 .BI "int buf_getbyte(buf *" b );
544 .BI "int buf_putbyte(buf *" b ", int " ch );
545 .PP
546 .BI "int buf_putstr(buf *" b ", const char *" p ", ...);"
547 .BI "int buf_vputstr(buf *" b ", const char *" p ", va_list *" ap );
548 .PP
549 .fi
550 For
551 .I suff
552 in
553 .BR 8 ,
554 .BR 16 ,
555 .BR 16l ,
556 .BR 16b ,
557 .BR 24 ,
558 .BR 24l ,
559 .BR 24b ,
560 .BR 32 ,
561 .BR 32l ,
562 and
563 .BR 32b ,
564 and, if a 64-bit integer type is available,
565 .BR 64 ,
566 .BR 64l ,
567 and
568 .BR 64b :
569 .nf
570 .BI "int buf_putu" suff "(buf *" b ", uint" suff " " w );
571 .BI "int buf_getu" suff "(buf *" b ", uint" suff " *" w );
572 .PP
573 .fi
574 For
575 .I suff
576 in
577 .BR 64 ,
578 .BR 64l ,
579 and
580 .BR 64b :
581 .nf
582 .BI "int buf_putk" suff "(buf *" b ", kludge64 " w );
583 .BI "int buf_getk" suff "(buf *" b ", kludge64 *" w );
584 .PP
585 .BI "int buf_getf32(buf *" b ", float " x );
586 .BI "int buf_getf32l(buf *" b ", float " x );
587 .BI "int buf_getf32b(buf *" b ", float " x );
588 .BI "int buf_getf64(buf *" b ", double " x );
589 .BI "int buf_getf64l(buf *" b ", double " x );
590 .BI "int buf_getf64b(buf *" b ", double " x );
591 .BI "int buf_putf32(buf *" b ", float *" x_out );
592 .BI "int buf_putf32l(buf *" b ", float *" x_out );
593 .BI "int buf_putf32b(buf *" b ", float *" x_out );
594 .BI "int buf_putf64(buf *" b ", double *" x_out );
595 .BI "int buf_putf64l(buf *" b ", double *" x_out );
596 .BI "int buf_putf64b(buf *" b ", double *" x_out );
597 .PP
598 .ta 2n
599 .BI "BUF_ENCLOSETAG(" tag ", buf *" b ", size_t " mk ", " check ", " poke ", size_t " lensz )
600 .I "    body"
601 .BI "BUF_ENCLOSEITAG(" tag ", buf *" b ", size_t " mk ", " W )
602 .I "    body"
603 .BI "BUF_ENCLOSEKTAG(" tag ", buf *" b ", size_t " mk ", " W )
604 .I "    body"
605 .BI "BUF_ENCLOSEZTAG(" tag ", buf *" b )
606 .I "    body"
607 .PP
608 .fi
609 For
610 .I suff
611 in
612 .BR 8 ,
613 .BR 16 ,
614 .BR 16_L ,
615 .BR 16_B ,
616 .BR 24 ,
617 .BR 24_L ,
618 .BR 24_B ,
619 .BR 32 ,
620 .BR 32_L ,
621 .BR 32_B ,
622 .BR 64 ,
623 .BR 64_L ,
624 and
625 .BR 64_B ,
626 .nf
627 .ta 2n
628 .BI "BUF_ENCLOSE" suff "(buf *" b ", size_t " mk )
629 .I "    body"
630 .PP
631 .BI "BUF_ENCLOSEZ(buf *" b )
632 .I "    body"
633 .PP
634 .fi
635 For
636 .I suff
637 in
638 .BR 8 ,
639 .BR 16 ,
640 .BR 16l ,
641 .BR 16b ,
642 .BR 24 ,
643 .BR 24l ,
644 .BR 24b ,
645 .BR 32 ,
646 .BR 32l ,
647 .BR 32b ,
648 .BR 64 ,
649 .BR 64l ,
650 .BR 64b ,
651 and
652 .BR z :
653 .nf
654 .BI "int buf_putstr" suff "(buf *" b ", const char *" p );
655 .BI "int buf_putstr" suff "(buf *" b ", const char *" p ", ...);"
656 .BI "int buf_vputstr" suff "(buf *" b ", const char *" p ", va_list *" ap );
657 .BI "int buf_putdstr" suff "(buf *" b ", dstr *" d );
658 .BI "int buf_getdstr" suff "(buf *" b ", dstr *" d );
659 .BI "int buf_putbuf" suff "(buf *" b ", buf *" bb );
660 .BI "int buf_getbuf" suff "(buf *" b ", buf *" bb );
661 .BI "int buf_putmem" suff "(buf *" b ", const void *" p ", size_t " sz );
662 .BI "void *buf_getmem" suff "(buf *" b ", size_t *" sz );
663 .PP
664 .fi
665 For
666 .I suff
667 in
668 .BR 64 ,
669 .BR 64l ,
670 and
671 .BR 64b :
672 .nf
673 .BI "int buf_putf" suff "(buf *" b ", double " x );
674 .BI "int buf_getf" suff "(buf *" b ", double *" x );
675 .fi
676 .
677 .\"--------------------------------------------------------------------------
678 .SH DESCRIPTION
679 The
680 .B buf
681 interface allows relatively convenient reading and writing of structured
682 binary data from and to fixed-size memory buffers.  It's useful for
683 formatting and parsing down network data packets, for example.
684 .
685 .SS "Buffer basics"
686 A buffer has three important pointers associated with it:
687 .TP
688 .I base
689 The base address of the buffer.
690 .TP
691 .I limit
692 Just past the last usable byte in the buffer
693 .TP
694 .I current
695 The position in the buffer at which the next read or write will occur.
696 .PP
697 A buffer is created using the
698 .B buf_init
699 function.  You must pass it the buffer base address and size, and a
700 pointer to a
701 .B buf
702 structure to fill in.  It doesn't allocate any memory, so you don't need
703 to dispose of the
704 .B buf
705 structure in any way before forgetting about it.
706 .PP
707 A collection of macros is provided for finding the positions of the
708 various interesting pointers known about a buffer, and the sizes of the
709 regions of memory they imply.
710 .TP
711 .B BBASE
712 The buffer's
713 .I base
714 pointer.
715 .TP
716 .B BLIM
717 The buffer's
718 .I limit
719 pointer.
720 .TP
721 .B BCUR
722 The buffer's
723 .I current
724 pointer.
725 .TP
726 .B BSZ
727 The size of the buffer; i.e.,
728 .I limit
729 \-
730 .IR base .
731 .TP
732 .B BLEN
733 The length of data in the buffer (if writing) or the amount of data
734 read (if reading); i.e.,
735 .I current
736 \-
737 .IR base .
738 .TP
739 .B BLEFT
740 The amount of space left in the buffer (if writing) or the amount of
741 data yet to read (if reading); i.e.,
742 .I limit
743 \-
744 .IR current .
745 .PP
746 The function
747 .B buf_flip
748 takes a buffer which has been used for writing, and makes it suitable
749 for reading.  This turns out to be useful when building packets in
750 multi-layered networking software.  Its precise behaviour is to preserve
751 .IR base ,
752 to set
753 .I limit
754 to
755 .IR current ,
756 and to set
757 .I current
758 to
759 .IR base .
760 There is a macro version,
761 .BR BFLIP ,
762 which does the same thing,
763 but it may evaluate its buffer argument multiple times.
764 .PP
765 A buffer can be
766 .IR broken ,
767 to indicate that it has overflowed or that its contents are otherwise
768 invalid.  The various buffer access functions described below all fail
769 on a broken buffer, and any errors they encounter cause the buffer to
770 become broken.  Most simple programs which only use the supplied buffer
771 access functions can avoid the tedium of error-checking every function
772 call and just check the brokenness state at the end of their run.
773 .PP
774 The function
775 .B buf_break
776 or its
777 macro equivalent
778 .B BBREAK
779 will break a buffer:
780 the function returns \-1 as a possible, but minor, convenience;
781 the macro expands to a statement and cannot return a value.
782 The macro
783 .B BBAD
784 reports true (nonzero) if its buffer argument is broken, or false (zero)
785 otherwise; its counterpart
786 .B BOK
787 reports true if the buffer is OK, and false if it is broken.
788 .
789 .SS "Low-level buffer access"
790 Access to the data in the buffer is usually sequential.  The
791 .B BENSURE
792 macro (or the equivalent
793 .B buf_ensure
794 function) checks that the buffer is OK and that there is enough space
795 remaining in the buffer for
796 .I sz
797 bytes: if so, it returns zero; otherwise it breaks the buffer and
798 returns \-1.
799 .PP
800 The
801 .B BSTEP
802 macro advances the buffer's
803 .I current
804 pointer by
805 .I sz
806 bytes.  It does no bounds checking.  Together with
807 .BR BENSURE ,
808 this provides sequential access to the buffer's contents.
809 .PP
810 The
811 .B buf_get
812 function is the basis of most buffer access functions, whether for
813 reading or writing.  If the buffer is OK, and there are
814 .I sz
815 or more bytes remaining, it steps the buffer's
816 .I current
817 pointer by
818 .I sz
819 and returns the
820 .I original
821 (pre-stepping)
822 .I current
823 pointer; otherwise it breaks the buffer if necessary, and returns a null
824 pointer.
825 .PP
826 The
827 .B buf_put
828 function writes
829 .I sz
830 bytes of data starting at
831 .I p
832 to the buffer.  If it succeeded, it returns 0; otherwise it returns \-1.
833 .PP
834 The
835 .B buf_fill
836 function writes
837 .I sz
838 copies of the byte
839 .I ch
840 to the buffer, as if by calling
841 .BR memset (3).
842 If it succeeds, it returns 0; otherwise it returns \-1.
843 .
844 .SS "Formatted buffer access"
845 The function
846 .B buf_getbyte
847 returns the next byte from a buffer as a nonnegative integer, or \-1 on
848 error.  The function
849 .B buf_putbyte
850 writes its argument to a buffer, and returns 0 on succes; it returns \-1
851 if it failed.
852 .PP
853 Many of the remaining functions deal with integer formatting and buffer
854 lengths.  The functions support 8-, 16-, 24- and 32-bit integers, in
855 big- or little-endian order; on platforms with 64-bit integers, these
856 are supported too.  The functions' names carry a suffix which is the
857 width in bits of the integers they deal with and an optional
858 .RB ` l '
859 for little- or
860 .RB ` b '
861 for big-endian byte order.  (The variant with no letter uses big-endian
862 order.  Use of these variants tends to mean `I don't really care, but be
863 consistent,' and is not recommended if you have an externally-defined
864 spec you're meant to be compatible with.)
865 .PP
866 The function
867 .BI buf_getu suff
868 reads an integer.  On success, it stores the integer it read at the
869 address
870 .I w
871 given, and returns zero; on failure, it returns \-1.  The function
872 .BI buf_putu suff
873 write an integer.  It returns zero on success or \-1 on failure.
874 .PP
875 For (portability to) platforms without 64-bit integers, the functions
876 .B buf_getk64
877 and
878 .B buf_putk64
879 (and
880 .RB ` l '-
881 and
882 .RB ` b '-suffixed
883 variants) perform the necessary functionality, but acting on the
884 .B kludge64
885 type; see
886 .BR bits (3).
887 .PP
888 The functions
889 .BR buf_getf32 ,
890 .BR buf_getf32l ,
891 and
892 .BR buf_getf32b ,
893 and
894 .BR buf_getf64 ,
895 .BR buf_getf64l ,
896 and
897 .BR buf_getf64b ,
898 read floating-point values
899 in IEEE\ 754 Binary32 and Binary64 format
900 from the buffer;
901 as usual, the suffix indicates the format and byte ordering convention.
902 On success, they store the result in
903 .BI *x
904 and return zero;
905 on failure, they break the buffer and return zero.
906 The functions
907 .BR buf_putf32 ,
908 .BR buf_putf32l ,
909 and
910 .BR buf_putf32b ,
911 and
912 .BR buf_putf64 ,
913 .BR buf_putf64l ,
914 and
915 .BR buf_putf64b
916 write floating-point numbers
917 in IEEE\ 754 Binary32 and Binary64 format
918 from the buffer.
919 On success, they return zero; on failure, they return \-1.
920 Note that these functions use IEEE\ 754 format
921 even if this is not the platform-native floating-point representation:
922 they use the
923 .BR fltfmt (3)
924 functions to do their work.
925 Specifically,
926 they use the
927 .B FLTRND_NEAREVEN
928 rounding convention,
929 and they ignore
930 .BR FLTERR_INEXACT ,
931 .BR FLTERR_UFLOW ,
932 and
933 .B FLTERR_OFLOW
934 errors,
935 and fail on
936 .B FLTERR_INVAL
937 and
938 .B FLTERR_REPR
939 errors.
940 If more subtle control over error handling is necessary,
941 use the
942 .BR fltfmt (3)
943 functions directly.
944 .PP
945 The function
946 .B buf_putstrf
947 processes a
948 .BR printf (3)-like
949 format string and arguments,
950 writing the output to the buffer.
951 The function
952 .B buf_vputstrf
953 does the same,
954 except that it reads arguments from a
955 .B va_list
956 captured argument tail,
957 leaving the tail ready to read the next unprocessed argument.
958 Both functions return the number of bytes written on success
959 or \-1 on failure.
960 Note that these functions apply no length framing or termination.
961 They are implemented using
962 .BR gprintf (3);
963 the output operations table is exposed as
964 .BR buf_printops ;
965 the functions expect the output pointer to be the address of the output
966 .BR buf .
967 .PP
968 Functions which deal with block lengths assume the length is prefixed to
969 the data, and don't include themselves.  They come in all of the integer
970 size variants, including 64-bits even on platforms without 64-bit integers;
971 they also have an additional
972 .RB ` z '
973 variant, which deals with zero-terminated data.  No checks are done on
974 writing that the data written contains no zero bytes.
975 .PP
976 The function
977 .BI buf_getmem suff
978 fetches a block of data.  On success, it returns its base address and
979 stores its length at the given address; on failure, it returns null.
980 The function
981 .BI buf_putmem suff
982 writes a block of data; it return zero on success or \-1 on failure.
983 .PP
984 The functon
985 .BI buf_getbuf suff
986 fetches a block of data and makes a second buffer point to it, i.e.,
987 setting its
988 .I base
989 and
990 .I current
991 pointers to the start of the block and its
992 .I limit
993 pointer to just past the end.  No copying of bulk data is performed.
994 The function
995 .BI buf_putbuf suff
996 writes the contents of a buffer (i.e., between its
997 .I base
998 and
999 .I current
1000 pointers).  The function
1001 .BI buf_getdstr suff
1002 fetches a block of data and append it to a dynamic string (see
1003 .BR dstr (3)).
1004 The function
1005 .BI buf_putdstr suff
1006 writes the contents of a dynamic string to a buffer.  Finally, the
1007 function
1008 .BI buf_putstr suff
1009 writes a standard C null-terminated string to a buffer.  All these
1010 functions return zero on success or \-1 on failure.
1011 .PP
1012 The function
1013 .BI buf_putstrf suff
1014 processes a
1015 .BR printf (3)-like
1016 format string and arguments,
1017 writing the output to the buffer.
1018 The function
1019 .BI buf_vputstrf suff
1020 does the same,
1021 except that it reads arguments from a
1022 .B va_list
1023 captured argument tail,
1024 leaving the tail ready to read the next unprocessed argument.
1025 Both functions return the number of bytes written on success
1026 or \-1 on failure.
1027 These functions add framing around the output:
1028 either a length prefix, or a trailing zero byte.
1029 .PP
1030 The
1031 .BI BUF_ENCLOSE suff
1032 macros are syntactically statement heads.
1033 (Notice that these macros use
1034 .RB ` _L '
1035 and
1036 .RB ` _B '
1037 suffixes for little- and big-endian byte order.)
1038 They leave space in the buffer for appropriate length framing,
1039 and execute the following
1040 .I body
1041 statement
1042 (which, of course, can be a compound statement enclosed in braces).
1043 When the
1044 .I body
1045 completes, the macro fills in space
1046 with the length of material written by the
1047 .IR body .
1048 The
1049 .I mk
1050 argument should be a variable of type
1051 .B size_t
1052 which will be overwritten by the macro.
1053 If the material is so large that its won't fit in the space
1054 then the buffer is broken.
1055 The
1056 .B BUF_ENCLOSEZ
1057 macro is similar,
1058 except that it just writes a terminating zero byte
1059 after whatever material was written by the
1060 .IR body .
1061 .PP
1062 The
1063 .BR BUF_ENCLOSE ...\&
1064 macros are based on lower-level machinery.
1065 The
1066 .B BUF_ENCLOSEITAG
1067 macro takes an additional argument
1068 .IR W ;
1069 it leaves
1070 .BI SZ_ W
1071 bytes for the length,
1072 checks that the length doesn't exceed
1073 .BI MASK W \fR,
1074 and stores the length using
1075 .BI STORE W \fR;
1076 all of these constants and macros are defined in
1077 .BR <mLib/bits.h> .
1078 The
1079 .B BUF_ENCLOSEKTAG
1080 is similar, except that it uses the
1081 .B kludge64
1082 machinery to handle 64-bit length fields.
1083 The
1084 .B BUF_ENCLOSEZTAG
1085 macro is superficially similar,
1086 but much simpler,
1087 since it all it does is write a zero byte after its
1088 .I body
1089 completes.
1090 All of those macros also take an additional
1091 .I tag
1092 argument
1093 used to scope the internal labels they construct:
1094 see
1095 .BR control (3)
1096 for the details on how this works.
1097 .PP
1098 The
1099 .B BUF_ENCLOSEITAG
1100 and
1101 .B BUF_ENCLOSEKTAG
1102 macros are themselves built from a lower-level macro named
1103 .BR BUF_ENCLOSETAG .
1104 In place of the
1105 .I W
1106 argument, it takes three arguments:
1107 .I check
1108 is an expression which should evaluate true if the length
1109 .B _delta
1110 can be represented;
1111 .I poke
1112 is a macro, invoked as
1113 .IB poke "(unsigned char *" p ", " size_t n ")" \fR,
1114 which should store
1115 .I n
1116 at address
1117 .IR p ,
1118 formatted in whatever way is appropriate;
1119 and
1120 .I lensz
1121 is the amount of space, in bytes, to save for the length.
1122 .
1123 .SS "Dynamic buffers"
1124 The type
1125 .B dbuf
1126 is a
1127 .IR "dynamic buffer" .
1128 It contains a buffer structure,
1129 accessible using the
1130 p.B DBUF_BUF
1131 macro.
1132 The ordinary buffer functions and macros can be used on this buffer,
1133 though, for convenience,
1134 there are similarly named functions and macros
1135 which accept a
1136 .B dbuf
1137 argument directly.
1138 There is
1139 .I "no difference"
1140 between the behaviour of the
1141 .B "buf"
1142 and
1143 .B "dbuf"
1144 functions.
1145 .PP
1146 A dynamic buffer is created by statically initializing it with
1147 .BR DBUF_INIT ,
1148 or by calling
1149 .BR dbuf_create
1150 or its macro equivalent
1151 .BR DBCREATE .
1152 The memory backing a dynamic buffer can be freed by
1153 .BR dbuf_destroy
1154 or the macro equivalent
1155 .BR DBDESTROY ;
1156 these leave the buffer in the state established by initialization:
1157 the buffer holds no resources, but is ready for immediate use.
1158 .PP
1159 A dynamic buffer contains a
1160 .B buf
1161 buffer,
1162 called its
1163 .I underlying
1164 buffer.
1165 The underlying buffer is accessible through the
1166 .B DBUF_BUF
1167 macro.
1168 All of the above functions and macros can be applied
1169 to a dynamic buffer's underlying buffer.
1170 As a convenience,
1171 corresponding to each of the functions and macros described above,
1172 there is a version named with an initial
1173 .RB ` d '
1174 or
1175 .RB ` D '
1176 as appropriate,
1177 which accepts a pointer to a dynamic buffer
1178 rather than an ordinary buffer,
1179 and acts on its underlying buffer.
1180 Note that these functions are in no way special.
1181 A dynamic buffer will grow automatically
1182 in response to either kind of functions.
1183 .PP
1184 A freshly created buffer is in
1185 .I write
1186 mode,
1187 and is empty, with.
1188 In this state, it will automatically extend its backing storage
1189 in response to
1190 .B BENSURE
1191 calls, rather than breaking.
1192 As a result,
1193 an
1194 .I "a priori"
1195 unpredictable amount of data can be written to a dynamic buffer
1196 and it will automatically grow as necessary to accommodate it.
1197 Of course, the
1198 .B BSZ
1199 and
1200 .B BLEFT
1201 queries are somewhat meaningless when applied to dynamic buffers \(en
1202 though perfectly valid.
1203 The critical function for this is
1204 .B buf_tryextend
1205 (also accessible as
1206 .BR dbuf_tryextend )
1207 which attempts to arrange that at least
1208 .I sz
1209 unused bytes are available in the buffer \(en
1210 i.e., that
1211 .B BLEFT
1212 would return at least
1213 .IR sz .
1214 If it succeeds, it returns zero;
1215 it will fail if the buffer is not in write mode,
1216 or if the buffer is not dynamic,
1217 in which case it returns \-1.
1218 It is unlikely that applications will call this function directly.
1219 .PP
1220 The
1221 .B buf_flip
1222 (or its macro equivalent)
1223 switches the buffer to
1224 .I read
1225 mode,
1226 in addition to its usual behaviour of
1227 setting the buffer's limit to its current position
1228 and its current position to its base.
1229 In read mode, a dynamic buffer will no longer grow dynamically,
1230 as one would expect.
1231 .PP
1232 The
1233 .B dbuf_reset
1234 function,
1235 and its macro equivalent
1236 .B DBRESET
1237 (which may evaluate its argument multiple times)
1238 will return a dynamic buffer to write mode,
1239 and also restore its current position to its base and
1240 clear its broken flag.
1241 .
1242 .\"--------------------------------------------------------------------------
1243 .SH "SEE ALSO"
1244 .
1245 .BR bits (3),
1246 .BR control (3),
1247 .BR dstr (3),
1248 .BR fltfmt (3),
1249 .BR gprintf (3),
1250 .BR mLib (3).
1251 .
1252 .\"--------------------------------------------------------------------------
1253 .SH AUTHOR
1254 .
1255 Mark Wooding, <mdw@distorted.org.uk>
1256 .
1257 .\"----- That's all, folks --------------------------------------------------