]> git.ipfire.org Git - thirdparty/pdns.git/blobdiff - pdns/lock.hh
dnsdist: Wrap pthread_ objects
[thirdparty/pdns.git] / pdns / lock.hh
index 895d346e06b46fe1a19019640c24884519acbf36..d3933059f5e2a5b5d5e3bf7b04b34c85ab8f5367 100644 (file)
@@ -19,9 +19,7 @@
  * along with this program; if not, write to the Free Software
  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
  */
-#ifndef LOCK_HH
-#define LOCK_HH
-
+#pragma once
 #include <pthread.h>
 #include <errno.h>
 #include "misc.hh"
@@ -56,6 +54,33 @@ public:
   }
 };
 
+class ReadWriteLock
+{
+public:
+  ReadWriteLock()
+  {
+    if (pthread_rwlock_init(&d_lock, nullptr) != 0) {
+      throw std::runtime_error("Error creating a read-write lock: " + stringerror());
+    }
+  }
+
+  ~ReadWriteLock() {
+    /* might have been moved */
+    pthread_rwlock_destroy(&d_lock);
+  }
+
+  ReadWriteLock(const ReadWriteLock& rhs) = delete;
+  ReadWriteLock& operator=(const ReadWriteLock& rhs) = delete;
+
+  pthread_rwlock_t* getLock()
+  {
+    return &d_lock;
+  }
+
+private:
+  pthread_rwlock_t d_lock;
+};
+
 class WriteLock
 {
   pthread_rwlock_t *d_lock;
@@ -79,6 +104,14 @@ public:
       pthread_rwlock_unlock(d_lock);
   }
 
+  WriteLock(ReadWriteLock& lock): WriteLock(lock.getLock())
+  {
+  }
+
+  WriteLock(ReadWriteLock* lock): WriteLock(lock->getLock())
+  {
+  }
+
   WriteLock(WriteLock&& rhs)
   {
     d_lock = rhs.d_lock;
@@ -87,7 +120,6 @@ public:
   WriteLock(const WriteLock& rhs) = delete;
   WriteLock& operator=(const WriteLock& rhs) = delete;
 
-
 };
 
 class TryWriteLock
@@ -121,7 +153,14 @@ public:
     rhs.d_havelock = false;
   }
 
-  
+  TryWriteLock(ReadWriteLock& lock): TryWriteLock(lock.getLock())
+  {
+  }
+
+  TryWriteLock(ReadWriteLock* lock): TryWriteLock(lock->getLock())
+  {
+  }
+
   ~TryWriteLock()
   {
     if(g_singleThreaded)
@@ -160,6 +199,15 @@ public:
     }
     d_havelock=(err==0);
   }
+
+  TryReadLock(ReadWriteLock& lock): TryReadLock(lock.getLock())
+  {
+  }
+
+  TryReadLock(ReadWriteLock* lock): TryReadLock(lock->getLock())
+  {
+  }
+
   TryReadLock(TryReadLock&& rhs)
   {
     d_lock = rhs.d_lock;
@@ -201,6 +249,15 @@ public:
       throw PDNSException("error acquiring rwlock readlock: "+stringerror(err));
     }
   }
+
+  ReadLock(ReadWriteLock& lock): ReadLock(lock.getLock())
+  {
+  }
+
+  ReadLock(ReadWriteLock* lock): ReadLock(lock->getLock())
+  {
+  }
+
   ~ReadLock()
   {
     if(g_singleThreaded)
@@ -212,9 +269,8 @@ public:
   ReadLock(ReadLock&& rhs)
   {
     d_lock = rhs.d_lock;
-    rhs.d_lock=0;
+    rhs.d_lock = nullptr;
   }
   ReadLock(const ReadLock& rhs) = delete;
   ReadLock& operator=(const ReadLock& rhs) = delete;
 };
-#endif