1#ifndef COROUTINE_EMSCRIPTEN_CONTEXT_H
2#define COROUTINE_EMSCRIPTEN_CONTEXT_H 1
12#include <emscripten/fiber.h>
14#define COROUTINE __attribute__((noreturn)) void
16#if INTPTR_MAX <= INT32_MAX
17#define COROUTINE_LIMITED_ADDRESS_SPACE
26 emscripten_fiber_t state;
27 coroutine_start entry_func;
32COROUTINE coroutine_trampoline(
void * _context);
34#define MAIN_ASYNCIFY_STACK_SIZE 65536
36 static char asyncify_stack[MAIN_ASYNCIFY_STACK_SIZE];
37 emscripten_fiber_init_from_current_context(&context->state, asyncify_stack, MAIN_ASYNCIFY_STACK_SIZE);
39#undef MAIN_ASYNCIFY_STACK_SIZE
41static inline void coroutine_initialize(
43 coroutine_start start,
47 assert(start && stack && size >= 1024);
49 uintptr_t addr = (uintptr_t)stack;
50 size_t offset = addr & 0xF;
51 void *c_stack = (
void*)((addr + 0xF) & ~0xF);
53 size_t c_stack_size = (size / 2) & ~0xF;
54 void *asyncify_stack = (
void*)((uintptr_t)c_stack + c_stack_size);
55 size_t asyncify_stack_size = size - c_stack_size;
56 context->entry_func = start;
58 emscripten_fiber_init(&context->state, coroutine_trampoline, context, c_stack, c_stack_size, asyncify_stack, asyncify_stack_size);
65 target->from = current;
66 emscripten_fiber_swap(¤t->state, &target->state);
67 target->from = previous;