|
> Windows has the CreateFiber() API that creates "fibers", which act like threads, but use "cooperative multitasking". For POSIX, using a combination of setjmp(), longjmp(), sigaltstack(), and some signal (e.g. SIGUSR2) will provide coroutine support though it is "pretty awful". While it is "horrible", it does actually work. I do this, and it works perfectly well. Here's a full implementation demonstrating this approach: https://gitlab.com/higan/higan/blob/master/libco/sjlj.c It's been successfully used on x86, amd64, ppc32, ppc64, mips, arm and sparc in several projects. However, it still has a good bit of overhead. But you can implement this concept absolutely trivially on any platform for maximum speed. All you need to do is save the non-volatile registers, swap the stack pointer, restore the non-volatile registers from the swapped-in stack, and return from the function. If you haven't realized, one function can reciprocally save and restore these contexts. Here's an x86 implementation, for example: co_swap: ;ecx = new thread, edx = old thread
mov [edx],esp
mov esp,[ecx]
pop eax ;faster than ret (CPU begins caching new opcodes here)
mov [edx+4],ebp ;much faster than push/pop on AMD CPUs
mov [edx+8],esi
mov [edx+12],edi
mov [edx+16],ebx
mov ebp,[ecx+4]
mov esi,[ecx+8]
mov edi,[ecx+12]
mov ebx,[ecx+16]
jmp eax
This turns out to be several times faster than abusing setjmp/longjmp.I turned this into the simplest possible library called libco (public domain or ISC, whichever you prefer.) The entire API is four functions, taking 0-2 arguments each: create, delete, active, switch. The work's already been done for several processors. Plus there's backends for the setjmp trick, Windows Fibers and even the slow-as-snails makecontext. If Python does decide to go this route, I'd certainly appreciate if the devs could be directed at libco for consideration. It'd save them a lot of trouble making these, and it'd get us some much-needed notoriety so that we could produce more backends and finally have a definitive cothreading library. |
https://github.com/python-greenlet/greenlet/tree/master/plat...