You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@kudu.apache.org by ad...@apache.org on 2016/07/14 18:03:25 UTC
[2/2] incubator-kudu git commit: rw_mutex: add configurable priority
rw_mutex: add configurable priority
The glibc implementation of pthread rwlocks exposes priorities that can help
if avoiding reader or writer starvation is desirable. I have a use case for
the latter, so let's expose the priorities in our wrapper.
Note: pthread rwlock priorities don't exist on macOS, which is why they're a
"best effort".
Change-Id: I16ba6cd041f126c94e63fa07a1e84c88db6778d7
Reviewed-on: http://gerrit.cloudera.org:8080/3603
Tested-by: Kudu Jenkins
Reviewed-by: Todd Lipcon <to...@apache.org>
Reviewed-by: Dan Burkert <da...@cloudera.com>
Project: http://git-wip-us.apache.org/repos/asf/incubator-kudu/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-kudu/commit/71a5bb50
Tree: http://git-wip-us.apache.org/repos/asf/incubator-kudu/tree/71a5bb50
Diff: http://git-wip-us.apache.org/repos/asf/incubator-kudu/diff/71a5bb50
Branch: refs/heads/master
Commit: 71a5bb5070f144f8df356f5e28dd4e063de3df5e
Parents: 8c68d35
Author: Adar Dembo <ad...@cloudera.com>
Authored: Fri Jul 8 18:51:56 2016 -0700
Committer: Adar Dembo <ad...@cloudera.com>
Committed: Thu Jul 14 18:02:27 2016 +0000
----------------------------------------------------------------------
src/kudu/util/rw_mutex.cc | 32 ++++++++++++++++++++++++++++++++
src/kudu/util/rw_mutex.h | 22 ++++++++++++++++++++++
2 files changed, 54 insertions(+)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/incubator-kudu/blob/71a5bb50/src/kudu/util/rw_mutex.cc
----------------------------------------------------------------------
diff --git a/src/kudu/util/rw_mutex.cc b/src/kudu/util/rw_mutex.cc
index b47d04f..d9473bb 100644
--- a/src/kudu/util/rw_mutex.cc
+++ b/src/kudu/util/rw_mutex.cc
@@ -31,8 +31,40 @@ void unlock_rwlock(pthread_rwlock_t* rwlock) {
namespace kudu {
RWMutex::RWMutex() {
+ Init(Priority::PREFER_READING);
+}
+
+RWMutex::RWMutex(Priority prio) {
+ Init(prio);
+}
+
+void RWMutex::Init(Priority prio) {
+#ifdef __linux__
+ // Adapt from priority to the pthread type.
+ int kind = PTHREAD_RWLOCK_PREFER_READER_NP;
+ switch (prio) {
+ case Priority::PREFER_READING:
+ kind = PTHREAD_RWLOCK_PREFER_READER_NP;
+ break;
+ case Priority::PREFER_WRITING:
+ kind = PTHREAD_RWLOCK_PREFER_WRITER_NONRECURSIVE_NP;
+ break;
+ }
+
+ // Initialize the new rwlock with the user's preference.
+ pthread_rwlockattr_t attr;
+ int rv = pthread_rwlockattr_init(&attr);
+ DCHECK_EQ(0, rv) << strerror(rv);
+ rv = pthread_rwlockattr_setkind_np(&attr, kind);
+ DCHECK_EQ(0, rv) << strerror(rv);
+ rv = pthread_rwlock_init(&native_handle_, &attr);
+ DCHECK_EQ(0, rv) << strerror(rv);
+ rv = pthread_rwlockattr_destroy(&attr);
+ DCHECK_EQ(0, rv) << strerror(rv);
+#else
int rv = pthread_rwlock_init(&native_handle_, NULL);
DCHECK_EQ(0, rv) << strerror(rv);
+#endif
}
RWMutex::~RWMutex() {
http://git-wip-us.apache.org/repos/asf/incubator-kudu/blob/71a5bb50/src/kudu/util/rw_mutex.h
----------------------------------------------------------------------
diff --git a/src/kudu/util/rw_mutex.h b/src/kudu/util/rw_mutex.h
index 0153556..64a88d1 100644
--- a/src/kudu/util/rw_mutex.h
+++ b/src/kudu/util/rw_mutex.h
@@ -28,7 +28,27 @@ namespace kudu {
// Implemented as a thin wrapper around pthread_rwlock_t.
class RWMutex {
public:
+
+ // Possible fairness policies for the RWMutex.
+ enum class Priority {
+ // The lock will prioritize readers at the expense of writers.
+ PREFER_READING,
+
+ // The lock will prioritize writers at the expense of readers.
+ //
+ // Care should be taken when using this fairness policy, as it can lead to
+ // unexpected deadlocks (e.g. a writer waiting on the lock will prevent
+ // additional readers from acquiring it).
+ PREFER_WRITING,
+ };
+
+ // Create an RWMutex that prioritizes readers.
RWMutex();
+
+ // Create an RWMutex with customized priority. This is a best effort; the
+ // underlying platform may not support custom priorities.
+ explicit RWMutex(Priority prio);
+
~RWMutex();
void ReadLock();
@@ -48,6 +68,8 @@ class RWMutex {
bool try_lock_shared() { return TryReadLock(); }
private:
+ void Init(Priority prio);
+
pthread_rwlock_t native_handle_;
DISALLOW_COPY_AND_ASSIGN(RWMutex);