mirror of
https://github.com/Takiiiiiiii/strato.git
synced 2025-07-17 08:46:39 +00:00
Lock TextureManager
/BufferManager
during submission
Multiple threads concurrently accessing the `TextureManager`/`BufferManager` (Referred to as "resource managers") has a potential deadlock with a resource being locked while acquiring the resource manager lock while the thread owning it tries to acquire a lock on the resource resulting in a deadlock. This has been fixed with locking of resource manager now being externally handled which ensures it can be locked prior to locking any resources, `CommandExecutor` provides accessors for retrieving the resource manager which automatically handles locking aside doing so on attachment of resources.
This commit is contained in:
@ -12,6 +12,18 @@ namespace skyline::gpu {
|
||||
return it->guest->begin().base() < pointer;
|
||||
}
|
||||
|
||||
void BufferManager::lock() {
|
||||
mutex.lock();
|
||||
}
|
||||
|
||||
void BufferManager::unlock() {
|
||||
mutex.unlock();
|
||||
}
|
||||
|
||||
bool BufferManager::try_lock() {
|
||||
return mutex.try_lock();
|
||||
}
|
||||
|
||||
BufferView BufferManager::FindOrCreate(GuestBuffer guestMapping, ContextTag tag) {
|
||||
/*
|
||||
* We align the buffer to the page boundary to ensure that:
|
||||
@ -22,8 +34,6 @@ namespace skyline::gpu {
|
||||
vk::DeviceSize offset{static_cast<size_t>(guestMapping.begin().base() - alignedStart)}, size{guestMapping.size()};
|
||||
guestMapping = span<u8>{alignedStart, alignedEnd};
|
||||
|
||||
std::scoped_lock lock(mutex);
|
||||
|
||||
// Lookup for any buffers overlapping with the supplied guest mapping
|
||||
boost::container::small_vector<std::shared_ptr<Buffer>, 4> overlaps;
|
||||
for (auto entryIt{std::lower_bound(buffers.begin(), buffers.end(), guestMapping.end().base(), BufferLessThan)}; entryIt != buffers.begin() && (*--entryIt)->guest->begin() <= guestMapping.end();)
|
||||
@ -89,7 +99,9 @@ namespace skyline::gpu {
|
||||
return newBuffer->GetView(static_cast<vk::DeviceSize>(guestMapping.begin() - newBuffer->guest->begin()) + offset, size);
|
||||
}
|
||||
|
||||
BufferManager::MegaBufferSlot::MegaBufferSlot(GPU &gpu) : backing(gpu.memory.AllocateBuffer(Size)) {}
|
||||
constexpr static vk::DeviceSize MegaBufferSize{100 * 1024 * 1024}; //!< Size in bytes of the megabuffer (100MiB)
|
||||
|
||||
BufferManager::MegaBufferSlot::MegaBufferSlot(GPU &gpu) : backing(gpu.memory.AllocateBuffer(MegaBufferSize)) {}
|
||||
|
||||
MegaBuffer::MegaBuffer(BufferManager::MegaBufferSlot &slot) : slot{&slot}, freeRegion{slot.backing.subspan(PAGE_SIZE)} {}
|
||||
|
||||
@ -135,7 +147,7 @@ namespace skyline::gpu {
|
||||
}
|
||||
|
||||
MegaBuffer BufferManager::AcquireMegaBuffer(const std::shared_ptr<FenceCycle> &cycle) {
|
||||
std::scoped_lock lock{mutex};
|
||||
std::scoped_lock lock{megaBufferMutex};
|
||||
|
||||
for (auto &slot : megaBuffers) {
|
||||
if (!slot.active.test_and_set(std::memory_order_acq_rel)) {
|
||||
|
Reference in New Issue
Block a user