commit c9c3598eaf41d8c95ccf5eae8fe26c37ca88747d
parent dfeb089a5def8b30d5c8b8a485d7c473032d7c2c
Author: sin <sin@2f30.org>
Date: Tue, 30 Jul 2013 12:20:41 +0100
Fix posix_memalign()
Use PAGESIZE instead of 0x1000.
Diffstat:
M | alloc.c | | | 47 | ++++++++++++++++++++++++++--------------------- |
1 file changed, 26 insertions(+), 21 deletions(-)
diff --git a/alloc.c b/alloc.c
@@ -15,6 +15,10 @@ enum {
NALLOC = 65536 * 128,
};
+enum {
+ PAGESIZE = 0x1000,
+};
+
/* Only needed because we have to implement
* realloc() */
struct chunk {
@@ -23,26 +27,26 @@ struct chunk {
enum chunk_state state;
} chunks[NALLOC];
-/* Align on a 0x1000 boundary */
+/* Align on a PAGESIZE boundary */
void *
mmap_page_aligned(size_t nbytes)
{
void *addr;
int ret;
- if (nbytes % 0x1000)
- nbytes = (nbytes + 0x1000) & ~(0x1000 - 1);
+ if (nbytes % PAGESIZE)
+ nbytes = (nbytes + PAGESIZE) & ~(PAGESIZE - 1);
- addr = mmap(0, nbytes + 0x1000,
+ addr = mmap(0, nbytes + PAGESIZE,
PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANON,
-1, 0);
if (addr == MAP_FAILED)
return NULL;
/* Guard page at the end of the allocation */
- ret = mprotect((char *)addr + nbytes, 0x1000,
+ ret = mprotect((char *)addr + nbytes, PAGESIZE,
PROT_NONE);
if (ret < 0) {
- munmap(addr, nbytes + 0x1000);
+ munmap(addr, nbytes + PAGESIZE);
return NULL;
}
return addr;
@@ -89,7 +93,7 @@ realloc(void *oldp, size_t nbytes)
n = chunks[i].size < nbytes ? chunks[i].size : nbytes;
memcpy(p, chunks[i].base, n);
chunks[i].state = FREE;
- munmap(chunks[i].base, chunks[i].size + 0x1000);
+ munmap(chunks[i].base, chunks[i].size + PAGESIZE);
return p;
}
}
@@ -118,7 +122,7 @@ free(void *p)
for (i = 0; i < NALLOC; i++) {
if (chunks[i].base == p) {
chunks[i].state = FREE;
- munmap(chunks[i].base, chunks[i].size + 0x1000);
+ munmap(chunks[i].base, chunks[i].size + PAGESIZE);
break;
}
}
@@ -150,24 +154,25 @@ malloc_size(void *p)
}
int
-posix_memalign(void **memptr, size_t alignment, size_t size)
+posix_memalign(void **memptr, size_t align, size_t size)
{
- void *result;
+ void *mem;
- /* Make sure that alignment is a large enough power of 2. */
- if (((alignment - 1) & alignment) != 0 || alignment < sizeof(void *))
+ if (((align - 1) & align))
return EINVAL;
+ if (align < sizeof(void *))
+ return EINVAL;
+
+ if (PAGESIZE % align) {
+ fprintf(stderr, "%s: %zu alignment not supported!\n",
+ __func__, align);
+ abort();
+ }
- /*
- * max(size, alignment) is enough to assure the requested alignment,
- * since the allocator always allocates power-of-two blocks.
- */
- if (size < alignment)
- size = alignment;
- result = malloc(size);
- if (!result)
+ mem = malloc(size);
+ if (!mem)
return ENOMEM;
- *memptr = result;
+ *memptr = mem;
return 0;
}