--- a/src/buffer.c Sun Apr 13 13:02:54 2025 +0200 +++ b/src/buffer.c Sun Apr 13 14:30:51 2025 +0200 @@ -29,6 +29,7 @@ #include "cx/buffer.h" #include <stdio.h> +#include <unistd.h> #include <string.h> #include <errno.h> @@ -190,6 +191,28 @@ return 0; } + unsigned long pagesize = sysconf(_SC_PAGESIZE); + // if page size is larger than 64 KB - for some reason - truncate to 64 KB + if (pagesize > 65536) pagesize = 65536; + if (newcap < pagesize) { + // when smaller as one page, map to the next power of two + newcap--; + newcap |= newcap >> 1; + newcap |= newcap >> 2; + newcap |= newcap >> 4; + // last operation only needed for pages larger 4096 bytes + // but if/else would be more expensive than just doing this + newcap |= newcap >> 8; + newcap++; + } else { + // otherwise, map to a multiple of the page size + newcap -= newcap % pagesize; + newcap += pagesize; + // note: if newcap is already page aligned, + // this gives a full additional page (which is good) + } + + const int force_copy_flags = CX_BUFFER_COPY_ON_WRITE | CX_BUFFER_COPY_ON_EXTEND; if (buffer->flags & force_copy_flags) { void *newspace = cxMalloc(buffer->allocator, newcap);