Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
- #include <stdint.h>
- typedef struct
- {
- // Element properties
- uint32_t e_size;
- uint32_t e_max;
- // >0 if we want to resize array
- uint8_t resize;
- void **index;
- void *elements;
- } dynarray_t;
- // Create the array on the heap, initialize.
- dynarray_t *dynarray_create (uint32_t size, uint32_t max, uint8_t resize)
- {
- dynarray_t *ret = (dynarray_t *) malloc (sizeof (dynarray_t));
- if (!ret)
- return NULL;
- memset (ret, 0, sizeof (dynarray_t));
- ret->e_size = size;
- ret->e_max = max;
- ret->resize = resize;
- ret->index = (void **) malloc (max * sizeof (void *));
- ret->elements = malloc (size * max);
- if (!ret->index || !ret->elements)
- {
- free (ret);
- return NULL;
- }
- memset (ret->index, 0, max * sizeof (void *));
- memset (ret->elements, 0, size * max);
- return ret;
- }
- // Destroy dynarray
- void dynarray_delete (dynarray_t *arr)
- {
- free (arr->index);
- free (arr->elements);
- free (arr);
- return;
- }
- // Resize array, adding arr->resize elements
- // returns arr on success, NULL on failure
- dynarray_t *dynarray_resize (dynarray_t *arr)
- {
- void *tmp;
- if (!(tmp = realloc (arr->index, arr->e_max * sizeof (void *) + arr->resize * sizeof (void *))))
- return NULL;
- else
- arr->index = tmp;
- if (!(tmp = realloc (arr->elements, arr->e_max * arr->e_size + arr->resize * arr->e_size)))
- return NULL;
- // Adjust index if necessary
- void *oldel = arr->elements;
- arr->elements = tmp;
- if (arr->elements != oldel)
- {
- int i;
- for (i = 0; i < arr->e_max; i++)
- if (arr->index [i])
- arr->index [i] = ((char*)arr->elements) + arr->e_size * i;
- }
- // Initialize new memory
- memset (arr->index + arr->e_max, 0, arr->resize * sizeof (void *));
- memset ((char*)arr->elements + arr->e_max * arr->e_size, 0, arr->resize * arr->e_size);
- arr->e_max += arr->resize;
- return arr;
- }
- // Add element to array, returns pointer to new element or NULL on failure
- void *dynarray_push (dynarray_t *arr, void *new)
- {
- // Valid?
- if (!arr || !new)
- return NULL;
- // Find empty slot
- int i;
- for (i = 0; i < arr->e_max; i++)
- if (arr->index [i] == NULL)
- break;
- if (i == arr->e_max) // Out of room, resize!
- {
- if (arr->resize)
- {
- return dynarray_push (dynarray_resize (arr), new);
- }
- else
- return NULL;
- }
- return arr->index [i] = memcpy ((char*)arr->elements + arr->e_size * i, new, arr->e_size);
- }
- // Clear element from array
- void dynarray_clear (dynarray_t *arr, uint32_t ele)
- {
- if (!arr || ele > arr->e_max)
- return;
- arr->index [ele] = NULL;
- memset ((char*)arr->elements + ele * arr->e_size, 0, arr->e_size);
- return;
- // Pop top element from array, write it to a pointer
- void dynarray_pop (dynarray_t *arr, void *dest)
- {
- if (!arr || !dest)
- return;
- int i;
- for (i = arr->e_max - 1; i >= 0; i--)
- if (arr->index [i])
- break;
- memcpy (dest, arr->index [i], arr->e_size);
- dynarray_clear (arr, i);
- return;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement