blob: bfcadc21392ad2af8efe03f1a77c0d21b3bfd0f0 [file] [log] [blame]
Markus Handellf70fbc82020-06-04 00:41:20 +02001/*
2 * Copyright 2020 The WebRTC Project Authors. All rights reserved.
3 *
4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree.
9 */
10
11#ifndef RTC_BASE_SYNCHRONIZATION_MUTEX_H_
12#define RTC_BASE_SYNCHRONIZATION_MUTEX_H_
13
14#include <atomic>
15
16#include "absl/base/const_init.h"
17#include "rtc_base/checks.h"
18#include "rtc_base/system/unused.h"
19#include "rtc_base/thread_annotations.h"
20
21#if defined(WEBRTC_ABSL_MUTEX)
22#include "rtc_base/synchronization/mutex_abseil.h"
23#elif defined(WEBRTC_WIN)
24#include "rtc_base/synchronization/mutex_critical_section.h"
25#elif defined(WEBRTC_POSIX)
26#include "rtc_base/synchronization/mutex_pthread.h"
27#else
28#error Unsupported platform.
29#endif
30
31namespace webrtc {
32
33// The Mutex guarantees exclusive access and aims to follow Abseil semantics
34// (i.e. non-reentrant etc).
35class RTC_LOCKABLE Mutex final {
36 public:
37 Mutex() = default;
38 Mutex(const Mutex&) = delete;
39 Mutex& operator=(const Mutex&) = delete;
40
41 void Lock() RTC_EXCLUSIVE_LOCK_FUNCTION() { impl_.Lock(); }
42 RTC_WARN_UNUSED_RESULT bool TryLock() RTC_EXCLUSIVE_TRYLOCK_FUNCTION(true) {
43 return impl_.TryLock();
44 }
45 void Unlock() RTC_UNLOCK_FUNCTION() { impl_.Unlock(); }
46
47 private:
48 MutexImpl impl_;
49};
50
51// MutexLock, for serializing execution through a scope.
52class RTC_SCOPED_LOCKABLE MutexLock final {
53 public:
54 MutexLock(const MutexLock&) = delete;
55 MutexLock& operator=(const MutexLock&) = delete;
56
57 explicit MutexLock(Mutex* mutex) RTC_EXCLUSIVE_LOCK_FUNCTION(mutex)
58 : mutex_(mutex) {
59 mutex->Lock();
60 }
61 ~MutexLock() RTC_UNLOCK_FUNCTION() { mutex_->Unlock(); }
62
63 private:
64 Mutex* mutex_;
65};
66
67// A mutex used to protect global variables. Do NOT use for other purposes.
68#if defined(WEBRTC_ABSL_MUTEX)
69using GlobalMutex = absl::Mutex;
70using GlobalMutexLock = absl::MutexLock;
71#else
72class RTC_LOCKABLE GlobalMutex final {
73 public:
74 GlobalMutex(const GlobalMutex&) = delete;
75 GlobalMutex& operator=(const GlobalMutex&) = delete;
76
77 constexpr explicit GlobalMutex(absl::ConstInitType /*unused*/)
78 : mutex_locked_(0) {}
79
80 void Lock() RTC_EXCLUSIVE_LOCK_FUNCTION();
81 void Unlock() RTC_UNLOCK_FUNCTION();
82
83 private:
84 std::atomic<int> mutex_locked_; // 0 means lock not taken, 1 means taken.
85};
86
87// GlobalMutexLock, for serializing execution through a scope.
88class RTC_SCOPED_LOCKABLE GlobalMutexLock final {
89 public:
90 GlobalMutexLock(const GlobalMutexLock&) = delete;
91 GlobalMutexLock& operator=(const GlobalMutexLock&) = delete;
92
93 explicit GlobalMutexLock(GlobalMutex* mutex) RTC_EXCLUSIVE_LOCK_FUNCTION();
94 ~GlobalMutexLock() RTC_UNLOCK_FUNCTION();
95
96 private:
97 GlobalMutex* mutex_;
98};
99#endif // if defined(WEBRTC_ABSL_MUTEX)
100
101} // namespace webrtc
102
103#endif // RTC_BASE_SYNCHRONIZATION_MUTEX_H_