core: Add pointer box / RAII impl
Signed-off-by: Ian Moffett <ian@mirocom.org>
This commit is contained in:
+132
@@ -0,0 +1,132 @@
|
||||
/*
|
||||
* Copyright (c) 2026, Chloe M.
|
||||
* Provided under the BSD-3 clause
|
||||
*/
|
||||
|
||||
#include <stddef.h>
|
||||
#include <stdint.h>
|
||||
#include <errno.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include "cescal/ptrbox.h"
|
||||
|
||||
/*
|
||||
* Allocate a pointer box entry to be used
|
||||
*/
|
||||
static struct ptrbox_entry *
|
||||
ptrbox_alloc_entry(void)
|
||||
{
|
||||
struct ptrbox_entry *entry;
|
||||
|
||||
if ((entry = malloc(sizeof(*entry))) == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
entry->data = NULL;
|
||||
entry->next = NULL;
|
||||
return entry;
|
||||
}
|
||||
|
||||
static int
|
||||
ptrbox_push_entry(struct ptrbox *ptrbox, struct ptrbox_entry *entry)
|
||||
{
|
||||
if (ptrbox == NULL || entry == NULL) {
|
||||
errno = EINVAL;
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (ptrbox->head == NULL || ptrbox->tail == NULL) {
|
||||
ptrbox->head = entry;
|
||||
ptrbox->tail = entry;
|
||||
} else {
|
||||
ptrbox->head->next = entry;
|
||||
ptrbox->head = entry;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
ptrbox_init(struct ptrbox *ptrbox)
|
||||
{
|
||||
if (ptrbox == NULL) {
|
||||
errno = EINVAL;
|
||||
return -1;
|
||||
}
|
||||
|
||||
ptrbox->head = NULL;
|
||||
ptrbox->tail = NULL;
|
||||
return 0;
|
||||
}
|
||||
|
||||
void *
|
||||
ptrbox_alloc(struct ptrbox *ptrbox, size_t len)
|
||||
{
|
||||
struct ptrbox_entry *entry;
|
||||
void *p;
|
||||
|
||||
if (ptrbox == NULL || len == 0) {
|
||||
errno = EINVAL;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if ((p = malloc(len)) == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if ((entry = ptrbox_alloc_entry()) == NULL) {
|
||||
free(p);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
entry->data = p;
|
||||
if (ptrbox_push_entry(ptrbox, entry) < 0) {
|
||||
free(p);
|
||||
free(entry);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
char *
|
||||
ptrbox_strdup(struct ptrbox *ptrbox, const char *s)
|
||||
{
|
||||
char *sdup;
|
||||
size_t slen;
|
||||
|
||||
if (ptrbox == NULL || s == NULL) {
|
||||
errno = EINVAL;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
slen = strlen(s) + 1;
|
||||
if ((sdup = ptrbox_alloc(ptrbox, slen)) == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
memcpy(sdup, s, slen);
|
||||
return sdup;
|
||||
}
|
||||
|
||||
void
|
||||
ptrbox_destroy(struct ptrbox *ptrbox)
|
||||
{
|
||||
struct ptrbox_entry *entry, *tmp;
|
||||
|
||||
if (ptrbox == NULL) {
|
||||
return;
|
||||
}
|
||||
|
||||
if ((entry = ptrbox->tail) == NULL) {
|
||||
return;
|
||||
}
|
||||
|
||||
while (entry != NULL) {
|
||||
tmp = entry;
|
||||
entry = entry->next;
|
||||
|
||||
free(tmp->data);
|
||||
free(tmp);
|
||||
}
|
||||
}
|
||||
@@ -33,6 +33,11 @@ state_init(struct cescal_state *state, const char *pathname)
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (ptrbox_init(&state->ptrbox) < 0) {
|
||||
close(state->in_fd);
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -41,4 +46,5 @@ state_close(struct cescal_state *state)
|
||||
{
|
||||
close(state->in_fd);
|
||||
state->in_fd = -1;
|
||||
ptrbox_destroy(&state->ptrbox);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user