Openwall GNU/*/Linux - a small security-enhanced Linux distro for servers
[<prev] [next>] [thread-next>] [day] [month] [year] [list]
Date: Tue, 28 Nov 2017 11:50:08 +0000
From: Nicholas Wilson <nicholas.wilson@...lvnc.com>
To: "musl@...ts.openwall.com" <musl@...ts.openwall.com>
Subject: [PATCH] Wasm support patch 1 (support systems without mmap)

I'm hoping the first patch is uncontroversial.

WebAssembly has a linear/flat memory model, whereby it's simply impossible for the addressable memory to contain "holes". Therefore, mmap can't really be emulated, and all memory has to be allocated via brk.

I've done this by allowing malloc to fall back to brk (even for allocations above MMAP_THRESHOLD) if mmap returns ENOSYS.

It's one line of code that will do harm in "normal" systems, and allows platforms that are emulating syscalls to choose not to support mmap, and still get a working malloc if brk is working.

All the best,
Nick


diff --git a/src/malloc/malloc.c b/src/malloc/malloc.c
index 9e05e1d6..572232e1 100644
--- a/src/malloc/malloc.c
+++ b/src/malloc/malloc.c
@@ -328,13 +328,17 @@ void *malloc(size_t n)
                size_t len = n + OVERHEAD + PAGE_SIZE - 1 & -PAGE_SIZE;
                char *base = __mmap(0, len, PROT_READ|PROT_WRITE,
                        MAP_PRIVATE|MAP_ANONYMOUS, -1, 0);
-               if (base == (void *)-1) return 0;
+               if (base == MAP_FAILED) {
+                       if (errno == ENOSYS) goto nommap;
+                       return 0;
+               }
                c = (void *)(base + SIZE_ALIGN - OVERHEAD);
                c->csize = len - (SIZE_ALIGN - OVERHEAD);
                c->psize = SIZE_ALIGN - OVERHEAD;
                return CHUNK_TO_MEM(c);
        }
 
+nommap:
        i = bin_index_up(n);
        for (;;) {
                uint64_t mask = mal.binmap & -(1ULL<<i);
@@ -405,7 +409,7 @@ void *realloc(void *p, size_t n)
                newlen = (newlen + PAGE_SIZE-1) & -PAGE_SIZE;
                if (oldlen == newlen) return p;
                base = __mremap(base, oldlen, newlen, MREMAP_MAYMOVE);
-               if (base == (void *)-1)
+               if (base == MAP_FAILED)
                        goto copy_realloc;
                self = (void *)(base + extra);
                self->csize = newlen - extra;

Powered by blists - more mailing lists

Your e-mail address:

Powered by Openwall GNU/*/Linux - Powered by OpenVZ