]> jfr.im git - irc/quakenet/newserv.git/blob - lib/array.c
BUILD: add require-all build mode
[irc/quakenet/newserv.git] / lib / array.c
1 /*
2 unencumbered array.c
3 dynamic UNORDERED array (yes this got me...)
4
5 will grow by allocchunksize (by default 100) when full and
6 new space is requested.
7
8 will shrink by freechunksize (by default 150) if that many
9 items are not occupied at the end.
10
11 clean written from the function prototypes.
12 */
13
14 #include <stdio.h>
15 #include <stdlib.h>
16 #include <string.h>
17 #include "../core/error.h"
18
19 #include "array.h"
20
21 void array_init(array *a, unsigned int itemsize) {
22 a->content = NULL;
23 a->cursi = 0; /* count */
24
25 a->itemsize = itemsize;
26 a->capacity = 0;
27
28 /* allochunksize MUST be <= freechunksize */
29 a->allocchunksize = 100;
30 a->freechunksize = 150;
31 }
32
33 /* should be called free_and_reinit really */
34 void array_free(array *a) {
35 free(a->content);
36
37 array_init(a, a->itemsize);
38 }
39
40 int array_getfreeslot(array *a) {
41 if(a->cursi + 1 >= a->capacity) {
42 a->capacity += a->allocchunksize;
43
44 /* we can be evil and use the same pointer as we're gonna exit if we fail */
45 a->content = realloc(a->content, a->capacity * a->itemsize);
46
47 if(!a->content)
48 Error("array", ERR_STOP, "Array resize failed.");
49 }
50
51 return a->cursi++;
52 }
53
54 void array_delslot(array *a, unsigned int index) {
55 /* if we're not deleting the end item then swap the last item into the deleted items space */
56 /* unordered so we can do this, and we can also use memcpy */
57 if(--a->cursi != index)
58 memcpy((char *)a->content + index * a->itemsize, (char *)a->content + a->cursi * a->itemsize, a->itemsize);
59
60 if(a->cursi + a->freechunksize < a->capacity) {
61
62 a->capacity = a->cursi + a->allocchunksize;
63
64 if(a->capacity == 0) {
65 free(a->content);
66
67 a->content = NULL;
68 } else {
69 void *newp = realloc(a->content, a->capacity * a->itemsize);
70
71 if(!newp) {
72 Error("array", ERR_WARNING, "Unable to shrink array!");
73 } else {
74 a->content = newp;
75 }
76 }
77 }
78 }
79