aboutsummaryrefslogtreecommitdiff
path: root/src/common/list.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/common/list.c')
-rw-r--r--src/common/list.c78
1 files changed, 78 insertions, 0 deletions
diff --git a/src/common/list.c b/src/common/list.c
new file mode 100644
index 0000000..00c18ee
--- /dev/null
+++ b/src/common/list.c
@@ -0,0 +1,78 @@
+#include "../include/list.h"
+#include "../include/helpers.h"
+
+node_t *init_node(void *x) {
+ node_t *n = safe_calloc(1, sizeof(node_t));
+ n->item = x;
+ n->next = NULL;
+ n->prev = NULL;
+ return n;
+}
+
+list_t *init_list() {
+ list_t *l = safe_calloc(1, sizeof(list_t));
+ l->head = NULL;
+ l->tail = NULL;
+ l->size = 0;
+ return l;
+}
+
+void *list_pop_front(list_t *l) {
+ node_t *front = l->head;
+ if (!front)
+ return NULL;
+
+ node_t *new = front->next;
+ l->head = new;
+
+ if (!new)
+ l->tail = NULL;
+
+ l->size--;
+ return front;
+}
+
+void list_push_back(list_t *l, void *x) {
+ node_t *back = l->tail;
+ node_t *new = init_node(x);
+ if (!back) {
+ l->head = new;
+ l->tail = l->head;
+ } else {
+ back->next = new;
+ new->prev = back;
+ l->tail = new;
+ }
+ l->size++;
+}
+
+void list_push_front(list_t *l, void *x) {
+ node_t *front = l->head;
+ node_t *new = init_node(x);
+ if (!front) {
+ l->tail = new;
+ l->head = l->tail;
+ } else {
+ front->prev = new;
+ new->next = front;
+ l->head = new;
+ }
+ l->size++;
+}
+
+void list_free(void *x, void (*freefunc)(void *)) {
+ list_t *l = x;
+ node_t *cur = l->head;
+ node_t *tmp;
+
+ if (!x)
+ return;
+
+ while (cur) {
+ freefunc(cur->item);
+ tmp = cur->next;
+ free(cur);
+ cur = tmp;
+ }
+ free(l);
+}