The primary template std::atomic<T> extends atomic operations to eligible user-defined types. Its interface follows std::atomic<bool>, with value-related parameters and results using T. Atomic specializations for built-in types may not be lock-free, and the available operations depend on the type. section 5.2.6 section 5.2.1
For a user-defined type, the requirements and comparison behavior matter:
- The type must have a trivial copy-assignment operator; its base classes and non-static data members must also meet that requirement. section 5.2.6
- Compare-exchange compares object representations as if with memcmp, not with a user-defined comparison operator. Padding bits or differing comparison semantics can therefore cause failure even when values compare equal. section 5.2.6
Table 5.3. The operations available on atomic types (view table figure)
| Operation |
atomic_flag |
atomic<bool> |
atomic<T*> |
atomic<integral-type> |
atomic<other-type> |
|---|---|---|---|---|---|
| test_and_set | Y | ||||
| clear | Y | ||||
| is_lock_free | Y | Y | Y | Y | |
| load | Y | Y | Y | Y | |
| store | Y | Y | Y | Y | |
| exchange | Y | Y | Y | Y | |
| compare_exchange_weak, compare_exchange_strong | Y | Y | Y | Y | |
| fetch_add, += | Y | Y | |||
| fetch_sub, -= | Y | Y | |||
| fetch_or, |= | Y | ||||
| fetch_and, &= | Y | ||||
| fetch_xor, ^= | Y | ||||
| ++, -- | Y | Y |
The available operations vary by atomic type: the table compares loads, stores, exchanges, compare-exchange, and type-specific arithmetic or bitwise operations. section 5.2.6
Shared state in parallel work
A shared count modified by parallel algorithm invocations creates a data race if it is an ordinary int. Making it std::atomic<int> makes synchronized access defined, though synchronization may serialize calls. section 10.2.3
