1 /*
2 * OpenVPN -- An application to securely tunnel IP networks
3 * over a single UDP port, with support for SSL/TLS-based
4 * session authentication and key exchange,
5 * packet encryption, packet authentication, and
6 * packet compression.
7 *
8 * Copyright (C) 2002-2022 OpenVPN Inc <sales@openvpn.net>
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License version 2
12 * as published by the Free Software Foundation.
13 *
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License along
20 * with this program; if not, write to the Free Software Foundation, Inc.,
21 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
22 */
23
24 #ifndef BUFFER_H
25 #define BUFFER_H
26
27 #include "basic.h"
28 #include "error.h"
29
30 #define BUF_SIZE_MAX 1000000
31
32 /*
33 * Define verify_align function, otherwise
34 * it will be a noop.
35 */
36 /* #define VERIFY_ALIGNMENT */
37
38 /*
39 * Keep track of source file/line of buf_init calls
40 */
41 #ifdef VERIFY_ALIGNMENT
42 #define BUF_INIT_TRACKING
43 #endif
44
45 /**************************************************************************/
46 /**
47 * Wrapper structure for dynamically allocated memory.
48 *
49 * The actual content stored in a \c buffer structure starts at the memory
50 * location \c buffer.data \c + \c buffer.offset, and has a length of \c
51 * buffer.len bytes. This, together with the space available before and
52 * after the content, is represented in the pseudocode below:
53 * @code
54 * uint8_t *content_start = buffer.data + buffer.offset;
55 * uint8_t *content_end = buffer.data + buffer.offset + buffer.len;
56 * int prepend_capacity = buffer.offset;
57 * int append_capacity = buffer.capacity - (buffer.offset + buffer.len);
58 * @endcode
59 */
60 struct buffer
61 {
62 int capacity; /**< Size in bytes of memory allocated by
63 * \c malloc(). */
64 int offset; /**< Offset in bytes of the actual content
65 * within the allocated memory. */
66 int len; /**< Length in bytes of the actual content
67 * within the allocated memory. */
68 uint8_t *data; /**< Pointer to the allocated memory. */
69
70 #ifdef BUF_INIT_TRACKING
71 const char *debug_file;
72 int debug_line;
73 #endif
74 };
75
76
77 /**************************************************************************/
78 /**
79 * Garbage collection entry for one dynamically allocated block of memory.
80 *
81 * This structure represents one link in the linked list contained in a \c
82 * gc_arena structure. Each time the \c gc_malloc() function is called,
83 * it allocates \c sizeof(gc_entry) + the requested number of bytes. The
84 * \c gc_entry is then stored as a header in front of the memory address
85 * returned to the caller.
86 */
87 struct gc_entry
88 {
89 struct gc_entry *next; /**< Pointer to the next item in the
90 * linked list. */
91 };
92
93 /**
94 * Garbage collection entry for a specially allocated structure that needs
95 * a custom free function to be freed like struct addrinfo
96 *
97 */
98 struct gc_entry_special
99 {
100 struct gc_entry_special *next;
101 void (*free_fnc)(void *);
102 void *addr;
103 };
104
105
106 /**
107 * Garbage collection arena used to keep track of dynamically allocated
108 * memory.
109 *
110 * This structure contains a linked list of \c gc_entry structures. When
111 * a block of memory is allocated using the \c gc_malloc() function, the
112 * allocation is registered in the function's \c gc_arena argument. All
113 * the dynamically allocated memory registered in a \c gc_arena can be
114 * freed using the \c gc_free() function.
115 */
116 struct gc_arena
117 {
118 struct gc_entry *list; /**< First element of the linked list of
119 * \c gc_entry structures. */
120 struct gc_entry_special *list_special;
121 };
122
123
124 #define BPTR(buf) (buf_bptr(buf))
125 #define BEND(buf) (buf_bend(buf))
126 #define BLAST(buf) (buf_blast(buf))
127 #define BLEN(buf) (buf_len(buf))
128 #define BDEF(buf) (buf_defined(buf))
129 #define BSTR(buf) (buf_str(buf))
130 #define BCAP(buf) (buf_forward_capacity(buf))
131
132 void buf_clear(struct buffer *buf);
133
134 void free_buf(struct buffer *buf);
135
136 bool buf_assign(struct buffer *dest, const struct buffer *src);
137
138 void string_clear(char *str);
139
140 int string_array_len(const char **array);
141
142 size_t array_mult_safe(const size_t m1, const size_t m2, const size_t extra);
143
144 #define PA_BRACKET (1<<0)
145 char *print_argv(const char **p, struct gc_arena *gc, const unsigned int flags);
146
147 void buf_size_error(const size_t size);
148
149 /* for dmalloc debugging */
150
151 #ifdef DMALLOC
152
153 #define alloc_buf(size) alloc_buf_debug(size, __FILE__, __LINE__)
154 #define alloc_buf_gc(size, gc) alloc_buf_gc_debug(size, gc, __FILE__, __LINE__);
155 #define clone_buf(buf) clone_buf_debug(buf, __FILE__, __LINE__);
156 #define gc_malloc(size, clear, arena) gc_malloc_debug(size, clear, arena, __FILE__, __LINE__)
157 #define string_alloc(str, gc) string_alloc_debug(str, gc, __FILE__, __LINE__)
158 #define string_alloc_buf(str, gc) string_alloc_buf_debug(str, gc, __FILE__, __LINE__)
159
160 struct buffer alloc_buf_debug(size_t size, const char *file, int line);
161
162 struct buffer alloc_buf_gc_debug(size_t size, struct gc_arena *gc, const char *file, int line);
163
164 struct buffer clone_buf_debug(const struct buffer *buf, const char *file, int line);
165
166 void *gc_malloc_debug(size_t size, bool clear, struct gc_arena *a, const char *file, int line);
167
168 char *string_alloc_debug(const char *str, struct gc_arena *gc, const char *file, int line);
169
170 struct buffer string_alloc_buf_debug(const char *str, struct gc_arena *gc, const char *file, int line);
171
172 #else /* ifdef DMALLOC */
173
174 struct buffer alloc_buf(size_t size);
175
176 struct buffer alloc_buf_gc(size_t size, struct gc_arena *gc); /* allocate buffer with garbage collection */
177
178 struct buffer clone_buf(const struct buffer *buf);
179
180 void *gc_malloc(size_t size, bool clear, struct gc_arena *a);
181
182 char *string_alloc(const char *str, struct gc_arena *gc);
183
184 struct buffer string_alloc_buf(const char *str, struct gc_arena *gc);
185
186 #endif /* ifdef DMALLOC */
187
188 void gc_addspecial(void *addr, void (*free_function)(void *), struct gc_arena *a);
189
190
191 #ifdef BUF_INIT_TRACKING
192 #define buf_init(buf, offset) buf_init_debug(buf, offset, __FILE__, __LINE__)
193 bool buf_init_debug(struct buffer *buf, int offset, const char *file, int line);
194
195 #else
196 #define buf_init(buf, offset) buf_init_dowork(buf, offset)
197 #endif
198
199
200 /* inline functions */
201 inline static void
gc_freeaddrinfo_callback(void * addr)202 gc_freeaddrinfo_callback(void *addr)
203 {
204 freeaddrinfo((struct addrinfo *) addr);
205 }
206
207 /** Return an empty struct buffer */
208 static inline struct buffer
clear_buf(void)209 clear_buf(void)
210 {
211 return (struct buffer) { 0 };
212 }
213
214 static inline bool
buf_defined(const struct buffer * buf)215 buf_defined(const struct buffer *buf)
216 {
217 return buf->data != NULL;
218 }
219
220 static inline bool
buf_valid(const struct buffer * buf)221 buf_valid(const struct buffer *buf)
222 {
223 return likely(buf->data != NULL) && likely(buf->len >= 0);
224 }
225
226 static inline uint8_t *
buf_bptr(const struct buffer * buf)227 buf_bptr(const struct buffer *buf)
228 {
229 if (buf_valid(buf))
230 {
231 return buf->data + buf->offset;
232 }
233 else
234 {
235 return NULL;
236 }
237 }
238
239 static int
buf_len(const struct buffer * buf)240 buf_len(const struct buffer *buf)
241 {
242 if (buf_valid(buf))
243 {
244 return buf->len;
245 }
246 else
247 {
248 return 0;
249 }
250 }
251
252 static inline uint8_t *
buf_bend(const struct buffer * buf)253 buf_bend(const struct buffer *buf)
254 {
255 return buf_bptr(buf) + buf_len(buf);
256 }
257
258 static inline uint8_t *
buf_blast(const struct buffer * buf)259 buf_blast(const struct buffer *buf)
260 {
261 if (buf_len(buf) > 0)
262 {
263 return buf_bptr(buf) + buf_len(buf) - 1;
264 }
265 else
266 {
267 return NULL;
268 }
269 }
270
271 static inline bool
buf_size_valid(const size_t size)272 buf_size_valid(const size_t size)
273 {
274 return likely(size < BUF_SIZE_MAX);
275 }
276
277 static inline bool
buf_size_valid_signed(const int size)278 buf_size_valid_signed(const int size)
279 {
280 return likely(size >= -BUF_SIZE_MAX) && likely(size < BUF_SIZE_MAX);
281 }
282
283 static inline char *
buf_str(const struct buffer * buf)284 buf_str(const struct buffer *buf)
285 {
286 return (char *)buf_bptr(buf);
287 }
288
289 static inline void
buf_reset(struct buffer * buf)290 buf_reset(struct buffer *buf)
291 {
292 buf->capacity = 0;
293 buf->offset = 0;
294 buf->len = 0;
295 buf->data = NULL;
296 }
297
298 static inline void
buf_reset_len(struct buffer * buf)299 buf_reset_len(struct buffer *buf)
300 {
301 buf->len = 0;
302 buf->offset = 0;
303 }
304
305 static inline bool
buf_init_dowork(struct buffer * buf,int offset)306 buf_init_dowork(struct buffer *buf, int offset)
307 {
308 if (offset < 0 || offset > buf->capacity || buf->data == NULL)
309 {
310 return false;
311 }
312 buf->len = 0;
313 buf->offset = offset;
314 return true;
315 }
316
317 static inline void
buf_set_write(struct buffer * buf,uint8_t * data,int size)318 buf_set_write(struct buffer *buf, uint8_t *data, int size)
319 {
320 if (!buf_size_valid(size))
321 {
322 buf_size_error(size);
323 }
324 buf->len = 0;
325 buf->offset = 0;
326 buf->capacity = size;
327 buf->data = data;
328 if (size > 0 && data)
329 {
330 *data = 0;
331 }
332 }
333
334 static inline void
buf_set_read(struct buffer * buf,const uint8_t * data,int size)335 buf_set_read(struct buffer *buf, const uint8_t *data, int size)
336 {
337 if (!buf_size_valid(size))
338 {
339 buf_size_error(size);
340 }
341 buf->len = buf->capacity = size;
342 buf->offset = 0;
343 buf->data = (uint8_t *)data;
344 }
345
346 /* Like strncpy but makes sure dest is always null terminated */
347 static inline void
strncpynt(char * dest,const char * src,size_t maxlen)348 strncpynt(char *dest, const char *src, size_t maxlen)
349 {
350 if (maxlen > 0)
351 {
352 strncpy(dest, src, maxlen-1);
353 dest[maxlen - 1] = 0;
354 }
355 }
356
357 /* return true if string contains at least one numerical digit */
358 static inline bool
has_digit(const unsigned char * src)359 has_digit(const unsigned char *src)
360 {
361 unsigned char c;
362 while ((c = *src++))
363 {
364 if (isdigit(c))
365 {
366 return true;
367 }
368 }
369 return false;
370 }
371
372 /**
373 * Securely zeroise memory.
374 *
375 * This code and description are based on code supplied by Zhaomo Yang, of the
376 * University of California, San Diego (which was released into the public
377 * domain).
378 *
379 * The secure_memzero function attempts to ensure that an optimizing compiler
380 * does not remove the intended operation if cleared memory is not accessed
381 * again by the program. This code has been tested under Clang 3.9.0 and GCC
382 * 6.2 with optimization flags -O, -Os, -O0, -O1, -O2, and -O3 on
383 * Ubuntu 16.04.1 LTS; under Clang 3.9.0 with optimization flags -O, -Os,
384 * -O0, -O1, -O2, and -O3 on FreeBSD 10.2-RELEASE; under Microsoft Visual Studio
385 * 2015 with optimization flags /O1, /O2 and /Ox on Windows 10.
386 *
387 * Theory of operation:
388 *
389 * 1. On Windows, use the SecureZeroMemory which ensures that data is
390 * overwritten.
391 * 2. Under GCC or Clang, use a memory barrier, which forces the preceding
392 * memset to be carried out. The overhead of a memory barrier is usually
393 * negligible.
394 * 3. If none of the above are available, use the volatile pointer
395 * technique to zero memory one byte at a time.
396 *
397 * @param data Pointer to data to zeroise.
398 * @param len Length of data, in bytes.
399 */
400 static inline void
secure_memzero(void * data,size_t len)401 secure_memzero(void *data, size_t len)
402 {
403 #if defined(_WIN32)
404 SecureZeroMemory(data, len);
405 #elif defined(__GNUC__) || defined(__clang__)
406 memset(data, 0, len);
407 __asm__ __volatile__ ("" : : "r" (data) : "memory");
408 #else
409 volatile char *p = (volatile char *) data;
410 while (len--)
411 {
412 *p++ = 0;
413 }
414 #endif
415 }
416
417 /*
418 * printf append to a buffer with overflow check,
419 * due to usage of vsnprintf, it will leave space for
420 * a final null character and thus use only
421 * capacity - 1
422 */
423 bool buf_printf(struct buffer *buf, const char *format, ...)
424 #ifdef __GNUC__
425 #if __USE_MINGW_ANSI_STDIO
426 __attribute__ ((format(gnu_printf, 2, 3)))
427 #else
428 __attribute__ ((format(__printf__, 2, 3)))
429 #endif
430 #endif
431 ;
432
433 /*
434 * puts append to a buffer with overflow check
435 */
436 bool buf_puts(struct buffer *buf, const char *str);
437
438 /*
439 * Like snprintf but guarantees null termination for size > 0
440 */
441 bool openvpn_snprintf(char *str, size_t size, const char *format, ...)
442 #ifdef __GNUC__
443 #if __USE_MINGW_ANSI_STDIO
444 __attribute__ ((format(gnu_printf, 3, 4)))
445 #else
446 __attribute__ ((format(__printf__, 3, 4)))
447 #endif
448 #endif
449 ;
450
451
452 /*
453 * remove/add trailing characters
454 */
455
456 void buf_null_terminate(struct buffer *buf);
457
458 void buf_chomp(struct buffer *buf);
459
460 void buf_rmtail(struct buffer *buf, uint8_t remove);
461
462 /*
463 * non-buffer string functions
464 */
465 void chomp(char *str);
466
467 void rm_trailing_chars(char *str, const char *what_to_delete);
468
469 const char *skip_leading_whitespace(const char *str);
470
471 void string_null_terminate(char *str, int len, int capacity);
472
473 /**
474 * Write buffer contents to file.
475 *
476 * @param filename The filename to write the buffer to.
477 * @param buf The buffer to write to the file.
478 *
479 * @return true on success, false otherwise.
480 */
481 bool buffer_write_file(const char *filename, const struct buffer *buf);
482
483 /*
484 * write a string to the end of a buffer that was
485 * truncated by buf_printf
486 */
487 void buf_catrunc(struct buffer *buf, const char *str);
488
489 /*
490 * convert a multi-line output to one line
491 */
492 void convert_to_one_line(struct buffer *buf);
493
494 /*
495 * Parse a string based on a given delimiter char
496 */
497 bool buf_parse(struct buffer *buf, const int delim, char *line, const int size);
498
499 /*
500 * Hex dump -- Output a binary buffer to a hex string and return it.
501 */
502 #define FHE_SPACE_BREAK_MASK 0xFF /* space_break parameter in lower 8 bits */
503 #define FHE_CAPS 0x100 /* output hex in caps */
504 char *
505 format_hex_ex(const uint8_t *data, int size, int maxoutput,
506 unsigned int space_break_flags, const char *separator,
507 struct gc_arena *gc);
508
509 static inline char *
format_hex(const uint8_t * data,int size,int maxoutput,struct gc_arena * gc)510 format_hex(const uint8_t *data, int size, int maxoutput, struct gc_arena *gc)
511 {
512 return format_hex_ex(data, size, maxoutput, 4, " ", gc);
513 }
514
515 /*
516 * Return a buffer that is a subset of another buffer.
517 */
518 struct buffer buf_sub(struct buffer *buf, int size, bool prepend);
519
520 /*
521 * Check if sufficient space to append to buffer.
522 */
523
524 static inline bool
buf_safe(const struct buffer * buf,int len)525 buf_safe(const struct buffer *buf, int len)
526 {
527 return buf_valid(buf) && buf_size_valid(len)
528 && buf->offset + buf->len + len <= buf->capacity;
529 }
530
531 static inline bool
buf_safe_bidir(const struct buffer * buf,int len)532 buf_safe_bidir(const struct buffer *buf, int len)
533 {
534 if (buf_valid(buf) && buf_size_valid_signed(len))
535 {
536 const int newlen = buf->len + len;
537 return newlen >= 0 && buf->offset + newlen <= buf->capacity;
538 }
539 else
540 {
541 return false;
542 }
543 }
544
545 static inline int
buf_forward_capacity(const struct buffer * buf)546 buf_forward_capacity(const struct buffer *buf)
547 {
548 if (buf_valid(buf))
549 {
550 int ret = buf->capacity - (buf->offset + buf->len);
551 if (ret < 0)
552 {
553 ret = 0;
554 }
555 return ret;
556 }
557 else
558 {
559 return 0;
560 }
561 }
562
563 static inline int
buf_forward_capacity_total(const struct buffer * buf)564 buf_forward_capacity_total(const struct buffer *buf)
565 {
566 if (buf_valid(buf))
567 {
568 int ret = buf->capacity - buf->offset;
569 if (ret < 0)
570 {
571 ret = 0;
572 }
573 return ret;
574 }
575 else
576 {
577 return 0;
578 }
579 }
580
581 static inline int
buf_reverse_capacity(const struct buffer * buf)582 buf_reverse_capacity(const struct buffer *buf)
583 {
584 if (buf_valid(buf))
585 {
586 return buf->offset;
587 }
588 else
589 {
590 return 0;
591 }
592 }
593
594 static inline bool
buf_inc_len(struct buffer * buf,int inc)595 buf_inc_len(struct buffer *buf, int inc)
596 {
597 if (!buf_safe_bidir(buf, inc))
598 {
599 return false;
600 }
601 buf->len += inc;
602 return true;
603 }
604
605 /*
606 * Make space to prepend to a buffer.
607 * Return NULL if no space.
608 */
609
610 static inline uint8_t *
buf_prepend(struct buffer * buf,int size)611 buf_prepend(struct buffer *buf, int size)
612 {
613 if (!buf_valid(buf) || size < 0 || size > buf->offset)
614 {
615 return NULL;
616 }
617 buf->offset -= size;
618 buf->len += size;
619 return BPTR(buf);
620 }
621
622 static inline bool
buf_advance(struct buffer * buf,int size)623 buf_advance(struct buffer *buf, int size)
624 {
625 if (!buf_valid(buf) || size < 0 || buf->len < size)
626 {
627 return false;
628 }
629 buf->offset += size;
630 buf->len -= size;
631 return true;
632 }
633
634 /*
635 * Return a pointer to allocated space inside a buffer.
636 * Return NULL if no space.
637 */
638
639 static inline uint8_t *
buf_write_alloc(struct buffer * buf,int size)640 buf_write_alloc(struct buffer *buf, int size)
641 {
642 uint8_t *ret;
643 if (!buf_safe(buf, size))
644 {
645 return NULL;
646 }
647 ret = BPTR(buf) + buf->len;
648 buf->len += size;
649 return ret;
650 }
651
652 static inline uint8_t *
buf_write_alloc_prepend(struct buffer * buf,int size,bool prepend)653 buf_write_alloc_prepend(struct buffer *buf, int size, bool prepend)
654 {
655 return prepend ? buf_prepend(buf, size) : buf_write_alloc(buf, size);
656 }
657
658 static inline uint8_t *
buf_read_alloc(struct buffer * buf,int size)659 buf_read_alloc(struct buffer *buf, int size)
660 {
661 uint8_t *ret;
662 if (size < 0 || buf->len < size)
663 {
664 return NULL;
665 }
666 ret = BPTR(buf);
667 buf->offset += size;
668 buf->len -= size;
669 return ret;
670 }
671
672 static inline bool
buf_write(struct buffer * dest,const void * src,int size)673 buf_write(struct buffer *dest, const void *src, int size)
674 {
675 uint8_t *cp = buf_write_alloc(dest, size);
676 if (!cp)
677 {
678 return false;
679 }
680 memcpy(cp, src, size);
681 return true;
682 }
683
684 static inline bool
buf_write_prepend(struct buffer * dest,const void * src,int size)685 buf_write_prepend(struct buffer *dest, const void *src, int size)
686 {
687 uint8_t *cp = buf_prepend(dest, size);
688 if (!cp)
689 {
690 return false;
691 }
692 memcpy(cp, src, size);
693 return true;
694 }
695
696 static inline bool
buf_write_u8(struct buffer * dest,int data)697 buf_write_u8(struct buffer *dest, int data)
698 {
699 uint8_t u8 = (uint8_t) data;
700 return buf_write(dest, &u8, sizeof(uint8_t));
701 }
702
703 static inline bool
buf_write_u16(struct buffer * dest,int data)704 buf_write_u16(struct buffer *dest, int data)
705 {
706 uint16_t u16 = htons((uint16_t) data);
707 return buf_write(dest, &u16, sizeof(uint16_t));
708 }
709
710 static inline bool
buf_write_u32(struct buffer * dest,int data)711 buf_write_u32(struct buffer *dest, int data)
712 {
713 uint32_t u32 = htonl((uint32_t) data);
714 return buf_write(dest, &u32, sizeof(uint32_t));
715 }
716
717 static inline bool
buf_copy(struct buffer * dest,const struct buffer * src)718 buf_copy(struct buffer *dest, const struct buffer *src)
719 {
720 return buf_write(dest, BPTR(src), BLEN(src));
721 }
722
723 static inline bool
buf_copy_n(struct buffer * dest,struct buffer * src,int n)724 buf_copy_n(struct buffer *dest, struct buffer *src, int n)
725 {
726 uint8_t *cp = buf_read_alloc(src, n);
727 if (!cp)
728 {
729 return false;
730 }
731 return buf_write(dest, cp, n);
732 }
733
734 static inline bool
buf_copy_range(struct buffer * dest,int dest_index,const struct buffer * src,int src_index,int src_len)735 buf_copy_range(struct buffer *dest,
736 int dest_index,
737 const struct buffer *src,
738 int src_index,
739 int src_len)
740 {
741 if (src_index < 0
742 || src_len < 0
743 || src_index + src_len > src->len
744 || dest_index < 0
745 || dest->offset + dest_index + src_len > dest->capacity)
746 {
747 return false;
748 }
749 memcpy(dest->data + dest->offset + dest_index, src->data + src->offset + src_index, src_len);
750 if (dest_index + src_len > dest->len)
751 {
752 dest->len = dest_index + src_len;
753 }
754 return true;
755 }
756
757 /* truncate src to len, copy excess data beyond len to dest */
758 static inline bool
buf_copy_excess(struct buffer * dest,struct buffer * src,int len)759 buf_copy_excess(struct buffer *dest,
760 struct buffer *src,
761 int len)
762 {
763 if (len < 0)
764 {
765 return false;
766 }
767 if (src->len > len)
768 {
769 struct buffer b = *src;
770 src->len = len;
771 if (!buf_advance(&b, len))
772 {
773 return false;
774 }
775 return buf_copy(dest, &b);
776 }
777 else
778 {
779 return true;
780 }
781 }
782
783 static inline bool
buf_read(struct buffer * src,void * dest,int size)784 buf_read(struct buffer *src, void *dest, int size)
785 {
786 uint8_t *cp = buf_read_alloc(src, size);
787 if (!cp)
788 {
789 return false;
790 }
791 memcpy(dest, cp, size);
792 return true;
793 }
794
795 static inline int
buf_read_u8(struct buffer * buf)796 buf_read_u8(struct buffer *buf)
797 {
798 int ret;
799 if (BLEN(buf) < 1)
800 {
801 return -1;
802 }
803 ret = *BPTR(buf);
804 buf_advance(buf, 1);
805 return ret;
806 }
807
808 static inline int
buf_read_u16(struct buffer * buf)809 buf_read_u16(struct buffer *buf)
810 {
811 uint16_t ret;
812 if (!buf_read(buf, &ret, sizeof(uint16_t)))
813 {
814 return -1;
815 }
816 return ntohs(ret);
817 }
818
819 static inline uint32_t
buf_read_u32(struct buffer * buf,bool * good)820 buf_read_u32(struct buffer *buf, bool *good)
821 {
822 uint32_t ret;
823 if (!buf_read(buf, &ret, sizeof(uint32_t)))
824 {
825 if (good)
826 {
827 *good = false;
828 }
829 return 0;
830 }
831 else
832 {
833 if (good)
834 {
835 *good = true;
836 }
837 return ntohl(ret);
838 }
839 }
840
841 /** Return true if buffer contents are equal */
842 static inline bool
buf_equal(const struct buffer * a,const struct buffer * b)843 buf_equal(const struct buffer *a, const struct buffer *b)
844 {
845 return BLEN(a) == BLEN(b) && 0 == memcmp(BPTR(a), BPTR(b), BLEN(a));
846 }
847
848 /**
849 * Compare src buffer contents with match.
850 * *NOT* constant time. Do not use when comparing HMACs.
851 */
852 static inline bool
buf_string_match(const struct buffer * src,const void * match,int size)853 buf_string_match(const struct buffer *src, const void *match, int size)
854 {
855 if (size != src->len)
856 {
857 return false;
858 }
859 return memcmp(BPTR(src), match, size) == 0;
860 }
861
862 /**
863 * Compare first size bytes of src buffer contents with match.
864 * *NOT* constant time. Do not use when comparing HMACs.
865 */
866 static inline bool
buf_string_match_head(const struct buffer * src,const void * match,int size)867 buf_string_match_head(const struct buffer *src, const void *match, int size)
868 {
869 if (size < 0 || size > src->len)
870 {
871 return false;
872 }
873 return memcmp(BPTR(src), match, size) == 0;
874 }
875
876 bool buf_string_match_head_str(const struct buffer *src, const char *match);
877
878 bool buf_string_compare_advance(struct buffer *src, const char *match);
879
880 int buf_substring_len(const struct buffer *buf, int delim);
881
882 /*
883 * Print a string which might be NULL
884 */
885 const char *np(const char *str);
886
887 /*#define CHARACTER_CLASS_DEBUG*/
888
889 /* character classes */
890
891 #define CC_ANY (1<<0)
892 #define CC_NULL (1<<1)
893
894 #define CC_ALNUM (1<<2)
895 #define CC_ALPHA (1<<3)
896 #define CC_ASCII (1<<4)
897 #define CC_CNTRL (1<<5)
898 #define CC_DIGIT (1<<6)
899 #define CC_PRINT (1<<7)
900 #define CC_PUNCT (1<<8)
901 #define CC_SPACE (1<<9)
902 #define CC_XDIGIT (1<<10)
903
904 #define CC_BLANK (1<<11)
905 #define CC_NEWLINE (1<<12)
906 #define CC_CR (1<<13)
907
908 #define CC_BACKSLASH (1<<14)
909 #define CC_UNDERBAR (1<<15)
910 #define CC_DASH (1<<16)
911 #define CC_DOT (1<<17)
912 #define CC_COMMA (1<<18)
913 #define CC_COLON (1<<19)
914 #define CC_SLASH (1<<20)
915 #define CC_SINGLE_QUOTE (1<<21)
916 #define CC_DOUBLE_QUOTE (1<<22)
917 #define CC_REVERSE_QUOTE (1<<23)
918 #define CC_AT (1<<24)
919 #define CC_EQUAL (1<<25)
920 #define CC_LESS_THAN (1<<26)
921 #define CC_GREATER_THAN (1<<27)
922 #define CC_PIPE (1<<28)
923 #define CC_QUESTION_MARK (1<<29)
924 #define CC_ASTERISK (1<<30)
925
926 /* macro classes */
927 #define CC_NAME (CC_ALNUM|CC_UNDERBAR)
928 #define CC_CRLF (CC_CR|CC_NEWLINE)
929
930 bool char_class(const unsigned char c, const unsigned int flags);
931
932 bool string_class(const char *str, const unsigned int inclusive, const unsigned int exclusive);
933
934 bool string_mod(char *str, const unsigned int inclusive, const unsigned int exclusive, const char replace);
935
936 const char *string_mod_const(const char *str,
937 const unsigned int inclusive,
938 const unsigned int exclusive,
939 const char replace,
940 struct gc_arena *gc);
941
942 void string_replace_leading(char *str, const char match, const char replace);
943
944 /** Return true iff str starts with prefix */
945 static inline bool
strprefix(const char * str,const char * prefix)946 strprefix(const char *str, const char *prefix)
947 {
948 return 0 == strncmp(str, prefix, strlen(prefix));
949 }
950
951
952 #ifdef CHARACTER_CLASS_DEBUG
953 void character_class_debug(void);
954
955 #endif
956
957 /*
958 * Verify that a pointer is correctly aligned
959 */
960 #ifdef VERIFY_ALIGNMENT
961 void valign4(const struct buffer *buf, const char *file, const int line);
962
963 #define verify_align_4(ptr) valign4(buf, __FILE__, __LINE__)
964 #else
965 #define verify_align_4(ptr)
966 #endif
967
968 /*
969 * Very basic garbage collection, mostly for routines that return
970 * char ptrs to malloced strings.
971 */
972
973 void gc_transfer(struct gc_arena *dest, struct gc_arena *src);
974
975 void x_gc_free(struct gc_arena *a);
976
977 void x_gc_freespecial(struct gc_arena *a);
978
979 static inline bool
gc_defined(struct gc_arena * a)980 gc_defined(struct gc_arena *a)
981 {
982 return a->list != NULL;
983 }
984
985 static inline void
gc_init(struct gc_arena * a)986 gc_init(struct gc_arena *a)
987 {
988 a->list = NULL;
989 a->list_special = NULL;
990 }
991
992 static inline void
gc_detach(struct gc_arena * a)993 gc_detach(struct gc_arena *a)
994 {
995 gc_init(a);
996 }
997
998 static inline struct gc_arena
gc_new(void)999 gc_new(void)
1000 {
1001 struct gc_arena ret;
1002 gc_init(&ret);
1003 return ret;
1004 }
1005
1006 static inline void
gc_free(struct gc_arena * a)1007 gc_free(struct gc_arena *a)
1008 {
1009 if (a->list)
1010 {
1011 x_gc_free(a);
1012 }
1013 if (a->list_special)
1014 {
1015 x_gc_freespecial(a);
1016 }
1017 }
1018
1019 static inline void
gc_reset(struct gc_arena * a)1020 gc_reset(struct gc_arena *a)
1021 {
1022 gc_free(a);
1023 }
1024
1025 /*
1026 * Allocate memory to hold a structure
1027 */
1028
1029 #define ALLOC_OBJ(dptr, type) \
1030 { \
1031 check_malloc_return((dptr) = (type *) malloc(sizeof(type))); \
1032 }
1033
1034 #define ALLOC_OBJ_CLEAR(dptr, type) \
1035 { \
1036 ALLOC_OBJ(dptr, type); \
1037 memset((dptr), 0, sizeof(type)); \
1038 }
1039
1040 #define ALLOC_ARRAY(dptr, type, n) \
1041 { \
1042 check_malloc_return((dptr) = (type *) malloc(array_mult_safe(sizeof(type), (n), 0))); \
1043 }
1044
1045 #define ALLOC_ARRAY_GC(dptr, type, n, gc) \
1046 { \
1047 (dptr) = (type *) gc_malloc(array_mult_safe(sizeof(type), (n), 0), false, (gc)); \
1048 }
1049
1050 #define ALLOC_ARRAY_CLEAR(dptr, type, n) \
1051 { \
1052 ALLOC_ARRAY(dptr, type, n); \
1053 memset((dptr), 0, (array_mult_safe(sizeof(type), (n), 0))); \
1054 }
1055
1056 #define ALLOC_ARRAY_CLEAR_GC(dptr, type, n, gc) \
1057 { \
1058 (dptr) = (type *) gc_malloc(array_mult_safe(sizeof(type), (n), 0), true, (gc)); \
1059 }
1060
1061 #define ALLOC_VAR_ARRAY_CLEAR_GC(dptr, type, atype, n, gc) \
1062 { \
1063 (dptr) = (type *) gc_malloc(array_mult_safe(sizeof(atype), (n), sizeof(type)), true, (gc)); \
1064 }
1065
1066 #define ALLOC_OBJ_GC(dptr, type, gc) \
1067 { \
1068 (dptr) = (type *) gc_malloc(sizeof(type), false, (gc)); \
1069 }
1070
1071 #define ALLOC_OBJ_CLEAR_GC(dptr, type, gc) \
1072 { \
1073 (dptr) = (type *) gc_malloc(sizeof(type), true, (gc)); \
1074 }
1075
1076 static inline void
check_malloc_return(const void * p)1077 check_malloc_return(const void *p)
1078 {
1079 if (!p)
1080 {
1081 out_of_memory();
1082 }
1083 }
1084
1085 /*
1086 * Manage lists of buffers
1087 */
1088 struct buffer_entry
1089 {
1090 struct buffer buf;
1091 struct buffer_entry *next;
1092 };
1093
1094 struct buffer_list
1095 {
1096 struct buffer_entry *head; /* next item to pop/peek */
1097 struct buffer_entry *tail; /* last item pushed */
1098 int size; /* current number of entries */
1099 int max_size; /* maximum size list should grow to */
1100 };
1101
1102 /**
1103 * Allocate an empty buffer list of capacity \c max_size.
1104 *
1105 * @param max_size the capacity of the list to allocate
1106 *
1107 * @return the new list
1108 */
1109 struct buffer_list *buffer_list_new(const int max_size);
1110
1111 /**
1112 * Frees a buffer list and all the buffers in it.
1113 *
1114 * @param ol the list to free
1115 */
1116 void buffer_list_free(struct buffer_list *ol);
1117
1118 /**
1119 * Checks if the list is valid and non-empty
1120 *
1121 * @param ol the list to check
1122 *
1123 * @return true iff \c ol is not NULL and contains at least one buffer
1124 */
1125 bool buffer_list_defined(const struct buffer_list *ol);
1126
1127 /**
1128 * Empty the list \c ol and frees all the contained buffers
1129 *
1130 * @param ol the list to reset
1131 */
1132 void buffer_list_reset(struct buffer_list *ol);
1133
1134 /**
1135 * Allocates and appends a new buffer containing \c str as data to \c ol
1136 *
1137 * @param ol the list to append the new buffer to
1138 * @param str the string to copy into the new buffer
1139 */
1140 void buffer_list_push(struct buffer_list *ol, const char *str);
1141
1142 /**
1143 * Allocates and appends a new buffer containing \c data of length \c size.
1144 *
1145 * @param ol the list to append the new buffer to
1146 * @param data the data to copy into the new buffer
1147 * @param size the length of \c data to copy into the buffer
1148 *
1149 * @return the new buffer
1150 */
1151 struct buffer_entry *buffer_list_push_data(struct buffer_list *ol, const void *data, size_t size);
1152
1153 /**
1154 * Retrieve the head buffer
1155 *
1156 * @param ol the list to retrieve the buffer from
1157 *
1158 * @return a pointer to the head buffer or NULL if the list is empty
1159 */
1160 struct buffer *buffer_list_peek(struct buffer_list *ol);
1161
1162 void buffer_list_advance(struct buffer_list *ol, int n);
1163
1164 void buffer_list_pop(struct buffer_list *ol);
1165
1166 /**
1167 * Aggregates as many buffers as possible from \c bl in a new buffer of maximum
1168 * length \c max_len .
1169 * All the aggregated buffers are removed from the list and replaced by the new
1170 * one, followed by any additional (non-aggregated) data.
1171 *
1172 * @param bl the list of buffer to aggregate
1173 * @param max the maximum length of the aggregated buffer
1174 */
1175 void buffer_list_aggregate(struct buffer_list *bl, const size_t max);
1176
1177 /**
1178 * Aggregates as many buffers as possible from \c bl in a new buffer
1179 * of maximum length \c max_len . \c sep is written after
1180 * each copied buffer (also after the last one). All the aggregated buffers are
1181 * removed from the list and replaced by the new one, followed by any additional
1182 * (non-aggregated) data.
1183 * Nothing happens if \c max_len is not enough to aggregate at least 2 buffers.
1184 *
1185 * @param bl the list of buffer to aggregate
1186 * @param max_len the maximum length of the aggregated buffer
1187 * @param sep the separator to put between buffers during aggregation
1188 */
1189 void buffer_list_aggregate_separator(struct buffer_list *bl,
1190 const size_t max_len, const char *sep);
1191
1192 struct buffer_list *buffer_list_file(const char *fn, int max_line_len);
1193
1194 /**
1195 * buffer_read_from_file - copy the content of a file into a buffer
1196 *
1197 * @param file path to the file to read
1198 * @param gc the garbage collector to use when allocating the buffer. It
1199 * is passed to alloc_buf_gc() and therefore can be NULL.
1200 *
1201 * @return the buffer storing the file content or an invalid buffer in case of
1202 * error
1203 */
1204 struct buffer buffer_read_from_file(const char *filename, struct gc_arena *gc);
1205
1206 #endif /* BUFFER_H */
1207