X

News, tips, partners, and perspectives for the Oracle Solaris operating system

Better performing pthread reader-writer locks for NUMA architectures

Guest Author
Introduction
-------------
Solaris 11.3 introduces an intelligent version of process private reader-writer locks
(rwlocks) that is aware of the underlying NUMA architecture. This awareness can be
used to extract better performance from the reader-writer locks. This is accomplished
by using a technique called lock cohorting. This blog post describes how to use the
new rwlocks.
Interface Changes
------------------
To ensure compatibility and ease of adaptation, the only change to the current
pthread_rwlock interfaces (see pthread_rwlock_*(3C) and pthread_rwlockattr_*(3C) interfaces)
made is the introduction of a new attribute, PTHREAD_RWSCALE_PRIVATE_NP. Once the property
of the attribute object is set to PTHREAD_RWSCALE_PRIVATE_NP, rest of the application
remains unchanged.


pthread_rwlockattr_t

lock_attr;

pthread_rwlockattr_setpshared(&lattr, PTHREAD_RWSCALE_PRIVATE_NP);
The above code will set the lock_attr object to be of NUMA aware type. When an rwlock is
created using lock_attr, it will provide better performance when compared to the
traditional process private rwlocks.
Use Case
---------
These locks are best used in the following scenario.
Consider a multi-threaded process where the threads share a process-private rwlock.
If such a process is running in a NUMA machine and the threads of the process are
*not* confined to a single NUMA node, then considerable performance improvement
can be seen when using the new rwlocks. If the threads of such a process are confined
to a single NUMA node, then it performs as a process running on a UMA machine would.
No performance degradation will be seen.
Example
--------
Here is a simple example to demonstrate the creation of an rwlock of
PTHREAD_RWSCALE_PRIVATE_NP type.
#include <pthread.h>
int
main()
{

/* Declare a variable of type pthread_rwlockattr_t */

pthread_rwlockattr_t rwlattr;

pthread_rwlock_t rwlock;

int rc;

/*

* Initialize the attribute object and call pthread_rwlockattr_setpshared

* to set it to the appropriate value. Default value of pthread_rwlock-

* attr_init is PTHREAD_PROCESS_PRIVATE

*/

rc = pthread_rwlockattr_setpshared(&rwlattr, PTHREAD_RWSCALE_SHARED_NP);

/*

* Call pthread_rwlock_init with the initialized rwlockattr object to

* initialize the rwlock to the desired type

*/

rc = pthread_rwlock_init(&rwlock, &rwlattr);

/*

* Use the lock and destroy it by using pthread_rwlock_destroy.

* It is important to destroy the lock to ensure that the memory

* allocated by the lock internally is freed.

*/

rc = pthread_rwlock_destroy(&rwlock);
}

Be the first to comment

Comments ( 0 )
Please enter your name.Please provide a valid email address.Please enter a comment.CAPTCHA challenge response provided was incorrect. Please try again.