Blob


1 #include "threadimpl.h"
3 void
4 makecontext(ucontext_t *uc, void (*fn)(void), int argc, ...)
5 {
6 uintptr *sp;
7 va_list arg;
9 //fprint(2, "makecontext %d\n", argc);
10 if(argc != 2)
11 sysfatal("libthread: makecontext misused");
12 va_start(arg, argc);
13 uc->mc.di = va_arg(arg, uint);
14 uc->mc.si = va_arg(arg, uint);
15 //fprint(2, "%ux %ux\n", uc->mc.di, uc->mc.si);
16 va_end(arg);
18 sp = (uintptr*)((char*)uc->uc_stack.ss_sp+uc->uc_stack.ss_size);
19 /*
20 * Stack pointer at call instruction (before return address
21 * gets pushed) must be 16-byte aligned.
22 */
23 if((uintptr)sp%4)
24 abort();
25 while((uintptr)sp%16 != 0)
26 sp--;
27 *--sp = 0; // fn's return address
28 *--sp = (uintptr)fn; // return address of setcontext
29 uc->mc.sp = (uintptr)sp;
30 }
32 int
33 swapcontext(ucontext_t *oucp, ucontext_t *ucp)
34 {
35 if(getcontext(oucp) == 0)
36 setcontext(ucp);
37 return 0;
38 }