2
* Copyright (c) 2012, 2013 by Farsight Security, Inc.
4
* Licensed under the Apache License, Version 2.0 (the "License");
5
* you may not use this file except in compliance with the License.
6
* You may obtain a copy of the License at
8
* http://www.apache.org/licenses/LICENSE-2.0
10
* Unless required by applicable law or agreed to in writing, software
11
* distributed under the License is distributed on an "AS IS" BASIS,
12
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
* See the License for the specific language governing permissions and
14
* limitations under the License.
21
#define VECTOR_GENERATE(name, type) \
22
typedef struct name##__vector { \
25
size_t _n, _n_alloced, _hint; \
27
static inline name * \
28
name##_init(unsigned hint) \
31
vec = my_calloc(1, sizeof(name)); \
32
if (hint == 0) hint = 1; \
33
vec->_hint = vec->_n_alloced = hint; \
34
vec->_v = my_malloc(vec->_n_alloced * sizeof(type)); \
35
vec->_p = &(vec->_v[0]); \
39
name##_reinit(unsigned hint, name *vec) \
41
if (hint == 0) hint = 1; \
42
vec->_hint = vec->_n_alloced = hint; \
44
vec->_v = my_malloc(vec->_n_alloced * sizeof(type)); \
45
vec->_p = &(vec->_v[0]); \
48
name##_detach(name *vec, type **out, size_t *outsz) \
51
*(outsz) = (vec)->_n; \
53
(vec)->_n_alloced = (vec)->_hint; \
54
(vec)->_v = my_malloc((vec)->_n_alloced * sizeof(type)); \
55
(vec)->_p = &(vec->_v[0]); \
58
name##_destroy(name **vec) \
67
name##_reserve(name *vec, size_t n_elems) \
69
while ((n_elems) > ((vec)->_n_alloced - (vec)->_n)) { \
70
(vec)->_n_alloced *= 2; \
71
(vec)->_v = my_realloc((vec)->_v, (vec)->_n_alloced \
73
(vec)->_p = &((vec)->_v[(vec)->_n]); \
77
name##_add(name *vec, type elem) \
79
while ((vec)->_n + 1 > (vec)->_n_alloced) { \
80
(vec)->_n_alloced *= 2; \
81
(vec)->_v = my_realloc((vec)->_v, (vec)->_n_alloced \
83
(vec)->_p = &((vec)->_v[(vec)->_n]); \
85
(vec)->_v[(vec)->_n] = elem; \
87
(vec)->_p = &((vec)->_v[(vec)->_n]); \
90
name##_append(name *vec, type const *elems, size_t n_elems) \
92
name##_reserve(vec, n_elems); \
93
memcpy((vec)->_v + (vec)->_n, elems, (n_elems) * sizeof(type)); \
94
(vec)->_n += (n_elems); \
95
(vec)->_p = &((vec)->_v[(vec)->_n]); \
98
name##_extend(name *vec0, name *vec1) \
100
name##_append(vec0, (vec1)->_v, (vec1)->_n); \
103
name##_reset(name *vec) \
106
if ((vec)->_n_alloced > (vec)->_hint) { \
107
(vec)->_n_alloced = (vec)->_hint; \
108
(vec)->_v = my_realloc((vec)->_v, (vec)->_n_alloced \
111
(vec)->_p = &(vec->_v[0]); \
114
name##_clip(name *vec, size_t n_elems) \
116
if (n_elems < (vec)->_n) { \
117
(vec)->_n = n_elems; \
118
(vec)->_p = &((vec)->_v[(vec)->_n]); \
121
static inline size_t \
122
name##_bytes(name *vec) \
124
return ((vec)->_n * sizeof(type)); \
126
static inline size_t \
127
name##_size(name *vec) \
129
return ((vec)->_n); \
132
name##_value(name *vec, size_t i) \
134
assert(i < (vec)->_n); \
135
return ((vec)->_v[i]); \
137
static inline type * \
138
name##_ptr(name *vec) \
140
return ((vec)->_p); \
142
static inline type * \
143
name##_data(name *vec) \
145
return ((vec)->_v); \
148
name##_advance(name *vec, size_t x) \
150
assert(x <= ((vec)->_n_alloced - (vec)->_n)); \
152
(vec)->_p = &((vec)->_v[(vec)->_n]); \