add emulation of futex() for non-Linux systems
Summary: Inside the Linux kernel, futex() works by hashing the source address to a fixed set of wakeup lists. When using folly on non-Linux systems we can emulate something similar by using std::mutex and std::condition_variable. Emulating futex() using higher-level APIs is less crazy than it sounds, because the emulated futex still provides the advantages of the real one: it allows all of the fast-paths of a new synchronization construct to be inlined; it is space efficient, taking only 1 word and allowing the caller to encode state into all of the word's bits; and it avoids system calls unless a thread actually needs to be put to sleep or woken up. Think of this as a way of boostrapping something with the same properties as futex() on platforms that don't expose it publically. (Presumably these platforms have private APIs that do something similar.) This diff moves all of the Linux-specific futex stuff into Futex.cpp, where it is gated by #ifdef __linux__. It also adds an emulated implementation. The emulated futex will be selected by default on non-Linux platforms, or it can be used on Linux by using an Atom template type of folly::detail::EmulatedFutexAtomic. This means, for example, that you can test MPMCQueue on top of the emulated API by instantiating a MPMCQueue<ElemType, EmulatedFutexAtomic>. As a bonus, this refactoring provides a small speed boost by removing an unnecessary evaluation of the errno macro in the success path of futexWait. Test Plan: 1. existing unit tests 2. new unit tests (including tests of Futex users) 3. compile Futex.cpp on OS X (some other build failures still occur) Reviewed By: delong.j@fb.com Subscribers: trunkagent, njormrod, yiding, boseant, mssarang FB internal diff: D1596118 Tasks: 4952724
Showing
Please register or sign in to comment