Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
freebsd
GitHub Repository: freebsd/freebsd-src
Path: blob/main/contrib/elftoolchain/common/utarray.h
39536 views
1
/*
2
Copyright (c) 2008-2013, Troy D. Hanson http://uthash.sourceforge.net
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 are met:
7
8
* Redistributions of source code must retain the above copyright
9
notice, this list of conditions and the following disclaimer.
10
11
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
12
IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
13
TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
14
PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
15
OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
16
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
17
PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
18
PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
19
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
20
NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
21
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
22
*/
23
24
/* $Id: utarray.h 2694 2012-11-24 17:11:58Z kaiwang27 $ */
25
26
/* a dynamic array implementation using macros
27
* see http://uthash.sourceforge.net/utarray
28
*/
29
#ifndef UTARRAY_H
30
#define UTARRAY_H
31
32
#define UTARRAY_VERSION 1.9.7
33
34
#ifdef __GNUC__
35
#define _UNUSED_ __attribute__ ((__unused__))
36
#else
37
#define _UNUSED_
38
#endif
39
40
#include <stddef.h> /* size_t */
41
#include <string.h> /* memset, etc */
42
#include <stdlib.h> /* exit */
43
44
#ifndef oom
45
#define oom() exit(-1)
46
#endif
47
48
typedef void (ctor_f)(void *dst, const void *src);
49
typedef void (dtor_f)(void *elt);
50
typedef void (init_f)(void *elt);
51
typedef struct {
52
size_t sz;
53
init_f *init;
54
ctor_f *copy;
55
dtor_f *dtor;
56
} UT_icd;
57
58
typedef struct {
59
unsigned i,n;/* i: index of next available slot, n: num slots */
60
UT_icd icd; /* initializer, copy and destructor functions */
61
char *d; /* n slots of size icd->sz*/
62
} UT_array;
63
64
#define utarray_init(a,_icd) do { \
65
memset(a,0,sizeof(UT_array)); \
66
(a)->icd=*_icd; \
67
} while(0)
68
69
#define utarray_done(a) do { \
70
if ((a)->n) { \
71
if ((a)->icd.dtor) { \
72
size_t _ut_i; \
73
for(_ut_i=0; _ut_i < (a)->i; _ut_i++) { \
74
(a)->icd.dtor(utarray_eltptr(a,_ut_i)); \
75
} \
76
} \
77
free((a)->d); \
78
} \
79
(a)->n=0; \
80
} while(0)
81
82
#define utarray_new(a,_icd) do { \
83
a=(UT_array*)malloc(sizeof(UT_array)); \
84
utarray_init(a,_icd); \
85
} while(0)
86
87
#define utarray_free(a) do { \
88
utarray_done(a); \
89
free(a); \
90
} while(0)
91
92
#define utarray_reserve(a,by) do { \
93
if (((a)->i+by) > ((a)->n)) { \
94
while(((a)->i+by) > ((a)->n)) { (a)->n = ((a)->n ? (2*(a)->n) : 8); } \
95
if ( ((a)->d=(char*)realloc((a)->d, (a)->n*(a)->icd.sz)) == NULL) oom(); \
96
} \
97
} while(0)
98
99
#define utarray_push_back(a,p) do { \
100
utarray_reserve(a,1); \
101
if ((a)->icd.copy) { (a)->icd.copy( _utarray_eltptr(a,(a)->i++), p); } \
102
else { memcpy(_utarray_eltptr(a,(a)->i++), p, (a)->icd.sz); }; \
103
} while(0)
104
105
#define utarray_pop_back(a) do { \
106
if ((a)->icd.dtor) { (a)->icd.dtor( _utarray_eltptr(a,--((a)->i))); } \
107
else { (a)->i--; } \
108
} while(0)
109
110
#define utarray_extend_back(a) do { \
111
utarray_reserve(a,1); \
112
if ((a)->icd.init) { (a)->icd.init(_utarray_eltptr(a,(a)->i)); } \
113
else { memset(_utarray_eltptr(a,(a)->i),0,(a)->icd.sz); } \
114
(a)->i++; \
115
} while(0)
116
117
#define utarray_len(a) ((a)->i)
118
119
#define utarray_eltptr(a,j) (((j) < (a)->i) ? _utarray_eltptr(a,j) : NULL)
120
#define _utarray_eltptr(a,j) ((char*)((a)->d + ((a)->icd.sz*(j) )))
121
122
#define utarray_insert(a,p,j) do { \
123
utarray_reserve(a,1); \
124
if (j > (a)->i) break; \
125
if ((j) < (a)->i) { \
126
memmove( _utarray_eltptr(a,(j)+1), _utarray_eltptr(a,j), \
127
((a)->i - (j))*((a)->icd.sz)); \
128
} \
129
if ((a)->icd.copy) { (a)->icd.copy( _utarray_eltptr(a,j), p); } \
130
else { memcpy(_utarray_eltptr(a,j), p, (a)->icd.sz); }; \
131
(a)->i++; \
132
} while(0)
133
134
#define utarray_inserta(a,w,j) do { \
135
if (utarray_len(w) == 0) break; \
136
if (j > (a)->i) break; \
137
utarray_reserve(a,utarray_len(w)); \
138
if ((j) < (a)->i) { \
139
memmove(_utarray_eltptr(a,(j)+utarray_len(w)), \
140
_utarray_eltptr(a,j), \
141
((a)->i - (j))*((a)->icd.sz)); \
142
} \
143
if ((a)->icd.copy) { \
144
size_t _ut_i; \
145
for(_ut_i=0;_ut_i<(w)->i;_ut_i++) { \
146
(a)->icd.copy(_utarray_eltptr(a,j+_ut_i), _utarray_eltptr(w,_ut_i)); \
147
} \
148
} else { \
149
memcpy(_utarray_eltptr(a,j), _utarray_eltptr(w,0), \
150
utarray_len(w)*((a)->icd.sz)); \
151
} \
152
(a)->i += utarray_len(w); \
153
} while(0)
154
155
#define utarray_resize(dst,num) do { \
156
size_t _ut_i; \
157
if (dst->i > (size_t)(num)) { \
158
if ((dst)->icd.dtor) { \
159
for(_ut_i=num; _ut_i < dst->i; _ut_i++) { \
160
(dst)->icd.dtor(utarray_eltptr(dst,_ut_i)); \
161
} \
162
} \
163
} else if (dst->i < (size_t)(num)) { \
164
utarray_reserve(dst,num-dst->i); \
165
if ((dst)->icd.init) { \
166
for(_ut_i=dst->i; _ut_i < num; _ut_i++) { \
167
(dst)->icd.init(utarray_eltptr(dst,_ut_i)); \
168
} \
169
} else { \
170
memset(_utarray_eltptr(dst,dst->i),0,(dst)->icd.sz*(num-dst->i)); \
171
} \
172
} \
173
dst->i = num; \
174
} while(0)
175
176
#define utarray_concat(dst,src) do { \
177
utarray_inserta((dst),(src),utarray_len(dst)); \
178
} while(0)
179
180
#define utarray_erase(a,pos,len) do { \
181
if ((a)->icd.dtor) { \
182
size_t _ut_i; \
183
for(_ut_i=0; _ut_i < len; _ut_i++) { \
184
(a)->icd.dtor(utarray_eltptr((a),pos+_ut_i)); \
185
} \
186
} \
187
if ((a)->i > (pos+len)) { \
188
memmove( _utarray_eltptr((a),pos), _utarray_eltptr((a),pos+len), \
189
(((a)->i)-(pos+len))*((a)->icd.sz)); \
190
} \
191
(a)->i -= (len); \
192
} while(0)
193
194
#define utarray_renew(a,u) do { \
195
if (a) utarray_clear(a); \
196
else utarray_new((a),(u)); \
197
} while(0)
198
199
#define utarray_clear(a) do { \
200
if ((a)->i > 0) { \
201
if ((a)->icd.dtor) { \
202
size_t _ut_i; \
203
for(_ut_i=0; _ut_i < (a)->i; _ut_i++) { \
204
(a)->icd.dtor(utarray_eltptr(a,_ut_i)); \
205
} \
206
} \
207
(a)->i = 0; \
208
} \
209
} while(0)
210
211
#define utarray_sort(a,cmp) do { \
212
qsort((a)->d, (a)->i, (a)->icd.sz, cmp); \
213
} while(0)
214
215
#define utarray_find(a,v,cmp) bsearch((v),(a)->d,(a)->i,(a)->icd.sz,cmp)
216
217
#define utarray_front(a) (((a)->i) ? (_utarray_eltptr(a,0)) : NULL)
218
#define utarray_next(a,e) (((e)==NULL) ? utarray_front(a) : (((int)((a)->i) > (utarray_eltidx(a,e)+1)) ? _utarray_eltptr(a,utarray_eltidx(a,e)+1) : NULL))
219
#define utarray_prev(a,e) (((e)==NULL) ? utarray_back(a) : ((utarray_eltidx(a,e) > 0) ? _utarray_eltptr(a,utarray_eltidx(a,e)-1) : NULL))
220
#define utarray_back(a) (((a)->i) ? (_utarray_eltptr(a,(a)->i-1)) : NULL)
221
#define utarray_eltidx(a,e) (((char*)(e) >= (char*)((a)->d)) ? (int)(((char*)(e) - (char*)((a)->d))/(a)->icd.sz) : -1)
222
223
/* last we pre-define a few icd for common utarrays of ints and strings */
224
static void utarray_str_cpy(void *dst, const void *src) {
225
char *const*_src = (char*const*)src, **_dst = (char**)dst;
226
*_dst = (*_src == NULL) ? NULL : strdup(*_src);
227
}
228
static void utarray_str_dtor(void *elt) {
229
char **eltc = (char**)elt;
230
if (*eltc) free(*eltc);
231
}
232
static const UT_icd ut_str_icd _UNUSED_ = {sizeof(char*),NULL,utarray_str_cpy,utarray_str_dtor};
233
static const UT_icd ut_int_icd _UNUSED_ = {sizeof(int),NULL,NULL,NULL};
234
static const UT_icd ut_ptr_icd _UNUSED_ = {sizeof(void*),NULL,NULL,NULL};
235
236
237
#endif /* UTARRAY_H */
238
239