// SPDX-License-Identifier: ISC #include #include #include #include #include #define DYNALLOC_MIN 64 bool dynalloc_reserve_add(struct dynalloc *s, size_t len) { size_t new_res; void *new_buf; if (len > SIZE_MAX - s->len) return errno = ERANGE, false; new_res = s->res; while (new_res < s->len + len) { if (new_res < DYNALLOC_MIN) new_res = DYNALLOC_MIN; else if (new_res <= SIZE_MAX / 2) new_res *= 2; else return errno = ERANGE, false; } new_buf = realloc(s->buf, new_res); if (!new_buf) return false; s->buf = new_buf; s->res = new_res; return true; } bool dynalloc_catb(struct dynalloc *s, const char *buf, size_t len) { if (!dynalloc_reserve_add(s, len)) return false; memcpy(s->buf + s->len, buf, len); s->len += len; return true; } bool dynalloc_cats(struct dynalloc *s, const char *buf) { return dynalloc_catb(s, buf, strlen(buf)); } bool dynalloc_cat0(struct dynalloc *s) { return dynalloc_catb(s, "", 1); } void dynalloc_free(struct dynalloc *s) { free(s->buf); s->len = 0; s->res = 0; }