blob: 620fe74e4a144ce511dc07015186c82fe0cc9061 [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"
Danil Chapovalov4319b162021-01-14 15:02:22 +000018#include "rtc_base/system/unused.h"
Markus Handellf70fbc82020-06-04 00:41:20 +020019#include "rtc_base/thread_annotations.h"
20
21#if defined(WEBRTC_ABSL_MUTEX)
Markus Handell8e75bd42020-06-05 11:47:40 +020022#include "rtc_base/synchronization/mutex_abseil.h" // nogncheck
Markus Handellf70fbc82020-06-04 00:41:20 +020023#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
Markus Handell2d27b1a2020-06-09 17:34:41 +020041 void Lock() RTC_EXCLUSIVE_LOCK_FUNCTION() {
Markus Handell2d27b1a2020-06-09 17:34:41 +020042 impl_.Lock();
Markus Handellf70fbc82020-06-04 00:41:20 +020043 }
Danil Chapovalov4319b162021-01-14 15:02:22 +000044 RTC_WARN_UNUSED_RESULT bool TryLock() RTC_EXCLUSIVE_TRYLOCK_FUNCTION(true) {
Markus Handell2a23bd22020-09-30 12:59:10 +020045 return impl_.TryLock();
Markus Handell2d27b1a2020-06-09 17:34:41 +020046 }
47 void Unlock() RTC_UNLOCK_FUNCTION() {
Markus Handell2d27b1a2020-06-09 17:34:41 +020048 impl_.Unlock();
49 }
Markus Handellf70fbc82020-06-04 00:41:20 +020050
51 private:
52 MutexImpl impl_;
Markus Handellf70fbc82020-06-04 00:41:20 +020053};
54
55// MutexLock, for serializing execution through a scope.
56class RTC_SCOPED_LOCKABLE MutexLock final {
57 public:
58 MutexLock(const MutexLock&) = delete;
59 MutexLock& operator=(const MutexLock&) = delete;
60
61 explicit MutexLock(Mutex* mutex) RTC_EXCLUSIVE_LOCK_FUNCTION(mutex)
62 : mutex_(mutex) {
63 mutex->Lock();
64 }
65 ~MutexLock() RTC_UNLOCK_FUNCTION() { mutex_->Unlock(); }
66
67 private:
68 Mutex* mutex_;
69};
70
71// A mutex used to protect global variables. Do NOT use for other purposes.
72#if defined(WEBRTC_ABSL_MUTEX)
73using GlobalMutex = absl::Mutex;
74using GlobalMutexLock = absl::MutexLock;
75#else
76class RTC_LOCKABLE GlobalMutex final {
77 public:
78 GlobalMutex(const GlobalMutex&) = delete;
79 GlobalMutex& operator=(const GlobalMutex&) = delete;
80
81 constexpr explicit GlobalMutex(absl::ConstInitType /*unused*/)
82 : mutex_locked_(0) {}
83
84 void Lock() RTC_EXCLUSIVE_LOCK_FUNCTION();
85 void Unlock() RTC_UNLOCK_FUNCTION();
86
87 private:
88 std::atomic<int> mutex_locked_; // 0 means lock not taken, 1 means taken.
89};
90
91// GlobalMutexLock, for serializing execution through a scope.
92class RTC_SCOPED_LOCKABLE GlobalMutexLock final {
93 public:
94 GlobalMutexLock(const GlobalMutexLock&) = delete;
95 GlobalMutexLock& operator=(const GlobalMutexLock&) = delete;
96
Markus Handell0dd35d32020-07-15 11:53:44 +020097 explicit GlobalMutexLock(GlobalMutex* mutex)
98 RTC_EXCLUSIVE_LOCK_FUNCTION(mutex_);
Markus Handellf70fbc82020-06-04 00:41:20 +020099 ~GlobalMutexLock() RTC_UNLOCK_FUNCTION();
100
101 private:
102 GlobalMutex* mutex_;
103};
104#endif // if defined(WEBRTC_ABSL_MUTEX)
105
106} // namespace webrtc
107
108#endif // RTC_BASE_SYNCHRONIZATION_MUTEX_H_