commit cf42ef6c23c178222c23fb9e520e7c3a7f6cf310
parent c9bf1cb3f656d62dbef085becaadef7a7fa7723b
Author: sin <sin@2f30.org>
Date:   Wed, 24 Jul 2013 18:22:09 +0300
Add toy memory allocator
Diffstat:
| A | alloc.c |  |  | 115 | +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ | 
1 file changed, 115 insertions(+), 0 deletions(-)
diff --git a/alloc.c b/alloc.c
@@ -0,0 +1,115 @@
+#include <unistd.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+enum chunk_state {
+	FREE = 0,
+	ALLOCATED,
+};
+
+/* A maximum of `NALLOC' allocations possible */
+enum {
+	NALLOC = 65536 * 64,
+};
+
+/* Only needed because we have to implement
+ * realloc() */
+struct chunk {
+	void *base;
+	size_t size;
+	enum chunk_state state;
+} chunks[NALLOC];
+
+void *
+malloc(size_t nbytes)
+{
+	void *p;
+	long i;
+
+	if (!nbytes)
+		return NULL;
+	p = sbrk(nbytes);
+	if (p == (void *)-1)
+		return NULL;
+	for (i = 0; i < NALLOC; i++) {
+		if (chunks[i].state == FREE) {
+			chunks[i].base = p;
+			chunks[i].size = nbytes;
+			chunks[i].state = ALLOCATED;
+			return p;
+		}
+	}
+	return NULL;
+}
+
+void *
+realloc(void *oldp, size_t nbytes)
+{
+	void *p;
+	size_t n;
+	long i;
+
+	if (!nbytes) {
+		free(oldp);
+		return NULL;
+	}
+	p = malloc(nbytes);
+	if (!p)
+		return NULL;
+	for (i = 0; i < NALLOC; i++) {
+		if (chunks[i].base == oldp) {
+			n = chunks[i].size < nbytes ? chunks[i].size : nbytes;
+			memcpy(p, chunks[i].base, n);
+			free(oldp);
+			return p;
+		}
+	}
+	return NULL;
+}
+
+void *
+calloc(size_t nmemb, size_t size)
+{
+	void *p;
+
+	p = malloc(nmemb * size);
+	if (!p)
+		return NULL;
+	memset(p, 0, size * nmemb);
+	return p;
+}
+
+void
+free(void *p)
+{
+	long i;
+
+	if (!p)
+		return;
+	for (i = 0; i < NALLOC; i++) {
+		if (chunks[i].base == p) {
+			chunks[i].state = FREE;
+			break;
+		}
+	}
+}
+
+void
+cfree(void *p)
+{
+	free(p);
+}
+
+size_t
+malloc_usable_size(void *p)
+{
+	long i;
+
+	if (!p)
+		return 0;
+	for (i = 0; i < NALLOC; i++)
+		if (chunks[i].base == p)
+			return chunks[i].size;
+	return 0;
+}