[IO] make the lock implementation protecting a IoContext's cq configurable 
This change introduces a new synchronization primitive "PseudoCountingTryLock" which takes an actual lock as template and provides a CountingTryLock interface. By using a PseudoCountingTryLock we don't have to change any synchronization code in IoContext::reapCompletion.
Since all PseudoCountingTryLock code is defined in a header the compiler should see our constant return values and hopefully optimize away any check depending on those constant return values.
Options:
- spin_lock - naive CAS spin lock
- mutex - std::mutex
- counting_try_lock (default) - our own lightweight special purpose synchronization primitive
Closes !123 (closed).