1 //===- RWMutex.h - Reader/Writer Mutual Exclusion Lock ----------*- C++ -*-===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
10 // This file declares the llvm::sys::RWMutex class.
12 //===----------------------------------------------------------------------===//
14 #ifndef LLVM_SUPPORT_RWMUTEX_H
15 #define LLVM_SUPPORT_RWMUTEX_H
17 #include "llvm/Config/llvm-config.h"
18 #include "llvm/Support/Threading.h"
24 /// @brief Platform agnostic RWMutex class.
27 /// @name Constructors
31 /// Initializes the lock but doesn't acquire it.
32 /// @brief Default Constructor.
33 explicit RWMutexImpl();
36 /// @name Do Not Implement
38 RWMutexImpl(const RWMutexImpl & original) = delete;
39 RWMutexImpl &operator=(const RWMutexImpl &) = delete;
42 /// Releases and removes the lock
51 /// Attempts to unconditionally acquire the lock in reader mode. If the
52 /// lock is held by a writer, this method will wait until it can acquire
54 /// @returns false if any kind of error occurs, true otherwise.
55 /// @brief Unconditionally acquire the lock in reader mode.
56 bool reader_acquire();
58 /// Attempts to release the lock in reader mode.
59 /// @returns false if any kind of error occurs, true otherwise.
60 /// @brief Unconditionally release the lock in reader mode.
61 bool reader_release();
63 /// Attempts to unconditionally acquire the lock in reader mode. If the
64 /// lock is held by any readers, this method will wait until it can
66 /// @returns false if any kind of error occurs, true otherwise.
67 /// @brief Unconditionally acquire the lock in writer mode.
68 bool writer_acquire();
70 /// Attempts to release the lock in writer mode.
71 /// @returns false if any kind of error occurs, true otherwise.
72 /// @brief Unconditionally release the lock in write mode.
73 bool writer_release();
76 /// @name Platform Dependent Data
79 #if defined(LLVM_ENABLE_THREADS) && LLVM_ENABLE_THREADS != 0
80 void* data_ = nullptr; ///< We don't know what the data will be
84 /// SmartMutex - An R/W mutex with a compile time constant parameter that
85 /// indicates whether this mutex should become a no-op when we're not
86 /// running in multithreaded mode.
87 template<bool mt_only>
94 explicit SmartRWMutex() = default;
95 SmartRWMutex(const SmartRWMutex<mt_only> & original) = delete;
96 SmartRWMutex<mt_only> &operator=(const SmartRWMutex<mt_only> &) = delete;
99 if (!mt_only || llvm_is_multithreaded())
100 return impl.reader_acquire();
102 // Single-threaded debugging code. This would be racy in multithreaded
103 // mode, but provides not sanity checks in single threaded mode.
108 bool unlock_shared() {
109 if (!mt_only || llvm_is_multithreaded())
110 return impl.reader_release();
112 // Single-threaded debugging code. This would be racy in multithreaded
113 // mode, but provides not sanity checks in single threaded mode.
114 assert(readers > 0 && "Reader lock not acquired before release!");
120 if (!mt_only || llvm_is_multithreaded())
121 return impl.writer_acquire();
123 // Single-threaded debugging code. This would be racy in multithreaded
124 // mode, but provides not sanity checks in single threaded mode.
125 assert(writers == 0 && "Writer lock already acquired!");
131 if (!mt_only || llvm_is_multithreaded())
132 return impl.writer_release();
134 // Single-threaded debugging code. This would be racy in multithreaded
135 // mode, but provides not sanity checks in single threaded mode.
136 assert(writers == 1 && "Writer lock not acquired before release!");
142 typedef SmartRWMutex<false> RWMutex;
144 /// ScopedReader - RAII acquisition of a reader lock
145 template<bool mt_only>
146 struct SmartScopedReader {
147 SmartRWMutex<mt_only>& mutex;
149 explicit SmartScopedReader(SmartRWMutex<mt_only>& m) : mutex(m) {
153 ~SmartScopedReader() {
154 mutex.unlock_shared();
158 typedef SmartScopedReader<false> ScopedReader;
160 /// ScopedWriter - RAII acquisition of a writer lock
161 template<bool mt_only>
162 struct SmartScopedWriter {
163 SmartRWMutex<mt_only>& mutex;
165 explicit SmartScopedWriter(SmartRWMutex<mt_only>& m) : mutex(m) {
169 ~SmartScopedWriter() {
174 typedef SmartScopedWriter<false> ScopedWriter;
176 } // end namespace sys
177 } // end namespace llvm
179 #endif // LLVM_SUPPORT_RWMUTEX_H