summaryrefslogtreecommitdiff
path: root/subversion/include/private/svn_mutex.h
diff options
context:
space:
mode:
Diffstat (limited to 'subversion/include/private/svn_mutex.h')
-rw-r--r--subversion/include/private/svn_mutex.h117
1 files changed, 117 insertions, 0 deletions
diff --git a/subversion/include/private/svn_mutex.h b/subversion/include/private/svn_mutex.h
new file mode 100644
index 0000000..c647697
--- /dev/null
+++ b/subversion/include/private/svn_mutex.h
@@ -0,0 +1,117 @@
+/**
+ * @copyright
+ * ====================================================================
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ * ====================================================================
+ * @endcopyright
+ *
+ * @file svn_mutex.h
+ * @brief Structures and functions for mutual exclusion
+ */
+
+#ifndef SVN_MUTEX_H
+#define SVN_MUTEX_H
+
+#include <apr_thread_mutex.h>
+
+#include "svn_error.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif /* __cplusplus */
+
+/**
+ * This is a simple wrapper around @c apr_thread_mutex_t and will be a
+ * valid identifier even if APR does not support threading.
+ */
+#if APR_HAS_THREADS
+
+/** A mutex for synchronization between threads. It may be NULL, in
+ * which case no synchronization will take place. The latter is useful
+ * when implementing some functionality with optional synchronization.
+ */
+typedef apr_thread_mutex_t svn_mutex__t;
+
+#else
+
+/** Dummy definition. The content will never be actually accessed.
+ */
+typedef void svn_mutex__t;
+
+#endif
+
+/** Initialize the @a *mutex. If @a mutex_required is TRUE, the mutex will
+ * actually be created with a lifetime defined by @a result_pool. Otherwise,
+ * the pointer will be set to @c NULL and svn_mutex__lock() as well as
+ * svn_mutex__unlock() will be no-ops.
+ *
+ * If threading is not supported by APR, this function is a no-op.
+ */
+svn_error_t *
+svn_mutex__init(svn_mutex__t **mutex,
+ svn_boolean_t mutex_required,
+ apr_pool_t *result_pool);
+
+/** Acquire the @a mutex, if that has been enabled in svn_mutex__init().
+ * Make sure to call svn_mutex__unlock() some time later in the same
+ * thread to release the mutex again. Recursive locking are not supported.
+ *
+ * @note You should use #SVN_MUTEX__WITH_LOCK instead of explicit lock
+ * acquisition and release.
+ */
+svn_error_t *
+svn_mutex__lock(svn_mutex__t *mutex);
+
+/** Release the @a mutex, previously acquired using svn_mutex__lock()
+ * that has been enabled in svn_mutex__init().
+ *
+ * Since this is often used as part of the calling function's exit
+ * sequence, we accept that function's current return code in @a err.
+ * If it is not #SVN_NO_ERROR, it will be used as the return value -
+ * irrespective of the possible internal failures during unlock. If @a err
+ * is #SVN_NO_ERROR, internal failures of this function will be
+ * reported in the return value.
+ *
+ * @note You should use #SVN_MUTEX__WITH_LOCK instead of explicit lock
+ * acquisition and release.
+ */
+svn_error_t *
+svn_mutex__unlock(svn_mutex__t *mutex,
+ svn_error_t *err);
+
+/** Acquires the @a mutex, executes the expression @a expr and finally
+ * releases the @a mutex. If any of these steps fail, the function using
+ * this macro will return an #svn_error_t. This macro guarantees that
+ * the @a mutex will always be unlocked again if it got locked successfully
+ * by the first step.
+ *
+ * @note Prefer using this macro instead of explicit lock acquisition and
+ * release.
+ */
+#define SVN_MUTEX__WITH_LOCK(mutex, expr) \
+do { \
+ svn_mutex__t *svn_mutex__m = (mutex); \
+ SVN_ERR(svn_mutex__lock(svn_mutex__m)); \
+ SVN_ERR(svn_mutex__unlock(svn_mutex__m, (expr))); \
+} while (0)
+
+#ifdef __cplusplus
+}
+#endif /* __cplusplus */
+
+#endif /* SVN_MUTEX_H */