2 Copyright 2020 Google LLC
4 Use of this source code is governed by a BSD-style
5 license that can be found in the LICENSE file or at
6 https://developers.google.com/open-source/licenses/bsd
9 #define REFTABLE_ALLOW_BANNED_ALLOCATORS
11 #include "reftable-basics.h"
12 #include "reftable-error.h"
14 static void *(*reftable_malloc_ptr
)(size_t sz
);
15 static void *(*reftable_realloc_ptr
)(void *, size_t);
16 static void (*reftable_free_ptr
)(void *);
18 void *reftable_malloc(size_t sz
)
20 if (reftable_malloc_ptr
)
21 return (*reftable_malloc_ptr
)(sz
);
25 void *reftable_realloc(void *p
, size_t sz
)
27 if (reftable_realloc_ptr
)
28 return (*reftable_realloc_ptr
)(p
, sz
);
29 return realloc(p
, sz
);
32 void reftable_free(void *p
)
34 if (reftable_free_ptr
)
40 void *reftable_calloc(size_t nelem
, size_t elsize
)
44 if (nelem
&& elsize
> SIZE_MAX
/ nelem
)
47 p
= reftable_malloc(nelem
* elsize
);
51 memset(p
, 0, nelem
* elsize
);
55 char *reftable_strdup(const char *str
)
57 size_t len
= strlen(str
);
58 char *result
= reftable_malloc(len
+ 1);
61 memcpy(result
, str
, len
+ 1);
65 void reftable_set_alloc(void *(*malloc
)(size_t),
66 void *(*realloc
)(void *, size_t), void (*free
)(void *))
68 reftable_malloc_ptr
= malloc
;
69 reftable_realloc_ptr
= realloc
;
70 reftable_free_ptr
= free
;
73 void reftable_buf_init(struct reftable_buf
*buf
)
75 struct reftable_buf empty
= REFTABLE_BUF_INIT
;
79 void reftable_buf_release(struct reftable_buf
*buf
)
81 reftable_free(buf
->buf
);
82 reftable_buf_init(buf
);
85 void reftable_buf_reset(struct reftable_buf
*buf
)
93 int reftable_buf_setlen(struct reftable_buf
*buf
, size_t len
)
104 int reftable_buf_cmp(const struct reftable_buf
*a
, const struct reftable_buf
*b
)
106 size_t len
= a
->len
< b
->len
? a
->len
: b
->len
;
108 int cmp
= memcmp(a
->buf
, b
->buf
, len
);
112 return a
->len
< b
->len
? -1 : a
->len
!= b
->len
;
115 int reftable_buf_add(struct reftable_buf
*buf
, const void *data
, size_t len
)
117 size_t newlen
= buf
->len
+ len
;
119 if (newlen
+ 1 > buf
->alloc
) {
120 char *reallocated
= buf
->buf
;
121 REFTABLE_ALLOC_GROW(reallocated
, newlen
+ 1, buf
->alloc
);
123 return REFTABLE_OUT_OF_MEMORY_ERROR
;
124 buf
->buf
= reallocated
;
127 memcpy(buf
->buf
+ buf
->len
, data
, len
);
128 buf
->buf
[newlen
] = '\0';
134 int reftable_buf_addstr(struct reftable_buf
*buf
, const char *s
)
136 return reftable_buf_add(buf
, s
, strlen(s
));
139 char *reftable_buf_detach(struct reftable_buf
*buf
)
141 char *result
= buf
->buf
;
142 reftable_buf_init(buf
);
146 void put_be24(uint8_t *out
, uint32_t i
)
148 out
[0] = (uint8_t)((i
>> 16) & 0xff);
149 out
[1] = (uint8_t)((i
>> 8) & 0xff);
150 out
[2] = (uint8_t)(i
& 0xff);
153 uint32_t get_be24(uint8_t *in
)
155 return (uint32_t)(in
[0]) << 16 | (uint32_t)(in
[1]) << 8 |
159 void put_be16(uint8_t *out
, uint16_t i
)
161 out
[0] = (uint8_t)((i
>> 8) & 0xff);
162 out
[1] = (uint8_t)(i
& 0xff);
165 size_t binsearch(size_t sz
, int (*f
)(size_t k
, void *args
), void *args
)
172 * (hi == sz) || f(hi) == true
173 * (lo == 0 && f(0) == true) || fi(lo) == false
175 while (hi
- lo
> 1) {
176 size_t mid
= lo
+ (hi
- lo
) / 2;
177 int ret
= f(mid
, args
);
190 return f(0, args
) ? 0 : 1;
193 void free_names(char **a
)
199 for (p
= a
; *p
; p
++) {
205 size_t names_length(const char **names
)
207 const char **p
= names
;
213 char **parse_names(char *buf
, int size
)
216 size_t names_cap
= 0;
217 size_t names_len
= 0;
219 char *end
= buf
+ size
;
222 char *next
= strchr(p
, '\n');
223 if (next
&& next
< end
) {
229 char **names_grown
= names
;
230 REFTABLE_ALLOC_GROW(names_grown
, names_len
+ 1, names_cap
);
235 names
[names_len
] = reftable_strdup(p
);
236 if (!names
[names_len
++])
242 REFTABLE_REALLOC_ARRAY(names
, names_len
+ 1);
243 names
[names_len
] = NULL
;
248 for (size_t i
= 0; i
< names_len
; i
++)
249 reftable_free(names
[i
]);
250 reftable_free(names
);
254 int names_equal(const char **a
, const char **b
)
257 for (; a
[i
] && b
[i
]; i
++)
258 if (strcmp(a
[i
], b
[i
]))
263 int common_prefix_size(struct reftable_buf
*a
, struct reftable_buf
*b
)
266 for (; p
< a
->len
&& p
< b
->len
; p
++) {
267 if (a
->buf
[p
] != b
->buf
[p
])
274 int hash_size(uint32_t id
)
278 case GIT_SHA1_FORMAT_ID
:
279 return GIT_SHA1_RAWSZ
;
280 case GIT_SHA256_FORMAT_ID
:
281 return GIT_SHA256_RAWSZ
;