#ifndef CCAN_DARRAY_H
#define CCAN_DARRAY_H
-/* Originally taken from: http://ccodearchive.net/info/darray.html
+/* Originally taken from: https://ccodearchive.net/info/darray.html
* But modified for libxkbcommon. */
#include <stdlib.h>
darray_init(arr); \
} while (0)
+#define darray_steal(arr, to, to_size) do { \
+ *(to) = (arr).item; \
+ if (to_size) \
+ *(unsigned int *) (to_size) = (arr).size; \
+ darray_init(arr); \
+} while (0)
+
/*
* Typedefs for darrays of common types. These are useful
* when you want to pass a pointer to an darray(T) around.
#define darray_item(arr, i) ((arr).item[i])
#define darray_size(arr) ((arr).size)
#define darray_empty(arr) ((arr).size == 0)
-#define darray_mem(arr, offset) ((arr).item + (offset))
/*** Insertion (single item) ***/
#define darray_from_items(arr, items, count) do { \
unsigned __count = (count); \
darray_resize(arr, __count); \
- memcpy((arr).item, items, __count * sizeof(*(arr).item)); \
+ if (__count != 0) \
+ memcpy((arr).item, items, __count * sizeof(*(arr).item)); \
} while (0)
#define darray_copy(arr_to, arr_from) \
darray_from_items((arr_to), (arr_from).item, (arr_from).size)
+#define darray_concat(arr_to, arr_from) \
+ darray_append_items((arr_to), (arr_from).item, (arr_from).size)
+
+/*** Removal ***/
+
+/* Warning: Do not call darray_remove_last on an empty darray. */
+#define darray_remove_last(arr) (--(arr).size)
+
/*** String buffer ***/
#define darray_append_string(arr, str) do { \
#define darray_growalloc(arr, need) do { \
unsigned __need = (need); \
if (__need > (arr).alloc) \
- darray_realloc(arr, darray_next_alloc((arr).alloc, __need, \
- sizeof(*(arr).item))); \
+ darray_realloc(arr, darray_next_alloc((arr).alloc, __need, \
+ sizeof(*(arr).item))); \
+} while (0)
+
+#define darray_shrink(arr) do { \
+ if ((arr).size > 0) \
+ (arr).item = realloc((arr).item, \
+ ((arr).alloc = (arr).size) * sizeof(*(arr).item)); \
} while (0)
static inline unsigned
(idx)++, (val)++)
#define darray_foreach_reverse(i, arr) \
- for ((i) = &(arr).item[(arr).size]; (i)-- > &(arr).item[0]; )
+ for ((i) = &(arr).item[(arr).size - 1]; (arr).size > 0 && (i) >= &(arr).item[0]; (i)--)
#endif /* CCAN_DARRAY_H */