# C Programming/Coroutines

A little known fact is that most C implementations have built-in
primitives that can be used for cooperative multitasking / coroutines.
They are setcontext and
setjmp.

## setjmp

The function `setjmp` is used in a pair with `longjmp` to transfer
execution to a different point in the code. It relies on an existing
`jmp_buf` declaration.

``` c
#include <setjmp.h>

int main (void)
{
  jmp_buf buf1;
  
  if (setjmp(buf1) == 0)
  {
    /* This code is executed on the first call to setjmp. */

    longjmp(buf1, 1);
  } else {
    /* This code is executed once longjmp is called. */
  }
  return 0; 
}
```

`setjmp()` stores the current execution point in memory, which remains
valid as long as the containing function doesn\'t return. It initially
returns `0`. Control is returned to `setjmp` once `longjmp` is called
with the original `jmp_buf` and the replacement return value.

Note that jmp_buf is passed to setjmp without using the address-of
operator.

The easiest way to understand setjmp and longjmp, is that setjmp stores
the state of the cpu which includes program counter, stack pointer, all
the registers, including the bits of the flags register, at the location
pointed to by jmp_buf , which is defined some LEN+1, which is enough
bytes to store the registers of whatever CPU is involved. The
longjmp(buf) , never returns, because it restores the CPU from the
contents of struct jmp_buf buf previously set by a previous call the
setjmp, so execution begins from after setjmp was called, but the return
value of setjmp is not 0, but whatever value was used in the second
parameter to longjmp. This is similar to the fork() system call, which
returns 0 to the child process, and the PID of the child process to the
parent.

The internet suggests co-routines are useful for implementing software
as state machines cooperating, such as lexer processing input text and
emitting tokens , so that a parser can decide to store the token and ask
for the next one, or to act on its current set of token . This is not
multithreaded programs synchronising on data, with possibly race
conditions if a bug forgets to acquire a lock, but with setjmp and
longjmp, seems to be cooperative processes that guarantee only one
process will run at a time, with no worries about context switches
waking up sleeping processes ( using separate jmp_buf static locations,
each process can call setjmp for its own jmp_buf, before calling longjmp
later on if zero was returned, or continue a loop to process shared data
for non-zero returns).

