The vulnerability as described in ISO/IEC 24772-1 clause 6.63 is applicable to C++.
This subclause requires a complete rewrite to have it reflect C++ issues.
Difference between threads and tasks. Can threads and tasks coexist?
Deadlock with single mutex,
The C standard does not provide hidden protocols. Although the vulnerability does not apply to the C language, there could exist an application vulnerability if a program uses synchronization mechanisms incorrectly. For example:
atomic int a;
int b;
/* . . . */
a += b; // This operation is an atomic read-modify-write of the variable ‘a’.
a = a + b; // This statement contains two accesses to ‘a’ and is not atomic.
To avoid the vulnerability or mitigate its ill effects, C++ software developers can:
Use the avoidance mechanisms of ISO/IEC 24772-1 clause 6.63.5.
Be aware of the operation of each synchronization mechanism, such as the cases where accesses to atomic variables may occur more than once in a statement.
Use higher level building blocks (such as TBB) in preference to …
Use the C++ Task mechanism in preference to threads …
Always put the acquisition and release of mutexes and the data access in a wrapper function. (i.e. Do not call member functions of std::mutex, std::timed_mutex, std::recursive_mutex, std::recursive_timed_mutex, std::shared_mutex and std::shared_timed_mutex objects directly.)
Use std::lock(), std::try_lock() or std::scoped_lock to acquire multiple mutexes in same scope. (std::lock() permits multiple mutexes at the same time).
Use std::lock() only where multiple locks must be locked together and use std::lock_guard with the std::adopt_lock argument for all mutexes (needs example) see std::lock() example on cppreference.com.
Wrap mutex locks std::lock or std::try_lock with std::lock_guard, std::unique_lock or std::shared_lock with adopt_lock tag within the same scope
If explicit locking are used, ensure that the lock is released on every exit path, including exceptions. Use lock_guard, scope_lock and unique_lock in preference to lock(), unlock(), and try_lock(),
Do not use platform specific multi-threading facilities
A thread shall not access objects whose lifetime has expired
0.5.2 [24] Wrap functions that can spuriously wake up in a loop 20
0.5.4 [26] Do not use std::condition_variable_any on a std::mutex
[0.10.1 [35] Source CCG Rule CP.100: Don't use lock-free programming unless you absolutely have to
27](https://docs.google.com/document/d/14E0BYqsH_d7fMKvXvaZWoNWtIC65cYBw0aZp4dlev0Q/edit#heading=h.3hq5f8vdw7d)
0.10.2 [36] Source CCG Rule CP.101: Distrust your hardware/compiler combination
0.10.3 [37] Source CCG Rule CP.102: Carefully study the literature
0.10.4 [38] Source CCG Rule CP.110: Do not write your own double-checked locking for initialization