From e304d0f8ee404ef7e1223a324012d4fb4049185d Mon Sep 17 00:00:00 2001
From: Max Kellermann <max@duempel.org>
Date: Sat, 13 Sep 2014 11:26:17 +0200
Subject: [PATCH] thread/Posix{Cond,Mutex}: don't ues PTHREAD_*_INITIALIZER on
 NetBSD

On NetBSD, PTHREAD_MUTEX_INITIALIZER and PTHREAD_COND_INITIALIZER are
not compatible with C++11 "constexpr" (see Mantis ticket 0004110).  As
a workaround, don't ues "constexpr", and use the functions
pthread_mutex_init(), pthread_mutex_destroy(), pthread_cond_init() and
pthread_cond_destroy() instead.  This adds some runtime overhead, but
is portable to POSIX implementations that have awkward initializer
macros.
---
 NEWS                      |  1 +
 src/notify.hxx            |  2 +-
 src/thread/PosixCond.hxx  | 14 ++++++++++++++
 src/thread/PosixMutex.hxx | 14 ++++++++++++++
 4 files changed, 30 insertions(+), 1 deletion(-)

diff --git a/NEWS b/NEWS
index b15161b23..499b3ac0c 100644
--- a/NEWS
+++ b/NEWS
@@ -1,4 +1,5 @@
 ver 0.18.15 (not yet released)
+* work around build failure on NetBSD
 
 ver 0.18.14 (2014/09/11)
 * protocol
diff --git a/src/notify.hxx b/src/notify.hxx
index 6b9e95368..1024dd8d9 100644
--- a/src/notify.hxx
+++ b/src/notify.hxx
@@ -28,7 +28,7 @@ struct notify {
 	Cond cond;
 	bool pending;
 
-#ifndef WIN32
+#if !defined(WIN32) && !defined(__NetBSD__)
 	constexpr
 #endif
 	notify():pending(false) {}
diff --git a/src/thread/PosixCond.hxx b/src/thread/PosixCond.hxx
index 6f98d3ad0..c2797649a 100644
--- a/src/thread/PosixCond.hxx
+++ b/src/thread/PosixCond.hxx
@@ -41,7 +41,21 @@ class PosixCond {
 	pthread_cond_t cond;
 
 public:
+#ifdef __NetBSD__
+	/* NetBSD's PTHREAD_COND_INITIALIZER is not compatible with
+	   "constexpr" */
+	PosixCond() {
+		pthread_cond_init(&cond, nullptr);
+	}
+
+	~PosixCond() {
+		pthread_cond_destroy(&cond);
+	}
+#else
+	/* optimized constexpr constructor for sane POSIX
+	   implementations */
 	constexpr PosixCond():cond(PTHREAD_COND_INITIALIZER) {}
+#endif
 
 	PosixCond(const PosixCond &other) = delete;
 	PosixCond &operator=(const PosixCond &other) = delete;
diff --git a/src/thread/PosixMutex.hxx b/src/thread/PosixMutex.hxx
index d50764af4..445c0ace2 100644
--- a/src/thread/PosixMutex.hxx
+++ b/src/thread/PosixMutex.hxx
@@ -41,7 +41,21 @@ class PosixMutex {
 	pthread_mutex_t mutex;
 
 public:
+#ifdef __NetBSD__
+	/* NetBSD's PTHREAD_MUTEX_INITIALIZER is not compatible with
+	   "constexpr" */
+	PosixMutex() {
+		pthread_mutex_init(&mutex, nullptr);
+	}
+
+	~PosixMutex() {
+		pthread_mutex_destroy(&mutex);
+	}
+#else
+	/* optimized constexpr constructor for sane POSIX
+	   implementations */
 	constexpr PosixMutex():mutex(PTHREAD_MUTEX_INITIALIZER) {}
+#endif
 
 	PosixMutex(const PosixMutex &other) = delete;
 	PosixMutex &operator=(const PosixMutex &other) = delete;