2 libco.ucontext (2008-01-28)
8 * WARNING: the overhead of POSIX ucontext is very high,
9 * assembly versions of libco or libco_sjlj should be much faster
11 * This library only exists for two reasons:
12 * 1 - as an initial test for the viability of a ucontext implementation
13 * 2 - to demonstrate the power and speed of libco over existing implementations,
14 * such as pth (which defaults to wrapping ucontext on unix targets)
16 * Use this library only as a *last resort*
28 static thread_local ucontext_t co_primary;
29 static thread_local ucontext_t *co_running = 0;
31 cothread_t co_active(void)
34 co_running = &co_primary;
35 return (cothread_t)co_running;
38 cothread_t co_create(unsigned int heapsize, void (*coentry)(void))
42 co_running = &co_primary;
44 if ((thread = (ucontext_t*)malloc(sizeof(ucontext_t))))
46 if ((!getcontext(thread) && !(thread->uc_stack.ss_sp = 0)) && (thread->uc_stack.ss_sp = malloc(heapsize)))
48 thread->uc_link = co_running;
49 thread->uc_stack.ss_size = heapsize;
50 makecontext(thread, coentry, 0);
54 co_delete((cothread_t)thread);
58 return (cothread_t)thread;
61 void co_delete(cothread_t cothread)
66 if (((ucontext_t*)cothread)->uc_stack.ss_sp)
67 free(((ucontext_t*)cothread)->uc_stack.ss_sp);
71 void co_switch(cothread_t cothread)
73 ucontext_t *old_thread = co_running;
74 co_running = (ucontext_t*)cothread;
75 swapcontext(old_thread, co_running);