mirror of
https://github.com/KytyPS5/KytyPS5.git
synced 2026-10-28 08:13:05 +00:00
refactor renderer
This commit is contained in:
1 parent
a720b28b7f
commit
a20cf5d298
112 files changed
+18269
-18368
No files matched your search
@@ -3,17 +3,14 @@
|
||||
#include "common/assert.h"
|
||||
#include "graphics/guest_gpu/command_processor/commandProcessor.h"
|
||||
#include "graphics/guest_gpu/graphicsRun.h"
|
||||
#include "graphics/host_gpu/objects/label.h"
|
||||
#include "graphics/host_gpu/renderer/render.h"
|
||||
#include "graphics/host_gpu/renderer/renderContext.h"
|
||||
#include "graphics/host_gpu/renderer/commandScheduler.h"
|
||||
|
||||
namespace Libs::Graphics {
|
||||
|
||||
GpuResourceManager::GpuResourceManager(GraphicContext& graphics)
|
||||
: m_page_manager(FaultThunk, this), m_buffer_cache(graphics, m_page_manager, m_resource_mutex),
|
||||
m_texture_cache(graphics, m_page_manager, m_buffer_cache, m_resource_mutex) {
|
||||
m_buffer_cache.SetTextureCache(m_texture_cache);
|
||||
}
|
||||
GpuResourceManager::GpuResourceManager(GraphicContext& graphics, CommandScheduler& scheduler)
|
||||
: m_page_manager(FaultThunk, this),
|
||||
m_buffer_cache(graphics, scheduler, m_page_manager, m_texture_cache, m_resource_mutex),
|
||||
m_texture_cache(graphics, scheduler, m_page_manager, m_buffer_cache, m_resource_mutex) {}
|
||||
|
||||
GpuResourceManager::~GpuResourceManager() = default;
|
||||
|
||||
@@ -24,6 +21,15 @@ bool GpuResourceManager::FaultThunk(void* context, PageFaultAccess access, uint6
|
||||
|
||||
bool GpuResourceManager::InvalidateMemory(PageFaultAccess access, uint64_t vaddr, uint64_t size,
|
||||
PageFaultPhase phase) noexcept {
|
||||
// Let the authoritative image materialize first. A clean overlapping buffer marks a write
|
||||
// fault CPU-dirty when it begins ownership transfer; doing that before image preflight would
|
||||
// make the image appear to race a real CPU write. Completion and release retain buffer-first
|
||||
// ordering so its pending fault is gone before TextureCache publishes the downloaded backing.
|
||||
if (phase == PageFaultPhase::Invalidate) {
|
||||
const bool image_handled = m_texture_cache.InvalidateMemory(access, vaddr, size, phase);
|
||||
const bool buffer_handled = m_buffer_cache.InvalidateMemory(access, vaddr, size, phase);
|
||||
return buffer_handled || image_handled;
|
||||
}
|
||||
const bool buffer_handled = m_buffer_cache.InvalidateMemory(access, vaddr, size, phase);
|
||||
const bool image_handled = m_texture_cache.InvalidateMemory(access, vaddr, size, phase);
|
||||
return buffer_handled || image_handled;
|
||||
@@ -33,19 +39,23 @@ bool GpuResourceManager::HandleFault(PageFaultAccess access, uint64_t fault_vadd
|
||||
if (!m_page_manager.IsMapped(fault_vaddr, 1)) {
|
||||
return false;
|
||||
}
|
||||
if (LabelInCallback()) {
|
||||
EXIT("unsupported guest-memory fault from an asynchronous GPU label callback, "
|
||||
if (CommandScheduler::InDeferredOperation()) {
|
||||
EXIT("unsupported guest-memory fault from an asynchronous GPU completion, "
|
||||
"addr=0x%016" PRIx64 " access=%u\n",
|
||||
fault_vaddr, static_cast<uint32_t>(access));
|
||||
}
|
||||
if (auto* cp = GraphicsRunCurrentCommandProcessor(); cp != nullptr) {
|
||||
cp->BeginReadbackTransaction();
|
||||
bool handled = false;
|
||||
bool handled = false;
|
||||
const auto resolve = [this, access, fault_vaddr, &handled](CommandProcessor& cp) {
|
||||
cp.BeginReadbackTransaction();
|
||||
(void)m_buffer_cache.SynchronizeBacking(fault_vaddr, 1);
|
||||
{
|
||||
ResourceMutex::FaultScope fault(m_resource_mutex);
|
||||
handled = m_page_manager.HandleFault(access, fault_vaddr);
|
||||
}
|
||||
cp->EndReadbackTransaction();
|
||||
cp.EndReadbackTransaction();
|
||||
};
|
||||
if (auto* cp = Gpu::CurrentCommandProcessor(); cp != nullptr) {
|
||||
resolve(*cp);
|
||||
return handled;
|
||||
}
|
||||
if (m_resource_mutex.IsOwnedByCurrentThread()) {
|
||||
@@ -53,36 +63,36 @@ bool GpuResourceManager::HandleFault(PageFaultAccess access, uint64_t fault_vadd
|
||||
" access=%u\n",
|
||||
fault_vaddr, static_cast<uint32_t>(access));
|
||||
}
|
||||
// Stop command-processor jobs before taking the shared cache transaction. External readback
|
||||
// workers inherit this paused state and therefore never form resource -> submission lock
|
||||
// inversion.
|
||||
GraphicsRunSubmissionLock submissions;
|
||||
ResourceMutex::FaultScope fault(m_resource_mutex);
|
||||
return m_page_manager.HandleFault(access, fault_vaddr);
|
||||
EXIT_IF(m_gpu == nullptr);
|
||||
m_gpu->SendCommandSyncWithProcessor(resolve);
|
||||
return handled;
|
||||
}
|
||||
|
||||
void GpuResourceManager::PrepareHostWrite(uint64_t vaddr, uint64_t size) {
|
||||
if (!m_page_manager.HasAnyMapping(vaddr, size)) {
|
||||
return;
|
||||
}
|
||||
if (LabelInCallback()) {
|
||||
EXIT("unsupported host write from an asynchronous GPU label callback, addr=0x%016" PRIx64
|
||||
if (CommandScheduler::InDeferredOperation()) {
|
||||
EXIT("unsupported host write from an asynchronous GPU completion, addr=0x%016" PRIx64
|
||||
" size=0x%016" PRIx64 "\n",
|
||||
vaddr, size);
|
||||
}
|
||||
const auto handle_range = [this, vaddr, size]() {
|
||||
const auto handle_range = [this, vaddr, size] {
|
||||
if (!m_page_manager.HandleWriteRange(vaddr, size)) {
|
||||
EXIT("failed to prepare host write, addr=0x%016" PRIx64 " size=0x%016" PRIx64 "\n",
|
||||
vaddr, size);
|
||||
}
|
||||
};
|
||||
if (auto* cp = GraphicsRunCurrentCommandProcessor(); cp != nullptr) {
|
||||
cp->BeginReadbackTransaction();
|
||||
const auto resolve = [this, &handle_range](CommandProcessor& cp) {
|
||||
cp.BeginReadbackTransaction();
|
||||
{
|
||||
ResourceMutex::FaultScope fault(m_resource_mutex);
|
||||
handle_range();
|
||||
}
|
||||
cp->EndReadbackTransaction();
|
||||
cp.EndReadbackTransaction();
|
||||
};
|
||||
if (auto* cp = Gpu::CurrentCommandProcessor(); cp != nullptr) {
|
||||
resolve(*cp);
|
||||
return;
|
||||
}
|
||||
if (m_resource_mutex.IsOwnedByCurrentThread()) {
|
||||
@@ -90,9 +100,8 @@ void GpuResourceManager::PrepareHostWrite(uint64_t vaddr, uint64_t size) {
|
||||
" size=0x%016" PRIx64 "\n",
|
||||
vaddr, size);
|
||||
}
|
||||
GraphicsRunSubmissionLock submissions;
|
||||
ResourceMutex::FaultScope fault(m_resource_mutex);
|
||||
handle_range();
|
||||
EXIT_IF(m_gpu == nullptr);
|
||||
m_gpu->SendCommandSyncWithProcessor(resolve);
|
||||
}
|
||||
|
||||
bool GpuResourceManager::IsMapped(uint64_t vaddr, uint64_t size) const noexcept {
|
||||
@@ -107,27 +116,26 @@ void GpuResourceManager::UnmapMemory(uint64_t vaddr, uint64_t size, GpuAccess ac
|
||||
if (!IsMapped(vaddr, size)) {
|
||||
EXIT("cannot unmap an unmapped GPU resource range\n");
|
||||
}
|
||||
m_texture_cache.UnmapMemory(vaddr, size);
|
||||
m_buffer_cache.UnmapMemory(vaddr, size);
|
||||
m_page_manager.OnGpuUnmap(vaddr, size, access);
|
||||
const auto unmap = [this, vaddr, size, access] {
|
||||
m_texture_cache.UnmapMemory(vaddr, size);
|
||||
m_buffer_cache.UnmapMemory(vaddr, size);
|
||||
m_page_manager.OnGpuUnmap(vaddr, size, access);
|
||||
};
|
||||
if (m_gpu == nullptr) {
|
||||
if (m_resource_mutex.IsOwnedByCurrentThread()) {
|
||||
EXIT("cannot synchronously unmap from a resource transaction\n");
|
||||
}
|
||||
unmap();
|
||||
return;
|
||||
}
|
||||
Gpu::SubmissionLock submissions(*m_gpu);
|
||||
m_gpu->SendCommandSync(unmap);
|
||||
}
|
||||
|
||||
void GpuResourceManager::FillBuffer(CommandBuffer& command, uint64_t vaddr, uint64_t size,
|
||||
uint32_t value) {
|
||||
if (command.IsInvalid()) {
|
||||
EXIT("cannot fill a buffer without a valid render command context\n");
|
||||
}
|
||||
Common::LockGuard lock(GetRenderContext().GetMutex());
|
||||
m_buffer_cache.FillBuffer(&command, vaddr, size, value);
|
||||
}
|
||||
|
||||
void GpuResourceManager::CopyBuffer(CommandBuffer& command, uint64_t dst_vaddr, uint64_t src_vaddr,
|
||||
uint64_t size) {
|
||||
if (command.IsInvalid()) {
|
||||
EXIT("cannot copy a buffer without a valid render command context\n");
|
||||
}
|
||||
Common::LockGuard lock(GetRenderContext().GetMutex());
|
||||
m_buffer_cache.CopyBuffer(&command, dst_vaddr, src_vaddr, size);
|
||||
void GpuResourceManager::RunGarbageCollector() {
|
||||
m_texture_cache.ProcessDownloadImages();
|
||||
m_texture_cache.RunGarbageCollector();
|
||||
m_buffer_cache.RunGarbageCollector();
|
||||
}
|
||||
|
||||
} // namespace Libs::Graphics
|
||||
Reference in new issue
Block a user