mirror of
https://github.com/shadps4-emu/shadPS4.git
synced 2026-06-04 15:05:02 -06:00
kernel: fix recursive read-lock deadlock on PthreadRwlock (#4517)
This commit is contained in:
parent
e777f56964
commit
6c282aa1da
@ -3,6 +3,7 @@
|
|||||||
|
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
|
#include <chrono>
|
||||||
#include <condition_variable>
|
#include <condition_variable>
|
||||||
#include <mutex>
|
#include <mutex>
|
||||||
|
|
||||||
@ -26,6 +27,16 @@ public:
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template <typename Clock, typename Duration>
|
||||||
|
bool try_lock_until(const std::chrono::time_point<Clock, Duration>& abs_time) {
|
||||||
|
std::unique_lock<std::mutex> lock(mtx);
|
||||||
|
if (!cv.wait_until(lock, abs_time, [this]() { return !writer_active && readers == 0; })) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
writer_active = true;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
void unlock() {
|
void unlock() {
|
||||||
std::lock_guard<std::mutex> lock(mtx);
|
std::lock_guard<std::mutex> lock(mtx);
|
||||||
writer_active = false;
|
writer_active = false;
|
||||||
@ -38,6 +49,25 @@ public:
|
|||||||
++readers;
|
++readers;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool try_lock_shared() {
|
||||||
|
std::lock_guard<std::mutex> lock(mtx);
|
||||||
|
if (writer_active) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
++readers;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename Clock, typename Duration>
|
||||||
|
bool try_lock_shared_until(const std::chrono::time_point<Clock, Duration>& abs_time) {
|
||||||
|
std::unique_lock<std::mutex> lock(mtx);
|
||||||
|
if (!cv.wait_until(lock, abs_time, [this]() { return !writer_active; })) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
++readers;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
void unlock_shared() {
|
void unlock_shared() {
|
||||||
std::lock_guard<std::mutex> lock(mtx);
|
std::lock_guard<std::mutex> lock(mtx);
|
||||||
if (--readers == 0) {
|
if (--readers == 0) {
|
||||||
|
|||||||
@ -10,6 +10,7 @@
|
|||||||
#include <shared_mutex>
|
#include <shared_mutex>
|
||||||
|
|
||||||
#include "common/enum.h"
|
#include "common/enum.h"
|
||||||
|
#include "common/shared_first_mutex.h"
|
||||||
#include "core/libraries/kernel/sync/mutex.h"
|
#include "core/libraries/kernel/sync/mutex.h"
|
||||||
#include "core/libraries/kernel/sync/semaphore.h"
|
#include "core/libraries/kernel/sync/semaphore.h"
|
||||||
#include "core/libraries/kernel/time.h"
|
#include "core/libraries/kernel/time.h"
|
||||||
@ -202,7 +203,7 @@ struct PthreadRwlockAttr {
|
|||||||
using PthreadRwlockAttrT = PthreadRwlockAttr*;
|
using PthreadRwlockAttrT = PthreadRwlockAttr*;
|
||||||
|
|
||||||
struct PthreadRwlock {
|
struct PthreadRwlock {
|
||||||
std::shared_timed_mutex lock;
|
Common::SharedFirstMutex lock;
|
||||||
Pthread* owner;
|
Pthread* owner;
|
||||||
|
|
||||||
int Wrlock(const OrbisKernelTimespec* abstime);
|
int Wrlock(const OrbisKernelTimespec* abstime);
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user