diff options
Diffstat (limited to 'src/openvpn/buffer.c')
-rw-r--r-- | src/openvpn/buffer.c | 76 |
1 files changed, 39 insertions, 37 deletions
diff --git a/src/openvpn/buffer.c b/src/openvpn/buffer.c index a63ce14..f9c76b1 100644 --- a/src/openvpn/buffer.c +++ b/src/openvpn/buffer.c @@ -5,7 +5,7 @@ * packet encryption, packet authentication, and * packet compression. * - * Copyright (C) 2002-2017 OpenVPN Technologies, Inc. <sales@openvpn.net> + * Copyright (C) 2002-2018 OpenVPN Inc <sales@openvpn.net> * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 @@ -1177,7 +1177,7 @@ buffer_list_reset(struct buffer_list *ol) } void -buffer_list_push(struct buffer_list *ol, const unsigned char *str) +buffer_list_push(struct buffer_list *ol, const char *str) { if (str) { @@ -1191,7 +1191,7 @@ buffer_list_push(struct buffer_list *ol, const unsigned char *str) } struct buffer_entry * -buffer_list_push_data(struct buffer_list *ol, const uint8_t *data, size_t size) +buffer_list_push_data(struct buffer_list *ol, const void *data, size_t size) { struct buffer_entry *e = NULL; if (data && (!ol->max_size || ol->size < ol->max_size)) @@ -1231,45 +1231,47 @@ buffer_list_peek(struct buffer_list *ol) } void -buffer_list_aggregate_separator(struct buffer_list *bl, const size_t max, const char *sep) +buffer_list_aggregate_separator(struct buffer_list *bl, const size_t max_len, + const char *sep) { - int sep_len = strlen(sep); + const int sep_len = strlen(sep); + struct buffer_entry *more = bl->head; + size_t size = 0; + int count = 0; + for (count = 0; more; ++count) + { + size_t extra_len = BLEN(&more->buf) + sep_len; + if (size + extra_len > max_len) + { + break; + } - if (bl->head) + size += extra_len; + more = more->next; + } + + if (count >= 2) { - struct buffer_entry *more = bl->head; - size_t size = 0; - int count = 0; - for (count = 0; more && size <= max; ++count) + struct buffer_entry *f; + ALLOC_OBJ_CLEAR(f, struct buffer_entry); + f->buf = alloc_buf(size + 1); /* prevent 0-byte malloc */ + + struct buffer_entry *e = bl->head; + for (size_t i = 0; e && i < count; ++i) { - size += BLEN(&more->buf) + sep_len; - more = more->next; + struct buffer_entry *next = e->next; + buf_copy(&f->buf, &e->buf); + buf_write(&f->buf, sep, sep_len); + free_buf(&e->buf); + free(e); + e = next; } - - if (count >= 2) + bl->head = f; + bl->size -= count - 1; + f->next = more; + if (!more) { - int i; - struct buffer_entry *e = bl->head, *f; - - ALLOC_OBJ_CLEAR(f, struct buffer_entry); - f->buf.data = malloc(size); - check_malloc_return(f->buf.data); - f->buf.capacity = size; - for (i = 0; e && i < count; ++i) - { - struct buffer_entry *next = e->next; - buf_copy(&f->buf, &e->buf); - buf_write(&f->buf, sep, sep_len); - free_buf(&e->buf); - free(e); - e = next; - } - bl->head = f; - f->next = more; - if (!more) - { - bl->tail = f; - } + bl->tail = f; } } } @@ -1325,7 +1327,7 @@ buffer_list_file(const char *fn, int max_line_len) bl = buffer_list_new(0); while (fgets(line, max_line_len, fp) != NULL) { - buffer_list_push(bl, (unsigned char *)line); + buffer_list_push(bl, line); } free(line); } |