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;
 }