zapret/tpws/strpool.c

108 lines
1.9 KiB
C

#define _GNU_SOURCE
#include "strpool.h"
#include <string.h>
#include <stdlib.h>
#undef uthash_nonfatal_oom
#define uthash_nonfatal_oom(elt) ut_oom_recover(elt)
static bool oom = false;
static void ut_oom_recover(strpool *elem)
{
oom = true;
}
// for zero terminated strings
bool StrPoolAddStr(strpool **pp, const char *s)
{
strpool *elem;
if (!(elem = (strpool*)malloc(sizeof(strpool))))
return false;
if (!(elem->str = strdup(s)))
{
free(elem);
return false;
}
oom = false;
HASH_ADD_KEYPTR(hh, *pp, elem->str, strlen(elem->str), elem);
if (oom)
{
free(elem->str);
free(elem);
return false;
}
return true;
}
// for not zero terminated strings
bool StrPoolAddStrLen(strpool **pp, const char *s, size_t slen)
{
strpool *elem;
if (!(elem = (strpool*)malloc(sizeof(strpool))))
return false;
if (!(elem->str = malloc(slen + 1)))
{
free(elem);
return false;
}
memcpy(elem->str, s, slen);
elem->str[slen] = 0;
oom = false;
HASH_ADD_KEYPTR(hh, *pp, elem->str, strlen(elem->str), elem);
if (oom)
{
free(elem->str);
free(elem);
return false;
}
return true;
}
bool StrPoolCheckStr(strpool *p, const char *s)
{
strpool *elem;
HASH_FIND_STR(p, s, elem);
return elem != NULL;
}
void StrPoolDestroy(strpool **p)
{
strpool *elem, *tmp;
HASH_ITER(hh, *p, elem, tmp) {
free(elem->str);
HASH_DEL(*p, elem);
free(elem);
}
*p = NULL;
}
bool strlist_add(struct str_list_head *head, const char *filename)
{
struct str_list *entry = malloc(sizeof(struct str_list));
if (!entry) return false;
entry->str = strdup(filename);
if (!entry->str)
{
free(entry);
return false;
}
LIST_INSERT_HEAD(head, entry, next);
return true;
}
static void strlist_entry_destroy(struct str_list *entry)
{
if (entry->str) free(entry->str);
free(entry);
}
void strlist_destroy(struct str_list_head *head)
{
struct str_list *entry;
while (entry = LIST_FIRST(head))
{
LIST_REMOVE(entry, next);
strlist_entry_destroy(entry);
}
}