A newer version of this document is available. Customers should click here to go to the newest version.
Intel® oneAPI Threading Building Blocks (oneTBB) Simple Mutex - Example
The following examples shows basic usage of a Intel® oneAPI Threading Building Blocks (oneTBB) mutex to protect a shared variable named count using simple mutexes and scoped locks:
Simple Mutex Example
#include <tbb/mutex.h>
int count;
tbb::mutex countMutex;
int IncrementCount() {
int result;
// Add oneTBB mutex
countMutex.lock(); // Implements ANNOTATE_LOCK_ACQUIRE()
result = count++; // Save result until after unlock
countMutex.unlock(); // Implements ANNOTATE_LOCK_RELEASE()
return result;
}
The semantics of countMutex.lock() and unlock() on countMutex correspond directly to the annotations ANNOTATE_LOCK_ACQUIRE() and ANNOTATE_LOCK_RELEASE(). However, it is generally better to use the scoped locking pattern.
Scoped Lock Example
With a scoped lock, you construct a temporary scoped_lock object that represents acquisition of a lock. Destruction of the scoped_lock object releases the lock on the mutex.
The following code shows the previous example rewritten using scoped locking:
#include <tbb/mutex.h>
int count;
tbb::mutex countMutex;
int IncrementCount() {
int result;
{
// Add oneTBB scoped lock at location of ANNOTATE_LOCK annotations
tbb::mutex::scoped_lock lock(countMutex); // Implements ANNOTATE_LOCK_ACQUIRE()
result = count++;
// Implicit ANNOTATE_LOCK_RELEASE() when leaving the scope below.
} // scoped lock is automatically released here
return result;
}
The scoped_lock pattern is preferred because it releases the lock no matter how control leaves the block. The scoped lock is released when destruction of the scoped_lock object occurs. In particular, it releases the lock even when control leaves because an exception was thrown.
oneTBB also has a tbb::atomic template class that can be used in simple cases such as managing a shared integer variable. Check the Related Information for details.