29 Atomic operations library [atomics]

29.7 Flag type and operations [atomics.flag]

namespace std {
  typedef struct atomic_flag {
    bool test_and_set(memory_order = memory_order_seq_cst) volatile noexcept;
    bool test_and_set(memory_order = memory_order_seq_cst) noexcept;
    void clear(memory_order = memory_order_seq_cst) volatile noexcept;
    void clear(memory_order = memory_order_seq_cst) noexcept;

    atomic_flag() noexcept = default;
    atomic_flag(const atomic_flag&) = delete;
    atomic_flag& operator=(const atomic_flag&) = delete;
    atomic_flag& operator=(const atomic_flag&) volatile = delete;
  } atomic_flag;

  bool atomic_flag_test_and_set(volatile atomic_flag*) noexcept;
  bool atomic_flag_test_and_set(atomic_flag*) noexcept;
  bool atomic_flag_test_and_set_explicit(volatile atomic_flag*, memory_order) noexcept;
  bool atomic_flag_test_and_set_explicit(atomic_flag*, memory_order) noexcept;
  void atomic_flag_clear(volatile atomic_flag*) noexcept;
  void atomic_flag_clear(atomic_flag*) noexcept;
  void atomic_flag_clear_explicit(volatile atomic_flag*, memory_order) noexcept;
  void atomic_flag_clear_explicit(atomic_flag*, memory_order) noexcept;

  #define ATOMIC_FLAG_INIT see below
}

The atomic_flag type provides the classic test-and-set functionality. It has two states, set and clear.

Operations on an object of type atomic_flag shall be lock-free. [ Note: Hence the operations should also be address-free. No other type requires lock-free operations, so the atomic_flag type is the minimum hardware-implemented type needed to conform to this International standard. The remaining types can be emulated with atomic_flag, though with less than ideal properties.  — end note ]

The atomic_flag type shall have standard layout. It shall have a trivial default constructor, a deleted copy constructor, a deleted copy assignment operator, and a trivial destructor.

The macro ATOMIC_FLAG_INIT shall be defined in such a way that it can be used to initialize an object of type atomic_flag to the clear state. For a static-duration object, that initialization shall be static. It is unspecified whether an uninitialized atomic_flag object has an initial state of set or clear.[ Example:

atomic_flag guard = ATOMIC_FLAG_INIT;

 — end example ]

bool atomic_flag_test_and_set(volatile atomic_flag *object) noexcept; bool atomic_flag_test_and_set(atomic_flag *object) noexcept; bool atomic_flag_test_and_set_explicit(volatile atomic_flag *object, memory_order order) noexcept; bool atomic_flag_test_and_set_explicit(atomic_flag *object, memory_order order) noexcept; bool atomic_flag::test_and_set(memory_order order = memory_order_seq_cst) volatile noexcept; bool atomic_flag::test_and_set(memory_order order = memory_order_seq_cst) noexcept;

Effects: Atomically sets the value pointed to by object or by this to true. Memory is affected according to the value of order. These operations are atomic read-modify-write operations ([intro.multithread]).

Returns: Atomically, the value of the object immediately before the effects.

void atomic_flag_clear(volatile atomic_flag *object) noexcept; void atomic_flag_clear(atomic_flag *object) noexcept; void atomic_flag_clear_explicit(volatile atomic_flag *object, memory_order order) noexcept; void atomic_flag_clear_explicit(atomic_flag *object, memory_order order) noexcept; void atomic_flag::clear(memory_order order = memory_order_seq_cst) volatile noexcept; void atomic_flag::clear(memory_order order = memory_order_seq_cst) noexcept;

Requires: The order argument shall not be memory_order_acquire or memory_order_acq_rel.

Effects: Atomically sets the value pointed to by object or by this to false. Memory is affected according to the value of order.