Commit a777fd4b authored by Benoit Lize's avatar Benoit Lize Committed by Commit Bot

[PartitionAlloc] Implement SpinningMutex on macOS.

macOS has futex()-like locks in pthread, meaning that SpinningFutex can
be useful there, the same way it is on Windows. Use pthread to implement
it.

Bug: 998048
Change-Id: I77df835baf2f099eedcfcee675f7a56ed6b3bb2b
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2550797Reviewed-by: default avatarKentaro Hara <haraken@chromium.org>
Commit-Queue: Benoit L <lizeb@chromium.org>
Cr-Commit-Position: refs/heads/master@{#830175}
parent 6028033b
...@@ -70,12 +70,19 @@ void SpinningMutex::LockSlow() { ...@@ -70,12 +70,19 @@ void SpinningMutex::LockSlow() {
} }
} }
#else #elif defined(OS_WIN)
void SpinningMutex::LockSlow() { void SpinningMutex::LockSlow() {
::AcquireSRWLockExclusive(reinterpret_cast<PSRWLOCK>(&lock_)); ::AcquireSRWLockExclusive(reinterpret_cast<PSRWLOCK>(&lock_));
} }
#elif defined(OS_APPLE)
void SpinningMutex::LockSlow() {
int retval = pthread_mutex_lock(&lock_);
PA_DCHECK(retval == 0);
}
#endif #endif
} // namespace internal } // namespace internal
} // namespace base } // namespace base
......
...@@ -8,6 +8,7 @@ ...@@ -8,6 +8,7 @@
#include <algorithm> #include <algorithm>
#include <atomic> #include <atomic>
#include "base/allocator/partition_allocator/partition_alloc_check.h"
#include "base/allocator/partition_allocator/yield_processor.h" #include "base/allocator/partition_allocator/yield_processor.h"
#include "base/base_export.h" #include "base/base_export.h"
#include "base/compiler_specific.h" #include "base/compiler_specific.h"
...@@ -18,11 +19,20 @@ ...@@ -18,11 +19,20 @@
#include <windows.h> #include <windows.h>
#endif #endif
#if defined(OS_APPLE)
#include <errno.h>
#include <pthread.h>
#endif
#if defined(OS_LINUX) || defined(OS_CHROMEOS) || defined(OS_ANDROID) #if defined(OS_LINUX) || defined(OS_CHROMEOS) || defined(OS_ANDROID)
#define PA_HAS_LINUX_KERNEL #define PA_HAS_LINUX_KERNEL
#endif #endif
#if defined(PA_HAS_LINUX_KERNEL) || defined(OS_WIN) // Linux: futex() makes Try() fast without a syscall.
// Windows: SRWLock are futex()-like.
// Apple: pthread has futex()-like locks (see pthread_mutex.c in Apple's
// libpthread).
#if defined(PA_HAS_LINUX_KERNEL) || defined(OS_WIN) || defined(OS_APPLE)
#define PA_HAS_SPINNING_MUTEX #define PA_HAS_SPINNING_MUTEX
#endif #endif
...@@ -75,8 +85,10 @@ class LOCKABLE BASE_EXPORT SpinningMutex { ...@@ -75,8 +85,10 @@ class LOCKABLE BASE_EXPORT SpinningMutex {
static constexpr int kLockedContended = 2; static constexpr int kLockedContended = 2;
std::atomic<int32_t> state_{kUnlocked}; std::atomic<int32_t> state_{kUnlocked};
#else #elif defined(OS_WIN)
SRWLOCK lock_ = SRWLOCK_INIT; SRWLOCK lock_ = SRWLOCK_INIT;
#elif defined(OS_APPLE)
pthread_mutex_t lock_ = PTHREAD_MUTEX_INITIALIZER;
#endif #endif
}; };
...@@ -141,7 +153,7 @@ ALWAYS_INLINE void SpinningMutex::Release() { ...@@ -141,7 +153,7 @@ ALWAYS_INLINE void SpinningMutex::Release() {
} }
} }
#else #elif defined(OS_WIN)
ALWAYS_INLINE bool SpinningMutex::Try() { ALWAYS_INLINE bool SpinningMutex::Try() {
return !!::TryAcquireSRWLockExclusive(reinterpret_cast<PSRWLOCK>(&lock_)); return !!::TryAcquireSRWLockExclusive(reinterpret_cast<PSRWLOCK>(&lock_));
...@@ -151,6 +163,19 @@ ALWAYS_INLINE void SpinningMutex::Release() { ...@@ -151,6 +163,19 @@ ALWAYS_INLINE void SpinningMutex::Release() {
::ReleaseSRWLockExclusive(reinterpret_cast<PSRWLOCK>(&lock_)); ::ReleaseSRWLockExclusive(reinterpret_cast<PSRWLOCK>(&lock_));
} }
#elif defined(OS_APPLE)
ALWAYS_INLINE bool SpinningMutex::Try() {
int retval = pthread_mutex_trylock(&lock_);
PA_DCHECK(retval == 0 || retval == EBUSY);
return retval == 0;
}
ALWAYS_INLINE void SpinningMutex::Release() {
int retval = pthread_mutex_unlock(&lock_);
PA_DCHECK(retval == 0);
}
#endif #endif
} // namespace internal } // namespace internal
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment