585 lines
16 KiB
C
585 lines
16 KiB
C
#include <stdio.h>
|
|
#include <stdlib.h>
|
|
#include <unistd.h>
|
|
#include <string.h>
|
|
#include <stdarg.h>
|
|
#include <sys/time.h>
|
|
|
|
#include "akbuf.h"
|
|
|
|
akbuf_ctx *ctx_hash[AKBUF_CTX_HASH_SIZE];
|
|
unsigned int ctx_hash_initialized = 0;
|
|
unsigned int prng_initialized = 0;
|
|
|
|
//#define RANDFUNC vanilla_rand /* XXX */
|
|
#define RANDFUNC randfunc_inc
|
|
|
|
//#define AKBUF_DEBUG
|
|
|
|
#define AK_REALSIZE(size) (((size) <= GRAIN_SIZE && (size) != 0)? (size) : (((size) | (GRAIN_SIZE - 1)) + 1))
|
|
#define CTX_HASH_FN(hnd) ((hnd) & (AKBUF_CTX_HASH_SIZE - 1))
|
|
|
|
#ifdef AKBUF_TEST
|
|
#define AKBUF_DEBUG
|
|
#endif
|
|
|
|
#ifdef AKBUF_DEBUG
|
|
void dump_all_ctxs(void)
|
|
{
|
|
#if 0
|
|
akbuf_ctx *ctx;
|
|
|
|
printf("dumping ctxs head %.8x:\n", (unsigned int)ctx_head);
|
|
ctx = ctx_head;
|
|
while (ctx != NULL)
|
|
{
|
|
printf(" ctx @ %.8x; handle %.8x bufs %.8x\n", (unsigned int)ctx, (unsigned int)ctx->hnd, (unsigned int)ctx->head);
|
|
ctx = ctx->next;
|
|
}
|
|
printf("end of dump\n");
|
|
#endif
|
|
}
|
|
#endif
|
|
unsigned int vanilla_rand(void)
|
|
{
|
|
if (prng_initialized == 0)
|
|
{
|
|
struct timeval tv;
|
|
|
|
gettimeofday(&tv, NULL);
|
|
srand(tv.tv_sec ^ tv.tv_usec ^ (getpid() << 16));
|
|
prng_initialized = 1;
|
|
}
|
|
return rand();
|
|
}
|
|
static unsigned int cur_ctx;
|
|
unsigned int randfunc_inc(void)
|
|
{
|
|
if (prng_initialized == 0)
|
|
{
|
|
struct timeval tv;
|
|
|
|
gettimeofday(&tv, NULL);
|
|
cur_ctx = tv.tv_usec;
|
|
prng_initialized = 1;
|
|
}
|
|
return cur_ctx ++;
|
|
}
|
|
void akbuf_panic(unsigned char *file, unsigned int line, unsigned char *from_file, unsigned int from_line, unsigned char *format, ...)
|
|
{
|
|
char msg[2048];
|
|
|
|
va_list va;
|
|
if (from_file != NULL)
|
|
{
|
|
snprintf(msg, sizeof(msg) - 1, "AKbuf PANIC @ %s:%u (from %s:%u): ", file, line, from_file, from_line); msg[sizeof(msg) - 1] = 0;
|
|
} else
|
|
{
|
|
snprintf(msg, sizeof(msg) - 1, "AKbuf PANIC @ %s:%u: ", file, line); msg[sizeof(msg) - 1] = 0;
|
|
}
|
|
write(2, msg, strlen(msg));
|
|
va_start(va, format);
|
|
vsnprintf(msg, sizeof(msg) - 1, format, va); msg[sizeof(msg) - 1] = 0;
|
|
va_end(va);
|
|
write(2, msg, strlen(msg));
|
|
write(2, "\n", 1);
|
|
_exit(1);
|
|
}
|
|
akbuf_ctx *akbuf_find_ctx(akbuf_ctxh hnd)
|
|
{
|
|
akbuf_ctx *cur;
|
|
|
|
if (ctx_hash_initialized == 0)
|
|
{
|
|
unsigned int i;
|
|
|
|
for (i = 0; i < AKBUF_CTX_HASH_SIZE; i ++) ctx_hash[i] = NULL;
|
|
ctx_hash_initialized = 1;
|
|
}
|
|
cur = ctx_hash[CTX_HASH_FN(hnd)];
|
|
while (cur != NULL) { if (cur->hnd == hnd) return cur; cur = cur->next; }
|
|
return NULL;
|
|
}
|
|
akbuf_ctxh akbuf_new_ctx(void)
|
|
{
|
|
akbuf_ctx *newCtx;
|
|
unsigned int idx;
|
|
|
|
newCtx = malloc(sizeof(*newCtx));
|
|
AKbuf_ASSERT(newCtx != NULL);
|
|
do
|
|
{
|
|
newCtx->hnd = RANDFUNC();
|
|
} while (akbuf_find_ctx(newCtx->hnd) != NULL || newCtx->hnd == AKbuf_INVALID_CTX);
|
|
newCtx->head = NULL;
|
|
newCtx->prev = NULL;
|
|
newCtx->next = ctx_hash[idx = CTX_HASH_FN(newCtx->hnd)];
|
|
if (newCtx->next != NULL) newCtx->next->prev = newCtx;
|
|
ctx_hash[idx] = newCtx;
|
|
return newCtx->hnd;
|
|
}
|
|
akbuf *akbuf_init(akbuf_ctxh ctxh, AKsize_t _size)
|
|
{
|
|
AKsize_t size;
|
|
akbuf *newBuf;
|
|
akbuf_ctx *ctx;
|
|
|
|
if ((ctx = akbuf_find_ctx(ctxh)) == NULL) AKbuf_PANIC("akbuf_init(): Invalid ctx %.8x", ctxh);
|
|
size = AK_REALSIZE(_size);
|
|
#ifdef AKBUF_DEBUG
|
|
printf("DEBUG: req size %.8x, final size %.8x\n", _size, size);
|
|
#endif
|
|
AKbuf_ASSERT(size >= _size);
|
|
newBuf = malloc(sizeof(akbuf));
|
|
AKbuf_ASSERT(newBuf != NULL);
|
|
newBuf->in_use = 1;
|
|
newBuf->size = size;
|
|
newBuf->idx = 0;
|
|
newBuf->prev = NULL;
|
|
newBuf->next = ctx->head;
|
|
newBuf->head = malloc(size);
|
|
AKbuf_ASSERT(newBuf->head != NULL);
|
|
if (ctx->head != NULL) ctx->head->prev = newBuf;
|
|
ctx->head = newBuf;
|
|
#ifdef AKBUF_DEBUG
|
|
memset(newBuf->head, 'A', newBuf->size);
|
|
#endif
|
|
return newBuf;
|
|
}
|
|
void akbuf_set_size(akbuf *buf, AKsize_t _size)
|
|
{
|
|
AKsize_t size;
|
|
|
|
AKbuf_dASSERT(buf != NULL);
|
|
size = AK_REALSIZE(_size);
|
|
AKbuf_ASSERT(size >= _size);
|
|
if (size == buf->size) return;
|
|
buf->head = realloc(buf->head, size);
|
|
AKbuf_ASSERT(buf->head != NULL);
|
|
buf->size = size;
|
|
if (buf->idx > size) buf->idx = size;
|
|
return;
|
|
}
|
|
void akbuf_consume(akbuf *buf, AKsize_t len)
|
|
{
|
|
AKbuf_dASSERT(buf != NULL);
|
|
if (len == 0) return;
|
|
AKbuf_ASSERT(buf->idx >= len && buf->idx <= buf->size);
|
|
memcpy(buf->head, buf->head + len, buf->idx - len);
|
|
buf->idx -= len;
|
|
if (len >= GRAIN_SIZE) akbuf_set_size(buf, buf->idx);
|
|
return;
|
|
}
|
|
unsigned char akbuf_eat_byte(akbuf *buf)
|
|
{
|
|
unsigned char ret;
|
|
|
|
AKbuf_dASSERT(buf != NULL);
|
|
AKbuf_ASSERT(buf->idx > 0 && buf->idx <= buf->size);
|
|
ret = *buf->head;
|
|
memcpy(buf->head, buf->head + 1, buf->idx - 1);
|
|
buf->idx --;
|
|
return ret;
|
|
}
|
|
void akbuf_set_data(akbuf *buf, unsigned char *data, AKsize_t len)
|
|
{
|
|
AKbuf_dASSERT(buf != NULL && data != NULL);
|
|
if (len > buf->size) akbuf_set_size(buf, len);
|
|
memcpy(buf->head, data, len);
|
|
buf->idx = len;
|
|
return;
|
|
}
|
|
void akbuf_vsprintf(akbuf *buf, unsigned char *format, va_list va)
|
|
{
|
|
AKssize_t n;
|
|
|
|
AKbuf_dASSERT(buf != NULL && format != NULL);
|
|
if ((n = vsnprintf(buf->head, buf->size, format, va)) >= buf->size && n >= 0)
|
|
{
|
|
AKbuf_ASSERT((n + 1) > n);
|
|
akbuf_set_size(buf, n + 1);
|
|
n = vsnprintf(buf->head, buf->size, format, va);
|
|
}
|
|
AKbuf_ASSERT(n >= 0);
|
|
buf->idx = n;
|
|
return;
|
|
}
|
|
void akbuf_sprintf(akbuf *buf, unsigned char *format, ...)
|
|
{
|
|
va_list va;
|
|
|
|
va_start(va, format);
|
|
akbuf_vsprintf(buf, format, va);
|
|
va_end(va);
|
|
return;
|
|
}
|
|
void akbuf_appendf(akbuf *buf, unsigned char *format, ...)
|
|
{
|
|
akbuf_ctxh ctx;
|
|
akbuf *appendbuf;
|
|
va_list va;
|
|
|
|
ctx = akbuf_new_ctx();
|
|
appendbuf = akbuf_init(ctx, 0);
|
|
va_start(va, format);
|
|
akbuf_vsprintf(appendbuf, format, va);
|
|
va_end(va);
|
|
akbuf_append_buf(buf, appendbuf);
|
|
akbuf_free_ctx(ctx);
|
|
}
|
|
void akbuf_append_data(akbuf *buf, unsigned char *data, AKsize_t len)
|
|
{
|
|
AKbuf_dASSERT(buf != NULL && data != NULL);
|
|
AKbuf_ASSERT(buf->idx + len >= buf->idx && buf->idx <= buf->size);
|
|
if (buf->idx + len >= buf->size) akbuf_set_size(buf, buf->idx + len);
|
|
memcpy(buf->head + buf->idx, data, len); buf->idx += len;
|
|
return;
|
|
}
|
|
void akbuf_append_byte(akbuf *buf, unsigned char b)
|
|
{
|
|
AKbuf_dASSERT(buf != NULL);
|
|
AKbuf_ASSERT(buf->idx + 1 > buf->idx && buf->idx <= buf->size);
|
|
if (buf->idx + 1 >= buf->size) akbuf_set_size(buf, buf->idx + 1);
|
|
buf->head[buf->idx ++] = b;
|
|
return;
|
|
}
|
|
int akbuf_chr(akbuf *buf, unsigned char b)
|
|
{
|
|
unsigned char *p;
|
|
|
|
AKbuf_dASSERT(buf != NULL);
|
|
if ((p = memchr(buf->head, b, buf->idx)) == NULL) return -1;
|
|
return (int)(p - buf->head);
|
|
}
|
|
void akbuf_asciiz(akbuf *buf)
|
|
{
|
|
AKbuf_dASSERT(buf != NULL);
|
|
AKbuf_ASSERT(buf->idx + 1 > buf->idx && buf->idx <= buf->size);
|
|
if (buf->idx == buf->size) akbuf_set_size(buf, buf->idx + 1);
|
|
buf->head[buf->idx] = 0;
|
|
return;
|
|
}
|
|
void akbuf_free(akbuf_ctxh ctxh, akbuf *buf)
|
|
{
|
|
akbuf_ctx *ctx;
|
|
akbuf *cur;
|
|
|
|
AKbuf_dASSERT(buf != NULL);
|
|
if ((ctx = akbuf_find_ctx(ctxh)) == NULL) AKbuf_PANIC("akbuf_free(): Invalid ctx %.8x", ctxh);
|
|
cur = ctx->head;
|
|
while (cur != buf && cur != NULL) cur = cur->next;
|
|
if (cur == NULL) AKbuf_PANIC("akbuf_free(): Unknown akbuf %.8x", (unsigned int)buf);
|
|
#ifdef AKBUF_DEBUG
|
|
printf("DEBUG: freeing buf %.8x\n", (unsigned int)cur);
|
|
#endif
|
|
AKbuf_ASSERT(cur->in_use == 1 && cur->head != NULL);
|
|
cur->in_use = 0;
|
|
if (cur->prev != NULL) cur->prev->next = cur->next;
|
|
if (cur->next != NULL) cur->next->prev = cur->prev;
|
|
if (cur == ctx->head) ctx->head = cur->next;
|
|
cur->prev = cur->next = NULL;
|
|
cur->idx = (unsigned int)-1;
|
|
#ifdef AKBUF_DEBUG
|
|
memset(cur->head, 'F', cur->size);
|
|
#else
|
|
//memset(cur->head, 'F', (cur->size > GRAIN_SIZE)? GRAIN_SIZE : cur->size);
|
|
#endif
|
|
cur->size = 0;
|
|
AKfree(cur->head); cur->head = NULL;
|
|
free(cur);
|
|
}
|
|
void _akbuf_free_ctx(akbuf_ctxh ctxh, unsigned char *from_file, unsigned int from_line)
|
|
{
|
|
akbuf_ctx *ctx;
|
|
akbuf *cur, *prev;
|
|
unsigned int idx;
|
|
|
|
if (ctxh == AKbuf_INVALID_CTX) return;
|
|
if ((ctx = akbuf_find_ctx(ctxh)) == NULL) AKbuf_PANIC_FROM("akbuf_free_ctx(): Invalid ctx %.8x", ctxh);
|
|
cur = ctx->head;
|
|
while (cur != NULL)
|
|
{
|
|
prev = cur;
|
|
cur = cur->next;
|
|
AKbuf_ASSERT(prev->in_use == 1 && prev->head != NULL);
|
|
prev->in_use = 0;
|
|
prev->prev = prev->next = NULL;
|
|
prev->idx = (unsigned int)-1;
|
|
#ifdef AKBUF_DEBUG
|
|
printf("DEBUG: prev %.8x prev->size %.8x\n", (unsigned int)prev, prev->size);
|
|
memset(prev->head, 'G', prev->size);
|
|
#endif
|
|
//memset(prev->head, 'F', (prev->size > GRAIN_SIZE)? GRAIN_SIZE : prev->size);
|
|
prev->size = 0;
|
|
AKfree(prev->head); prev->head = NULL;
|
|
free(prev);
|
|
}
|
|
ctx->head = NULL;
|
|
if (ctx->prev != NULL) ctx->prev->next = ctx->next;
|
|
if (ctx->next != NULL) ctx->next->prev = ctx->prev;
|
|
if (ctx == ctx_hash[idx = CTX_HASH_FN(ctxh)]) ctx_hash[idx] = ctx->next;
|
|
#ifdef AKBUF_DEBUG
|
|
memset(ctx, 'C', sizeof(akbuf_ctx));
|
|
#endif
|
|
free(ctx);
|
|
}
|
|
akbuf_table *akbuf_table_init(akbuf_ctxh ctxh, unsigned int type)
|
|
{
|
|
akbuf *tblbuf;
|
|
akbuf_table *ret;
|
|
|
|
tblbuf = akbuf_init(ctxh, sizeof(akbuf_table));
|
|
AKbuf_dASSERT(tblbuf != NULL);
|
|
akbuf_set_idx(tblbuf, sizeof(akbuf_table));
|
|
ret = (akbuf_table *)akbuf_data(tblbuf);
|
|
ret->head = ret->tail = NULL;
|
|
ret->type = type;
|
|
ret->ctxh = ctxh;
|
|
return ret;
|
|
}
|
|
akbuf_table_entry *akbuf_table_entry_add(akbuf_ctxh ctxh, akbuf_table *tbl, unsigned char *key, akbuf *data)
|
|
{
|
|
akbuf *entbuf;
|
|
akbuf_table_entry *new;
|
|
|
|
AKbuf_dASSERT(tbl != NULL && key != NULL && data != NULL);
|
|
AKbuf_ASSERT(ctxh == tbl->ctxh);
|
|
if (akbuf_find_ctx(ctxh) == NULL) AKbuf_PANIC("akbuf_table_entry_add(): Invalid ctx %.08x", ctxh);
|
|
if ((new = akbuf_table_entry_find(tbl, key)) != NULL)
|
|
{
|
|
akbuf_clone(new->data, data);
|
|
return new;
|
|
}
|
|
entbuf = akbuf_init(ctxh, sizeof(akbuf_table_entry));
|
|
AKbuf_dASSERT(entbuf != NULL);
|
|
akbuf_set_idx(entbuf, sizeof(akbuf_table_entry));
|
|
new = (akbuf_table_entry *)akbuf_data(entbuf);
|
|
new->key = akbuf_init(ctxh, 0);
|
|
akbuf_strcpy(new->key, key);
|
|
akbuf_append_byte(new->key, 0);
|
|
new->data = akbuf_init(ctxh, akbuf_idx(data));
|
|
akbuf_clone(new->data, data);
|
|
new->prev = tbl->tail;
|
|
new->next = NULL;
|
|
if (tbl->head == NULL)
|
|
{
|
|
tbl->head = new;
|
|
} else
|
|
{
|
|
tbl->tail->next = new;
|
|
}
|
|
tbl->tail = new;
|
|
return new;
|
|
}
|
|
akbuf_table_entry *akbuf_table_entry_add_buf(akbuf_ctxh ctxh, akbuf_table *tbl, akbuf *key, akbuf *data)
|
|
{
|
|
akbuf *entbuf;
|
|
akbuf_table_entry *new;
|
|
|
|
AKbuf_dASSERT(tbl != NULL && key != NULL && data != NULL);
|
|
AKbuf_ASSERT(tbl->type == AKBUF_TABLE_BIN);
|
|
AKbuf_ASSERT(ctxh == tbl->ctxh);
|
|
if (akbuf_find_ctx(ctxh) == NULL) AKbuf_PANIC("akbuf_table_entry_add(): Invalid ctx %.08x", ctxh);
|
|
entbuf = akbuf_init(ctxh, sizeof(akbuf_table_entry));
|
|
AKbuf_dASSERT(entbuf != NULL);
|
|
akbuf_set_idx(entbuf, sizeof(akbuf_table_entry));
|
|
new = (akbuf_table_entry *)akbuf_data(entbuf);
|
|
new->key = akbuf_init(ctxh, akbuf_idx(key));
|
|
akbuf_clone(new->key, key);
|
|
akbuf_append_byte(new->key, 0);
|
|
new->data = akbuf_init(ctxh, akbuf_idx(data));
|
|
akbuf_clone(new->data, data);
|
|
new->prev = tbl->tail;
|
|
new->next = NULL;
|
|
if (tbl->head == NULL)
|
|
{
|
|
tbl->head = new;
|
|
} else
|
|
{
|
|
tbl->tail->next = new;
|
|
}
|
|
tbl->tail = new;
|
|
return new;
|
|
}
|
|
akbuf_table_entry *akbuf_table_entry_add_str(akbuf_ctxh ctxh, akbuf_table *tbl, unsigned char *key, unsigned char *data)
|
|
{
|
|
akbuf *buf;
|
|
akbuf_ctxh ctx;
|
|
akbuf_table_entry *ret;
|
|
|
|
ctx = akbuf_new_ctx();
|
|
buf = akbuf_init(ctx, 0);
|
|
akbuf_strcpy(buf, data); akbuf_append_byte(buf, 0);
|
|
ret = akbuf_table_entry_add(ctxh, tbl, key, buf);
|
|
akbuf_free_ctx(ctx);
|
|
return ret;
|
|
}
|
|
akbuf_table_entry *akbuf_table_entry_find(akbuf_table *tbl, unsigned char *key)
|
|
{
|
|
int (*cmpfn)();
|
|
akbuf_table_entry *ent;
|
|
|
|
AKbuf_dASSERT(tbl != NULL && key != NULL);
|
|
AKbuf_ASSERT(tbl->type == AKBUF_TABLE_NOCASE || tbl->type == AKBUF_TABLE_CASE);
|
|
cmpfn = (tbl->type == AKBUF_TABLE_CASE)? strcmp : strcasecmp;
|
|
ent = tbl->head;
|
|
while (ent != NULL)
|
|
{
|
|
if (cmpfn(akbuf_data(ent->key), key) == 0) return ent;
|
|
ent = ent->next;
|
|
}
|
|
return NULL;
|
|
}
|
|
akbuf *akbuf_table_entry_get(akbuf_table *tbl, unsigned char *key)
|
|
{
|
|
akbuf_table_entry *ent;
|
|
|
|
if ((ent = akbuf_table_entry_find(tbl, key)) == NULL) return NULL;
|
|
return ent->data;
|
|
}
|
|
unsigned char *akbuf_table_entry_get_str(akbuf_table *tbl, unsigned char *key)
|
|
{
|
|
akbuf *buf;
|
|
|
|
if ((buf = akbuf_table_entry_get(tbl, key)) == NULL) return NULL;
|
|
akbuf_asciiz(buf);
|
|
return akbuf_data(buf);
|
|
}
|
|
|
|
void akbuf_urlencode_data(unsigned char *data, AKsize_t len, akbuf *outbuf)
|
|
{
|
|
unsigned int i;
|
|
unsigned int c;
|
|
|
|
for (i = 0; i < len; i ++)
|
|
{
|
|
unsigned char hexchars[] = "0123456789ABCDEF";
|
|
|
|
c = data[i];
|
|
if ((c >= '0' && c <= '9') || (c >= 'A' && c <= 'Z') || (c >= 'a' && c <= '<'))
|
|
{
|
|
akbuf_append_byte(outbuf, c);
|
|
} else
|
|
{
|
|
akbuf_append_byte(outbuf, '%');
|
|
akbuf_append_byte(outbuf, hexchars[(c >> 4) & 0xf]);
|
|
akbuf_append_byte(outbuf, hexchars[c & 0xf]);
|
|
}
|
|
}
|
|
}
|
|
void akbuf_base64encode_data(unsigned char *data, AKsize_t len, akbuf *outbuf)
|
|
{
|
|
AKsize_t rem;
|
|
unsigned char b64chars[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
|
|
|
|
rem = len;
|
|
while (rem > 2)
|
|
{
|
|
akbuf_append_byte(outbuf, b64chars[data[0] >> 2]);
|
|
akbuf_append_byte(outbuf, b64chars[((data[0] & 0x03) << 4) + (data[1] >> 4)]);
|
|
akbuf_append_byte(outbuf, b64chars[((data[1] & 0x0f) << 2) + (data[2] >> 6)]);
|
|
akbuf_append_byte(outbuf, b64chars[data[2] & 0x3f]);
|
|
data += 3;
|
|
rem -= 3;
|
|
}
|
|
if (rem != 0)
|
|
{
|
|
akbuf_append_byte(outbuf, b64chars[data[0] >> 2]);
|
|
if (rem > 1)
|
|
{
|
|
akbuf_append_byte(outbuf, b64chars[((data[0] & 0x03) << 4) + (data[1] >> 4)]);
|
|
akbuf_append_byte(outbuf, b64chars[((data[1] & 0x0f) << 2)]);
|
|
akbuf_append_byte(outbuf, '=');
|
|
} else
|
|
{
|
|
akbuf_append_byte(outbuf, b64chars[((data[0] & 0x03) << 4)]);
|
|
akbuf_append_byte(outbuf, '=');
|
|
akbuf_append_byte(outbuf, '=');
|
|
}
|
|
}
|
|
}
|
|
|
|
#ifdef AKBUF_TEST
|
|
int main(int argc, char *argv[])
|
|
{
|
|
akbuf_ctxh ctx;
|
|
akbuf *buf, *buf2;
|
|
int i;
|
|
akbuf_table *tbl;
|
|
akbuf_table_entry *ent;
|
|
|
|
printf("akbuf_new_ctx()\n");
|
|
ctx = akbuf_new_ctx();
|
|
printf(" = %.8x\n", (unsigned int)ctx);
|
|
printf("akbuf_new_ctx() second = %.8x\n", (unsigned int)akbuf_new_ctx());
|
|
dump_all_ctxs();
|
|
|
|
buf = akbuf_init(ctx, 0);
|
|
akbuf_strcpy(buf, "blutti");
|
|
printf("akbuf_table_init() =\n");
|
|
tbl = akbuf_table_init(ctx, 0);
|
|
printf(" %.08x\n", (unsigned int)tbl);
|
|
printf("akbuf_table_entry_add() =\n");
|
|
ent = akbuf_table_entry_add(ctx, tbl, "foobar", buf);
|
|
printf(" %.08x\n", (unsigned int)ent);
|
|
printf("[%s]\n", akbuf_data(ent->key));
|
|
akbuf_strcpy(buf, "fnutti");
|
|
ent = akbuf_table_entry_add(ctx, tbl, "foobar2", buf);
|
|
printf(" next = %.08x prev = %.08x head = %.08x tail = %.08x\n", (unsigned int)ent->next, (unsigned int)ent->prev, (unsigned int)tbl->head, (unsigned int)tbl->tail);
|
|
printf("akbuf_table_entry_get(..., \"foobar\")\n");
|
|
buf2 = akbuf_table_entry_get(tbl, "foobar");
|
|
if (buf2 != NULL)
|
|
{
|
|
akbuf_asciiz(buf2);
|
|
printf(" [%s]\n", akbuf_data(buf2));
|
|
}
|
|
printf("akbuf_table_entry_get(..., \"foobar2\")\n");
|
|
buf2 = akbuf_table_entry_get(tbl, "foobar2");
|
|
if (buf2 != NULL)
|
|
{
|
|
akbuf_asciiz(buf2);
|
|
printf(" [%s]\n", akbuf_data(buf2));
|
|
}
|
|
|
|
#if 1
|
|
printf("akbuf_init(0x242)\n");
|
|
buf = akbuf_init(ctx, 0x242);
|
|
printf(" = %.8x\n", (unsigned int)buf);
|
|
//printf("akbuf_init(0xffffffff)\n");
|
|
//akbuf_init(ctx, 0xffffffff);
|
|
akbuf_strcpy(buf, "foobar blutti");
|
|
akbuf_append_str(buf, " fnutti");
|
|
akbuf_asciiz(buf);
|
|
printf("[%s]\n", akbuf_data(buf));
|
|
buf2 = akbuf_init(ctx, 0);
|
|
akbuf_strcpy(buf2, "1 2 3");
|
|
akbuf_append_str(buf2," 4 5 6");
|
|
akbuf_consume(buf2, 4);
|
|
akbuf_asciiz(buf2);
|
|
printf("[%s]\n", akbuf_data(buf2));
|
|
buf = akbuf_init(ctx, 0);
|
|
akbuf_sprintf(buf, "foobar %u [%s]", 0x242, "foo");
|
|
akbuf_asciiz(buf);
|
|
printf("fmt [%s]\n", akbuf_data(buf));
|
|
printf("freeing\n");
|
|
akbuf_free_ctx(ctx);
|
|
dump_all_ctxs();
|
|
ctx = akbuf_new_ctx();
|
|
buf = akbuf_init(ctx, 0x666);
|
|
akbuf_strcpy(buf, "foo\nbar\nblutti\nfnutti");
|
|
buf2 = akbuf_init(ctx, 0);
|
|
while ((i = akbuf_chr(buf, '\n')) != -1)
|
|
{
|
|
akbuf_split(buf, buf2, i);
|
|
akbuf_asciiz(buf2);
|
|
printf("split [%s]\n", akbuf_data(buf2));
|
|
}
|
|
akbuf_asciiz(buf);
|
|
printf("rem [%s]\n", akbuf_data(buf));
|
|
dump_all_ctxs();
|
|
akbuf_free_ctx(ctx);
|
|
#endif
|
|
akbuf_free_ctx(ctx);
|
|
return 0;
|
|
}
|
|
#endif
|