Skip to content


Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
A User Space Threading Library Supporting Multi-Core Systems
C Shell Perl C++ Other
branch: master

A User Space Threading Library Supporting Multi-Core Systems

  • Lightweight user threads with support for blocking IO and fast context switching (ie. similar to Erlang or Go but using C)
  • Fast, scalable load balancing across multiple cores
  • Lock-free data structures
  • Supports x86 and x86_64. Further architectures can be added easily.
  • Supports native event backends on Linux and Solaris
  • Supports libev event backend


  • Why Events Are A Bad Idea (for high-concurrency servers) - Rob von Behren, Jeremy Condit, and Eric Brewer
    • Specifically, the following quote summarizes nicely: "...the duality argument of Lauer and Needham ... implies that good implementations of thread systems and event systems will have similar performance."


  • Type 'make' to build the library and run the unit tests
  • Link your application to
  • Be sure to define the architecture when including libfiber's headers. You can specify the following gcc flags:
    • For x86 64 bit: -m64 -DARCH_x86_64
    • For x86 32 bit: -m32 -march=i686 -DARCH_x86
  • overrides many system calls so make sure you know what you're doing
  • The makefile will attempt to detect gcc split stack support (Go uses this). This requires gcc 4.7 or higher. I recommend using this.
    • make CC=gcc-4.7


  • See example/echo_server.c for an example.
  • The basic idea is that you write blocking code and libfiber makes it event driven for you.

Spawn a fiber running 'client_function' per client:

while((sock = accept(server_socket, NULL, NULL)) >= 0) {
    fiber_t* client_fiber = fiber_create(10240, &client_function, (void*)(intptr_t)sock);

'client_function' does a blocking read() and write() on the socket:

void* client_function(void* param)
    while((num_read = read(sock, buffer, sizeof(buffer))) > 0) {
        if(num_read != write(sock, buffer, num_read)) {


  • Call fiber_manager_init() at the beginning of your program
    • Specify the number of kernel threads (ie. CPUs) to use
    • This will initialize the event system and shim blocking IO calls
  • Familiar threading concepts are available in include/
    • Mutexes
    • Semaphores
    • Read/Write Mutexes
    • Barriers
    • Spin Locks
    • Condition Variables
  • Lock free data structures available in include/
    • Single-Producer/Single-Consumer FIFO
    • Multi-Producer/Single-Consumer FIFO (two implementations with different properties)
    • Multi-Producer/Multi-Consumer LIFO
    • Multi-Producer/Multi-Consumer FIFO (using hazard pointers)
    • Fixed-Size Ring Buffer
    • Work Stealing


  • Anecdotally:

    • libfiber's mutex objects significantly outperform pthread's mutex objects under contention. This is because a contended mutex requires context switches.
    • libfiber's channels signifcantly outperform Go's channels. Both libfiber's and Go's channels use a mutex internally - libfiber's fast mutex gives an advantage.
      • See go/test_channel.go, go/test_channel2.go, test/test_bounded_mpmc_channel.c, and test/test_bounded_mpmc_channel2.c
  • TODO: automated benchmarks with real numbers


  • Thorough unit tests
  • Over 90% test coverage ('make coveragereport', then see bin/lcov/index.html)
    • Only extreme failure cases missing, such as NOMEM
  • Tested on x86 Linux, x86_64 Linux, x86 Solaris 10
  • Separate tests for lock free data structure and hazard pointers


  • Detect architecture automatically using known defines


Something went wrong with that request. Please try again.