Latches and Barriers

This lesson gives an overview of latches and barriers, predicted to be introduced in C++20.

Latches and barriers are simple thread synchronization mechanisms which enable some threads to wait until a counter becomes zero. At first, don’t confuse the new barriers with memory barriers (also known as fences). In C++20, we will presumably get latches and barriers in three variations: std::latch, std::barrier, and std::flex_barrier.

First, there are two questions:

  1. What are the differences between these three mechanisms to synchronize threads? You can use an std::latch only once, but you can use an std::barrier and an std::flex_barrier more than once. Additionally, an std::flex_barrier enables you to execute a function when the counter becomes zero.
  2. What use cases do latches and barriers support that cannot be done in C++11 and C++14 with futures, threads, or condition variables in combination with locks? Latches and barriers address no new use cases, but they are a lot easier to use; they are also more performant because they often use a lock-free mechanism internally.

Now, I will have a closer look at these three coordination mechanisms.

std::latch

std::latch is a countdown counter; its value is set in the constructor. A thread can decrement the counter by using the method thread.count_down_and_wait and wait until the counter becomes zero. In addition, the method thread.count_down only decrements the counter by 1 without waiting. std::latch also has the method thread.is_ready that can be used to test if the counter is zero, and the method thread.wait to wait until the counter becomes zero. You cannot increment or reset the counter of a std::latch, hence you cannot reuse it.

Here is a short code snippet from the N4204 proposal:

Get hands-on with 1200+ tech skills courses.