]> git.proxmox.com Git - qemu.git/commit - trace-events
coroutine: introduce coroutines
authorKevin Wolf <kwolf@redhat.com>
Mon, 17 Jan 2011 16:08:14 +0000 (16:08 +0000)
committerKevin Wolf <kwolf@redhat.com>
Mon, 1 Aug 2011 10:14:09 +0000 (12:14 +0200)
commit00dccaf1f848290d979a4b1e6248281ce1b32aaa
treeacc1d17a272a1a3494125d96ff22bb638566f076
parentf6e8ffc22fe153ba981f2747e4c52ea7e55f6ecc
coroutine: introduce coroutines

Asynchronous code is becoming very complex.  At the same time
synchronous code is growing because it is convenient to write.
Sometimes duplicate code paths are even added, one synchronous and the
other asynchronous.  This patch introduces coroutines which allow code
that looks synchronous but is asynchronous under the covers.

A coroutine has its own stack and is therefore able to preserve state
across blocking operations, which traditionally require callback
functions and manual marshalling of parameters.

Creating and starting a coroutine is easy:

  coroutine = qemu_coroutine_create(my_coroutine);
  qemu_coroutine_enter(coroutine, my_data);

The coroutine then executes until it returns or yields:

  void coroutine_fn my_coroutine(void *opaque) {
      MyData *my_data = opaque;

      /* do some work */

      qemu_coroutine_yield();

      /* do some more work */
  }

Yielding switches control back to the caller of qemu_coroutine_enter().
This is typically used to switch back to the main thread's event loop
after issuing an asynchronous I/O request.  The request callback will
then invoke qemu_coroutine_enter() once more to switch back to the
coroutine.

Note that if coroutines are used only from threads which hold the global
mutex they will never execute concurrently.  This makes programming with
coroutines easier than with threads.  Race conditions cannot occur since
only one coroutine may be active at any time.  Other coroutines can only
run across yield.

This coroutines implementation is based on the gtk-vnc implementation
written by Anthony Liguori <anthony@codemonkey.ws> but it has been
significantly rewritten by Kevin Wolf <kwolf@redhat.com> to use
setjmp()/longjmp() instead of the more expensive swapcontext() and by
Paolo Bonzini <pbonzini@redhat.com> for Windows Fibers support.

Signed-off-by: Kevin Wolf <kwolf@redhat.com>
Signed-off-by: Stefan Hajnoczi <stefanha@linux.vnet.ibm.com>
Makefile.objs
coroutine-ucontext.c [new file with mode: 0644]
coroutine-win32.c [new file with mode: 0644]
qemu-coroutine-int.h [new file with mode: 0644]
qemu-coroutine.c [new file with mode: 0644]
qemu-coroutine.h [new file with mode: 0644]
trace-events