The big problem with setjmp/longjmp for fibers is that a call to longjmp is undefined behavior if the `jmp_buf` argument was created by a call to `setjmp` on a different thread (1). That means fibers cannot be easily relocated onto a different thread, making M:N threading tricky to implement and erasing a lot of the benefit of fibers.
And that said, implementing a super-fast setcontext/swapcontext is like twenty lines of assembly with not too many gotchas, if you don't care about saving a few things that require syscalls.
But all that said the real downside of stack switching is that it's overkill for coroutines that can be implemented as a finite state machine, unless the runtime supports growable stacks (otherwise you pay a big cost on fiber creation, and eat a lot of memory for many fibers). There are a few languages that do this and it's super cool, but C isn't one of them.
WASM will almost certainly support stack switching, iirc there have been proposals for wasmtime to support it already?
> And that said, implementing a super-fast setcontext/swapcontext is like twenty lines of assembly with not too many gotchas, if you don't care about saving a few things that require syscalls.
sigaltstack(2) wasn't all that prohibitive when I did that in Python 2.6 back then. Was it 2009?
I seriously can't understand this obsession with FSMs. A naive setcontext()-based implementation outperfomed both greenlets (with its crazy legacy of memcpy-ing parts of stack from stackless) and Tornado/Twisted (with them being pure-python and therefore lacking any means to force some async on client libraries. which one does in C) while letting everyone write some nice clean synchronous-looking code.
10 years later we end up with half a language hacked up and still nowhere near the ease of use that was coded in a week or so.
> I seriously can't understand this obsession with FSM
It's the most optimal representation of the common-case (non-recursive asynchronous tasks), has the same overhead as a function call, plays very well with branch prediction, can be easily inlined by optimizers, and it's a lot easier to implement.
And that said, implementing a super-fast setcontext/swapcontext is like twenty lines of assembly with not too many gotchas, if you don't care about saving a few things that require syscalls.
But all that said the real downside of stack switching is that it's overkill for coroutines that can be implemented as a finite state machine, unless the runtime supports growable stacks (otherwise you pay a big cost on fiber creation, and eat a lot of memory for many fibers). There are a few languages that do this and it's super cool, but C isn't one of them.
WASM will almost certainly support stack switching, iirc there have been proposals for wasmtime to support it already?
(1) https://pubs.opengroup.org/onlinepubs/9699919799/functions/l...