Intel(R) Threading Building Blocks Doxygen Documentation  version 4.2.3
spin_rw_mutex.h
Go to the documentation of this file.
1 /*
2  Copyright (c) 2005-2019 Intel Corporation
3 
4  Licensed under the Apache License, Version 2.0 (the "License");
5  you may not use this file except in compliance with the License.
6  You may obtain a copy of the License at
7 
8  http://www.apache.org/licenses/LICENSE-2.0
9 
10  Unless required by applicable law or agreed to in writing, software
11  distributed under the License is distributed on an "AS IS" BASIS,
12  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  See the License for the specific language governing permissions and
14  limitations under the License.
15 
16 
17 
18 
19 */
20 
21 #ifndef __TBB_spin_rw_mutex_H
22 #define __TBB_spin_rw_mutex_H
23 
24 #include "tbb_stddef.h"
25 #include "tbb_machine.h"
26 #include "tbb_profiling.h"
28 
29 namespace tbb {
30 
31 #if __TBB_TSX_AVAILABLE
32 namespace interface8 { namespace internal {
33  class x86_rtm_rw_mutex;
34 }}
35 #endif
36 
39 
41 
42 class spin_rw_mutex_v3 : internal::mutex_copy_deprecated_and_disabled {
44 
47 
49 
51 
54 
57 
59 
61 
64 
67 
70 
72 public:
75 #if TBB_USE_THREADING_TOOLS
77 #endif
78  }
79 
80 #if TBB_USE_ASSERT
81  ~spin_rw_mutex_v3() {
83  __TBB_ASSERT( !state, "destruction of an acquired mutex");
84  };
85 #endif /* TBB_USE_ASSERT */
86 
88 
90  class scoped_lock : internal::no_copy {
91 #if __TBB_TSX_AVAILABLE
92  friend class tbb::interface8::internal::x86_rtm_rw_mutex;
93 #endif
94  public:
96 
97  scoped_lock() : mutex(NULL), is_writer(false) {}
98 
100  scoped_lock( spin_rw_mutex& m, bool write = true ) : mutex(NULL) {
101  acquire(m, write);
102  }
103 
106  if( mutex ) release();
107  }
108 
110  void acquire( spin_rw_mutex& m, bool write = true ) {
111  __TBB_ASSERT( !mutex, "holding mutex already" );
112  is_writer = write;
113  mutex = &m;
114  if( write ) mutex->internal_acquire_writer();
115  else mutex->internal_acquire_reader();
116  }
117 
119 
121  __TBB_ASSERT( mutex, "mutex is not acquired" );
122  if (is_writer) return true; // Already a writer
123  is_writer = true;
124  return mutex->internal_upgrade();
125  }
126 
128  void release() {
129  __TBB_ASSERT( mutex, "mutex is not acquired" );
130  spin_rw_mutex *m = mutex;
131  mutex = NULL;
132 #if TBB_USE_THREADING_TOOLS||TBB_USE_ASSERT
134  else m->internal_release_reader();
135 #else
136  if( is_writer ) __TBB_AtomicAND( &m->state, READERS );
137  else __TBB_FetchAndAddWrelease( &m->state, -(intptr_t)ONE_READER);
138 #endif /* TBB_USE_THREADING_TOOLS||TBB_USE_ASSERT */
139  }
140 
143  __TBB_ASSERT( mutex, "mutex is not acquired" );
144  if (!is_writer) return true; // Already a reader
145 #if TBB_USE_THREADING_TOOLS||TBB_USE_ASSERT
146  mutex->internal_downgrade();
147 #else
148  __TBB_FetchAndAddW( &mutex->state, ((intptr_t)ONE_READER-WRITER));
149 #endif /* TBB_USE_THREADING_TOOLS||TBB_USE_ASSERT */
150  is_writer = false;
151  return true;
152  }
153 
155  bool try_acquire( spin_rw_mutex& m, bool write = true ) {
156  __TBB_ASSERT( !mutex, "holding mutex already" );
157  bool result;
158  is_writer = write;
159  result = write? m.internal_try_acquire_writer()
161  if( result )
162  mutex = &m;
163  return result;
164  }
165 
166  protected:
167 
170 
172 
173  bool is_writer;
174  };
175 
176  // Mutex traits
177  static const bool is_rw_mutex = true;
178  static const bool is_recursive_mutex = false;
179  static const bool is_fair_mutex = false;
180 
181  // ISO C++0x compatibility methods
182 
185 
187 
189 
191  void unlock() {
192 #if TBB_USE_THREADING_TOOLS||TBB_USE_ASSERT
195 #else
197  else __TBB_FetchAndAddWrelease( &state, -(intptr_t)ONE_READER);
198 #endif /* TBB_USE_THREADING_TOOLS||TBB_USE_ASSERT */
199  }
200 
201  // Methods for reader locks that resemble ISO C++0x compatibility methods.
202 
205 
207 
209 
210 protected:
211  typedef intptr_t state_t;
212  static const state_t WRITER = 1;
213  static const state_t WRITER_PENDING = 2;
214  static const state_t READERS = ~(WRITER | WRITER_PENDING);
215  static const state_t ONE_READER = 4;
216  static const state_t BUSY = WRITER | READERS;
218 
222 
223 private:
225 };
226 
228 
229 } // namespace tbb
230 
231 #if __TBB_TSX_AVAILABLE
233 #endif
234 
235 namespace tbb {
236 namespace interface8 {
238 
246 #if __TBB_TSX_AVAILABLE
248 #else
250 #endif
251 } // namespace interface8
252 
255 } // namespace tbb
256 #endif /* __TBB_spin_rw_mutex_H */
Fast, unfair, spinning reader-writer lock with backoff and writer-preference.
Definition: spin_rw_mutex.h:42
void __TBB_EXPORTED_METHOD internal_acquire_reader()
Internal acquire read lock.
spin_rw_mutex * mutex
The pointer to the current mutex that is held, or NULL if no mutex is held.
void __TBB_EXPORTED_METHOD internal_release_reader()
Internal release read lock.
static const state_t BUSY
#define __TBB_ASSERT(predicate, comment)
No-op version of __TBB_ASSERT.
Definition: tbb_stddef.h:169
bool __TBB_EXPORTED_METHOD internal_acquire_writer()
Internal acquire write lock.
bool try_lock_read()
Try acquiring reader lock (non-blocking)
void __TBB_EXPORTED_METHOD internal_construct()
bool __TBB_EXPORTED_METHOD internal_try_acquire_reader()
Internal try_acquire read lock.
#define __TBB_FetchAndAddWrelease(P, V)
Definition: tbb_machine.h:313
void __TBB_AtomicAND(volatile void *operand, uintptr_t addend)
Definition: tbb_machine.h:892
~scoped_lock()
Release lock (if lock is held).
static const bool is_fair_mutex
void lock_read()
Acquire reader lock.
bool try_acquire(spin_rw_mutex &m, bool write=true)
Try acquire lock on given mutex.
void __TBB_EXPORTED_METHOD internal_downgrade()
Out of line code for downgrading a writer to a reader.
scoped_lock(spin_rw_mutex &m, bool write=true)
Acquire lock on given mutex.
static const state_t ONE_READER
bool downgrade_to_reader()
Downgrade writer to become a reader.
static const state_t WRITER
#define __TBB_EXPORTED_METHOD
Definition: tbb_stddef.h:102
static const bool is_recursive_mutex
spin_rw_mutex_v3()
Construct unacquired mutex.
Definition: spin_rw_mutex.h:74
The graph class.
bool upgrade_to_writer()
Upgrade reader to become a writer.
#define __TBB_DEFINE_PROFILING_SET_NAME(sync_object_type)
static const state_t WRITER_PENDING
spin_rw_mutex_v3 spin_rw_mutex
Definition: spin_rw_mutex.h:37
state_t state
State of lock.
void __TBB_EXPORTED_METHOD internal_release_writer()
Out of line code for releasing a write lock.
void acquire(spin_rw_mutex &m, bool write=true)
Acquire lock on given mutex.
void lock()
Acquire writer lock.
static const bool is_rw_mutex
void unlock()
Release lock.
bool is_writer
If mutex!=NULL, then is_writer is true if holding a writer lock, false if holding a reader lock.
scoped_lock()
Construct lock that has not acquired a mutex.
Definition: spin_rw_mutex.h:97
bool __TBB_EXPORTED_METHOD internal_try_acquire_writer()
Internal try_acquire write lock.
Wrapper around the platform's native lock.
Definition: mutex.h:39
The scoped locking pattern.
Definition: spin_rw_mutex.h:90
bool try_lock()
Try acquiring writer lock (non-blocking)
bool __TBB_EXPORTED_METHOD internal_upgrade()
Internal upgrade reader to become a writer.
static const state_t READERS
interface7::internal::padded_mutex< tbb::spin_rw_mutex, true > speculative_spin_rw_mutex
A cross-platform spin reader/writer mutex with speculative lock acquisition.

Copyright © 2005-2019 Intel Corporation. All Rights Reserved.

Intel, Pentium, Intel Xeon, Itanium, Intel XScale and VTune are registered trademarks or trademarks of Intel Corporation or its subsidiaries in the United States and other countries.

* Other names and brands may be claimed as the property of others.