rcx

library of miscellaneous bits of C code
git clone git://git.rr3.xyz/rcx
Log | Files | Refs | README | LICENSE

commit b9c673ffb02568211832f0767291afe0822114b8
parent 2df5ebc15b0eadaacbd274b46a282b7005d1a014
Author: Robert Russell <robertrussell.72001@gmail.com>
Date:   Fri,  9 Sep 2022 11:03:56 -0700

Add null terminator option to vector

This will be needed for a future string/char vector type.

Diffstat:
Minc/rcx/vector.h | 23++++++++++++++---------
1 file changed, 14 insertions(+), 9 deletions(-)

diff --git a/inc/rcx/vector.h b/inc/rcx/vector.h @@ -1,6 +1,7 @@ #pragma once #include <errno.h> +#include <stdbool.h> #include <string.h> #include "rcx/alloc.h" @@ -19,6 +20,7 @@ typedef struct { /* Defaults */ #define R_VECTOR_STATIC #define R_VECTOR_METHOD(name, prefix) JOIN(JOIN(prefix,_),name) +#define R_VECTOR_NULL_TERM false #define R_VECTOR_MIN_CAP 8 #define R_VECTOR_HDR_TYPE r_vector_generic_hdr_ #define R_VECTOR_REALLOC r_erealloc @@ -67,19 +69,22 @@ int R_VECTOR_METHOD(resize,##__VA_ARGS__)(T **v, usize cap) { \ } \ if (R_VECTOR_REALLOC(&h, sizeof *h + arrsize) < 0) \ return -1; \ - h->len = MIN(len, cap); \ + h->len = MIN(len, cap - !!R_VECTOR_NULL_TERM); \ h->cap = cap; \ *v = (void *)(h + 1); \ + if (R_VECTOR_NULL_TERM) \ + memset(&(*v)[h->len], 0, sizeof (*v)[0]); \ } \ return 0; \ } \ int R_VECTOR_METHOD(reserve,##__VA_ARGS__)(T **v, usize n) { \ R_VECTOR_HDR_TYPE *h = *v ? R_VECTOR_HDR_(*v) : 0; \ - usize rem = h ? h->cap - h->len : 0; \ + usize rem = h ? h->cap - h->len - !!R_VECTOR_NULL_TERM : 0; \ if (n > rem) { \ usize need = n - rem; \ - usize cap = h ? h->cap + MAX(h->cap, need) : need; \ - if (h && cap < h->cap) { /* Overflow? */ \ + usize cap = h ? h->cap + MAX(h->cap, need) \ + : need + !!R_VECTOR_NULL_TERM; \ + if ((h && cap < h->cap) || (R_VECTOR_NULL_TERM && cap == 0)) { \ errno = ENOMEM; \ return -1; \ } \ @@ -98,8 +103,8 @@ int R_VECTOR_METHOD(insv,##__VA_ARGS__)(T **dst, usize i, T *src) { \ int R_VECTOR_METHOD(insn,##__VA_ARGS__)(T **dst, usize i, T *src, usize n) { \ if (R_VECTOR_METHOD(reserve,##__VA_ARGS__)(dst, n)) \ return -1; \ - memmove(&(*dst)[i+n], &(*dst)[i], \ - (R_VECTOR_HDR_(*dst)->len - i) * sizeof (*dst)[0]); \ + usize m = R_VECTOR_HDR_(*dst)->len - i + !!R_VECTOR_NULL_TERM; \ + memmove(&(*dst)[i+n], &(*dst)[i], m * sizeof (*dst)[0]); \ memcpy(&(*dst)[i], src, n * sizeof (*dst)[0]); \ R_VECTOR_HDR_(*dst)->len += n; \ return 0; \ @@ -117,9 +122,9 @@ int R_VECTOR_METHOD(catn,##__VA_ARGS__)(T **dst, T *src, usize n) { \ } \ T R_VECTOR_METHOD(del,##__VA_ARGS__)(T **v, usize i) { \ T e = (*v)[i]; \ - memmove(&(*v)[i], &(*v)[i+1], \ - (R_VECTOR_HDR_(*v)->len - i - 1) * sizeof (*v)[0]); \ - R_VECTOR_HDR_(*v)->len--; \ + usize m = R_VECTOR_HDR_(*v)->len - i - 1 + !!R_VECTOR_NULL_TERM; \ + memmove(&(*v)[i], &(*v)[i+1], m * sizeof (*v)[0]); \ + R_VECTOR_HDR_(*v)->len -= 1; \ return e; \ } \ T R_VECTOR_METHOD(pop,##__VA_ARGS__)(T **v) { \