#include #include #include static char stack[2][65536]; // a stack for each coroutine static ucontext_t coroutine_state[2]; // container to remember context // switch current coroutine (0 -> 1 -> 0 -> 1 ...) static inline void yield_to_next(void) { static int current = 0; int prev = current; int next = 1 - current; current = next; swapcontext(&coroutine_state[prev], &coroutine_state[next]); } static void coroutine(int coroutine_number) { int i; for (i = 0; i < 5; i++) { printf("Coroutine %d counts i=%d (&i=%p)\n", coroutine_number, i, &i); yield_to_next(); } } int main() { ucontext_t return_to_main; // set up int i; for (i = 0; i < 2; i++) { // initialize ucontext_t getcontext(&coroutine_state[i]); // set up per-context stack coroutine_state[i].uc_stack.ss_sp = stack[i]; coroutine_state[i].uc_stack.ss_size = sizeof(stack[i]); // when done, resume 'return_to_main' context coroutine_state[i].uc_link = &return_to_main; // let context[i] perform a call to coroutine(i) when swapped to makecontext(&coroutine_state[i], (void (*)(void))coroutine, 1, i); } printf("Starting coroutines...\n"); swapcontext(&return_to_main, coroutine_state); printf("Done.\n"); return 0; }