diff --git a/block_to_imp.c b/block_to_imp.c index 87eebca..c5c31a0 100644 --- a/block_to_imp.c +++ b/block_to_imp.c @@ -9,6 +9,7 @@ #include #include #include +#include #include #include "objc/runtime.h" #include "objc/blocks_runtime.h" @@ -28,17 +29,10 @@ static void *executeBuffer; static void *writeBuffer; static ptrdiff_t offset; static mutex_t trampoline_lock; +#ifndef SHM_ANON static char *tmpPattern; - -struct wx_buffer +static void initTmpFile(void) { - void *w; - void *x; -}; - -PRIVATE void init_trampolines(void) -{ - INIT_LOCK(trampoline_lock); char *tmp = getenv("TMPDIR"); if (NULL == tmp) { @@ -49,14 +43,40 @@ PRIVATE void init_trampolines(void) abort(); } } +static int getAnonMemFd(void) +{ + const char *pattern = strdup(tmpPattern); + int fd = mkstemp(pattern); + unlink(pattern); + free(pattern); + return fd; +} +#else +static void initTmpFile(void) {} +static int getAnonMemFd(void) +{ + return shm_open(SHM_ANON, O_CREAT | O_RDWR, 0); +} +#endif + +struct wx_buffer +{ + void *w; + void *x; +}; + +PRIVATE void init_trampolines(void) +{ + INIT_LOCK(trampoline_lock); + initTmpFile(); +} static struct wx_buffer alloc_buffer(size_t size) { LOCK_FOR_SCOPE(&trampoline_lock); if ((0 == offset) || (offset + size >= PAGE_SIZE)) { - int fd = mkstemp(tmpPattern); - unlink(tmpPattern); + int fd = getAnonMemFd(); ftruncate(fd, PAGE_SIZE); void *w = mmap(NULL, PAGE_SIZE, PROT_WRITE, MAP_SHARED, fd, 0); executeBuffer = mmap(NULL, PAGE_SIZE, PROT_READ|PROT_EXEC, MAP_SHARED, fd, 0);