lemoncake

rbtree based memory allocator
git clone git://git.2f30.org/lemoncake.git
Log | Files | Refs | README | LICENSE

commit aeb9cb9c7b7f9cf626c4f6d2dded3f6866f35b15
parent c9ae01670f67170b07b823dcd1dc74ad78ef4600
Author: sin <sin@2f30.org>
Date:   Fri Aug  2 15:40:36 +0100

Add LEMONCAKE_DEBUG option

Diffstat:
lemoncake.c | 78++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++----------------
1 file changed, 62 insertions(+), 16 deletions(-)
diff --git a/lemoncake.c b/lemoncake.c @@ -1,16 +1,25 @@ /* See LICENSE file for copyright and license details. */ #include <sys/mman.h> +#include <sys/stat.h> +#include <fcntl.h> #include <unistd.h> #include <stdio.h> #include <stdlib.h> #include <string.h> #include <stdint.h> +#include <stdbool.h> #include <errno.h> #include "tree.h" #include "spinlock.h" enum { ALIGN = 4 * sizeof(size_t) }; +struct lemoncake_ctx { + bool init; +}; + +static struct lemoncake_ctx ctx; + struct node { void *buf; size_t siz; @@ -51,24 +60,29 @@ at_cmp(struct node *a, struct node *b) return 0; } -__attribute__ ((unused)) static void -dump_alloc_tree(void) -{ - struct node *n; - - RB_FOREACH(n, alloc_tree, &at) - fprintf(stderr, "%s: buf: %p, size: %zu\n", - __func__, n->buf, n->siz); -} - -__attribute__ ((unused)) static void -dump_free_tree(void) +static void +dump_trees(void) { struct node *n; - - RB_FOREACH(n, free_tree, &ft) - fprintf(stderr, "%s: buf: %p, size: %zu\n", - __func__, n->buf, n->siz); + char buf[BUFSIZ]; + int fd; + + fd = open("lemoncake.out", O_WRONLY | O_CREAT, 0644); + if (fd != -1) { + RB_FOREACH(n, alloc_tree, &at) { + snprintf(buf, sizeof(buf), + "alloc: buf: %p, size: %zu\n", + n->buf, n->siz); + write(fd, buf, strlen(buf)); + } + RB_FOREACH(n, free_tree, &ft) { + snprintf(buf, sizeof(buf), + "free: buf: %p, size: %zu\n", + n->buf, n->siz); + write(fd, buf, strlen(buf)); + } + close(fd); + } } static inline void * @@ -100,12 +114,34 @@ mmap_aligned(size_t align, size_t siz) return p; } +static void +lemoncake_dump(void) +{ + dump_trees(); +} + +static int +lemoncake_init(void) +{ + char *p; + + if (ctx.init) + return 0; + p = getenv("LEMONCAKE_DEBUG"); + if (p) + atexit(lemoncake_dump); + ctx.init = true; + return 0; +} + void * malloc(size_t siz) { struct node n, *an, *res; void *p; + if (lemoncake_init()) + return NULL; if (!siz) return NULL; lock(&rblock); @@ -145,6 +181,8 @@ realloc(void *oldp, size_t siz) struct node *oldan, *newan; struct node *fn; + if (lemoncake_init()) + return NULL; if (!oldp) return malloc(siz); if (!siz) { @@ -210,6 +248,8 @@ calloc(size_t nmemb, size_t siz) { void *p; + if (lemoncake_init()) + return NULL; p = malloc(nmemb * siz); if (!p) return NULL; @@ -222,6 +262,8 @@ free(void *p) { struct node n, *fn, *res; + if (lemoncake_init()) + return; if (!p) return; lock(&rblock); @@ -246,6 +288,8 @@ memalign(size_t align, size_t siz) struct node *an; void *p; + if (lemoncake_init()) + return NULL; if (((align - 1) & align)) return NULL; if (align < sizeof(void *)) @@ -315,6 +359,8 @@ malloc_usable_size(void *p) { struct node n, *res; + if (lemoncake_init()) + return 0; if (!p) return 0; lock(&rblock);