From 670a4ae67b83af151c373e9dba7febc660ccf48e Mon Sep 17 00:00:00 2001 From: Alex Shinn Date: Thu, 25 Feb 2010 23:58:57 +0900 Subject: [PATCH] adding option to mmap heaps instead of mallocing them --- gc.c | 14 ++++++++++++-- include/chibi/features.h | 7 +++++++ sexp.c | 16 ++++++++++++---- 3 files changed, 31 insertions(+), 6 deletions(-) diff --git a/gc.c b/gc.c index 5e2a4d23..455b1a85 100644 --- a/gc.c +++ b/gc.c @@ -4,6 +4,10 @@ #include "chibi/sexp.h" +#if SEXP_USE_MMAP_GC +#include +#endif + /* These settings are configurable but only recommended for */ /* experienced users, so they're not in config.h. */ @@ -171,8 +175,14 @@ sexp sexp_gc (sexp ctx, size_t *sum_freed) { sexp_heap sexp_make_heap (size_t size) { sexp_free_list free, next; - sexp_heap h - = (sexp_heap) malloc(sizeof(struct sexp_heap) + size + sexp_heap_align(1)); + sexp_heap h; +#if SEXP_USE_MMAP_GC + h = mmap(NULL, sizeof(struct sexp_heap) + size + sexp_heap_align(1), + PROT_READ|PROT_WRITE|PROT_EXEC, + MAP_ANON|MAP_PRIVATE, 0, 0); +#else + h = malloc(sizeof(struct sexp_heap) + size + sexp_heap_align(1)); +#endif if (! h) return NULL; h->size = size; h->data = (char*) sexp_heap_align((sexp_uint_t)&(h->data)); diff --git a/include/chibi/features.h b/include/chibi/features.h index 1a6caed2..d93f5b5c 100644 --- a/include/chibi/features.h +++ b/include/chibi/features.h @@ -57,6 +57,9 @@ /* explicitly free sexps, though. */ /* #define SEXP_USE_MALLOC 1 */ +/* uncomment this to allocate heaps with mmap instead of malloc */ +/* #define SEXP_USE_MMAP_GC 1 */ + /* uncomment this to add conservative checks to the native GC */ /* Please mail the author if enabling this makes a bug */ /* go away and you're not working on your own C extension. */ @@ -205,6 +208,10 @@ #define SEXP_USE_MALLOC 0 #endif +#ifndef SEXP_USE_MMAP_GC +#define SEXP_USE_MMAP_GC 0 +#endif + #ifndef SEXP_USE_DEBUG_GC #define SEXP_USE_DEBUG_GC 0 #endif diff --git a/sexp.c b/sexp.c index d0c41eaf..dd32415d 100644 --- a/sexp.c +++ b/sexp.c @@ -290,13 +290,20 @@ sexp sexp_make_context (sexp ctx, sexp_uint_t size) { #if ! SEXP_USE_GLOBAL_HEAP void sexp_destroy_context (sexp ctx) { - sexp_heap heap; + sexp_heap heap, tmp; size_t sum_freed; if (sexp_context_heap(ctx)) { sexp_sweep(ctx, &sum_freed); /* sweep w/o mark to run finalizers */ heap = sexp_context_heap(ctx); sexp_context_heap(ctx) = NULL; - free(heap); + for ( ; heap; heap=tmp) { + tmp = heap->next; +#if SEXP_USE_MMAP_GC + munmap(heap, heap->size); +#else + free(heap); +#endif + } } } #endif @@ -702,11 +709,12 @@ sexp sexp_intern(sexp ctx, char *str) { #if SEXP_USE_HUFF_SYMS res = 0; for ( ; (c=*p); p++) { + if ((c < 0) || (c > 127)) + goto normal_intern; he = huff_table[(unsigned char)c]; newbits = he.len; - if ((space+newbits) > (sizeof(sexp)*8)) { + if ((space+newbits) > (sizeof(sexp)*8)) goto normal_intern; - } res |= (((sexp_uint_t) he.bits) << space); space += newbits; }