diff --git a/buffer.c b/buffer.c new file mode 100644 index 0000000..4fb09e0 --- /dev/null +++ b/buffer.c @@ -0,0 +1,81 @@ +/* buffer.c + * + * Copyright (C) 2010-2011 Henrik Hautakoski + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, + * MA 02110-1301, USA. + */ + +#include +#include +#include "error.h" +#include "buffer.h" + +#define CHNK_SIZE 128 + +unsigned char buffer_null = '\0'; + +void buffer_init(struct buffer *b) { + + b->block = &buffer_null; + b->size = b->len = 0; +} + +void buffer_expand(struct buffer *b, size_t len) { + + if (b->len + len < b->size) + return; + if (!b->size) + b->block = NULL; + + do + b->size += CHNK_SIZE; + while(b->len + len > b->size); + + b->block = realloc(b->block, b->size); +} + +char* buffer_cstr(struct buffer *b) { + + buffer_expand(b, 1); + b->block[b->len + 1] = '\0'; + + return (char*) b->block; +} + +void buffer_free(struct buffer *b) { + + if (!b->size) + return; + + free(b->block); + buffer_init(b); +} + +void buffer_attach(struct buffer *b, void *ptr, size_t len, size_t size) { + + buffer_free(b); + b->block = ptr; + b->len = len; + b->size = size; + buffer_expand(b, 0); +} + +void buffer_append(struct buffer *b, const void *ptr, size_t len) { + + buffer_expand(b, len); + memcpy(b->block + b->len, ptr, len); + buffer_setlen(b, b->len + len); +} diff --git a/buffer.h b/buffer.h new file mode 100644 index 0000000..8b3faae --- /dev/null +++ b/buffer.h @@ -0,0 +1,96 @@ +/* buffer.h + * + * Copyright (C) 2010-2011 Henrik Hautakoski + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, + * MA 02110-1301, USA. + */ + +#ifndef BUFFER_H +#define BUFFER_H + +#include +#include + +struct buffer { + unsigned char *block; + size_t len; + size_t size; +}; + +extern unsigned char buffer_null; + +#define BUFFER_INIT { &buffer_null, 0, 0 } + +void buffer_init(struct buffer *b); + +static inline size_t buffer_avail(struct buffer *b) { + + return b->size ? b->size - (b->len + 1) : 0; +} + +void buffer_expand(struct buffer *b, size_t len); + +static inline void buffer_setlen(struct buffer *b, size_t len) { + + if (!b->size) + return; + + if (len >= b->size) + len = b->size - 1; + b->len = len; +} + +static inline void buffer_reduce(struct buffer *b, size_t len) { + + if (len > b->len) + len = b->len; + + buffer_setlen(b, b->len - len); +} + +char* buffer_cstr(struct buffer *b); + +void buffer_free(struct buffer *b); + +void buffer_attach(struct buffer *b, void *str, size_t len, size_t size); + +void buffer_append(struct buffer *b, const void *ptr, size_t len); + +static inline void buffer_append_str(struct buffer *b, const char *str) { + + buffer_append(b, str, strlen(str)); +} + +static inline void buffer_append_ch(struct buffer *b, char ch) { + + buffer_expand(b, 1); + b->block[b->len++] = ch; +} + +static inline void buffer_append_repeat(struct buffer *b, char ch, size_t len) { + + buffer_expand(b, len); + memset(b->block + b->len, ch, len); + buffer_setlen(b, b->len + len); +} + +static inline void buffer_str_term(struct buffer *b, char ch) { + + if (b->block[b->len - 1] != ch) + buffer_append_ch(b, ch); +} + +#endif /* BUFFER_H */ diff --git a/strbuf.c b/strbuf.c deleted file mode 100644 index 3ac96d9..0000000 --- a/strbuf.c +++ /dev/null @@ -1,90 +0,0 @@ -/* strbuf.c - * - * Copyright (C) 2010-2011 Henrik Hautakoski - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, - * MA 02110-1301, USA. - */ - -#include -#include -#include "error.h" -#include "strbuf.h" - -#define CHNK_SIZE 128 - -char strbuf_null = '\0'; - -void strbuf_init(strbuf_t *s) { - - s->buf = &strbuf_null; - s->size = s->len = 0; -} - -void strbuf_expand(strbuf_t *s, size_t len) { - - if (s->len + len + 1 < s->size) - return; - if (!s->size) - s->buf = NULL; - - do - s->size += CHNK_SIZE; - while(s->len + len + 1 > s->size); - - s->buf = realloc(s->buf, s->size); -} - -char* strbuf_release(strbuf_t *s) { - - char *ret; - - if (!s->size) - ret = malloc(1); - else if (s->len + 1 != s->size) - ret = realloc(s->buf, s->len + 1); - else - ret = s->buf; - - strbuf_init(s); - - return ret; -} - -void strbuf_free(strbuf_t *s) { - - if (!s->size) - return; - - free(s->buf); - strbuf_init(s); -} - -void strbuf_attach(strbuf_t *s, void *buf, size_t len, size_t size) { - - strbuf_free(s); - s->buf = buf; - s->len = len; - s->size = size; - strbuf_expand(s, 0); - s->buf[s->len] = '\0'; -} - -void strbuf_append(strbuf_t *s, const void *ptr, size_t len) { - - strbuf_expand(s, len); - memcpy(s->buf + s->len, ptr, len); - strbuf_setlen(s, s->len + len); -} diff --git a/strbuf.h b/strbuf.h deleted file mode 100644 index 17f9a8c..0000000 --- a/strbuf.h +++ /dev/null @@ -1,98 +0,0 @@ -/* strbuf.h - * - * Copyright (C) 2010-2011 Henrik Hautakoski - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, - * MA 02110-1301, USA. - */ - -#ifndef __STRBUF_H -#define __STRBUF_H - -#include -#include - -typedef struct { - char *buf; - size_t len; - size_t size; -} strbuf_t; - -extern char strbuf_null; - -#define STRBUF_INIT { &strbuf_null, 0, 0 } - -void strbuf_init(strbuf_t *s); - -static inline size_t strbuf_avail(strbuf_t *s) { - - return s->size ? s->size - (s->len + 1) : 0; -} - -void strbuf_expand(strbuf_t *s, size_t len); - -static inline void strbuf_setlen(strbuf_t *s, size_t len) { - - if (!s->size) - return; - - if (len >= s->size) - len = s->size - 1; - s->len = len; - s->buf[s->len] = '\0'; -} - -static inline void strbuf_reduce(strbuf_t *s, size_t len) { - - if (len > s->len) - len = s->len; - - strbuf_setlen(s, s->len - len); -} - -char* strbuf_release(strbuf_t *s); - -void strbuf_free(strbuf_t *s); - -void strbuf_attach(strbuf_t *s, void *str, size_t len, size_t size); - -void strbuf_append(strbuf_t *s, const void *ptr, size_t len); - -static inline void strbuf_append_str(strbuf_t *s, const char *str) { - - strbuf_append(s, str, strlen(str)); -} - -static inline void strbuf_append_ch(strbuf_t *s, char ch) { - - strbuf_expand(s, 1); - s->buf[s->len++] = ch; - s->buf[s->len] = '\0'; -} - -static inline void strbuf_append_repeat(strbuf_t *s, char ch, size_t len) { - - strbuf_expand(s, len); - memset(s->buf + s->len, ch, len); - strbuf_setlen(s, s->len + len); -} - -static inline void strbuf_term(strbuf_t *s, char ch) { - - if (s->buf[s->len-1] != ch) - strbuf_append_ch(s, ch); -} - -#endif /* __STRBUF_H */