This commit is contained in:
TheLastRar 2025-12-15 16:13:49 -06:00 committed by GitHub
commit eae7a8674a
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 61 additions and 4 deletions

View File

@ -2354,6 +2354,7 @@ GSDevice::PresentResult GSDeviceVK::BeginPresent(bool frame_skip)
{0, 0}, {static_cast<u32>(swap_chain_texture->GetWidth()), static_cast<u32>(swap_chain_texture->GetHeight())}};
vkCmdSetViewport(GetCurrentCommandBuffer(), 0, 1, &vp);
vkCmdSetScissor(GetCurrentCommandBuffer(), 0, 1, &scissor);
m_is_presenting = true;
return PresentResult::OK;
}
@ -2363,6 +2364,7 @@ void GSDeviceVK::EndPresent()
VkCommandBuffer cmdbuffer = GetCurrentCommandBuffer();
vkCmdEndRenderPass(cmdbuffer);
m_is_presenting = false;
m_swap_chain->GetCurrentTexture()->TransitionToLayout(cmdbuffer, GSTextureVK::Layout::PresentSrc);
g_perfmon.Put(GSPerfMon::RenderPasses, 1);
@ -2372,6 +2374,11 @@ void GSDeviceVK::EndPresent()
InvalidateCachedState();
}
bool GSDeviceVK::IsPresenting() const
{
return m_is_presenting;
}
#ifdef ENABLE_OGL_DEBUG
static std::array<float, 3> Palette(float phase, const std::array<float, 3>& a, const std::array<float, 3>& b,
const std::array<float, 3>& c, const std::array<float, 3>& d)
@ -5001,6 +5008,33 @@ void GSDeviceVK::ExecuteCommandBufferAndRestartRenderPass(bool wait_for_completi
}
}
void GSDeviceVK::ExecuteCommandBufferAndRestartPresent(bool wait_for_completion, const char* reason, ...)
{
std::va_list ap;
va_start(ap, reason);
const std::string reason_str(StringUtil::StdStringFromFormatV(reason, ap));
va_end(ap);
Console.Warning("VK: Executing command buffer due to '%s'", reason_str.c_str());
pxAssert(m_is_presenting);
vkCmdEndRenderPass(GetCurrentCommandBuffer());
ExecuteCommandBuffer(wait_for_completion);
GSTextureVK* swap_chain_texture = m_swap_chain->GetCurrentTexture();
const VkFramebuffer fb = swap_chain_texture->GetFramebuffer(false);
pxAssert(fb);
const VkRenderPassBeginInfo rp = {VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO, nullptr,
GetRenderPass(swap_chain_texture->GetVkFormat(), VK_FORMAT_UNDEFINED, VK_ATTACHMENT_LOAD_OP_LOAD,
VK_ATTACHMENT_STORE_OP_STORE),
fb,
{{0, 0}, {static_cast<u32>(swap_chain_texture->GetWidth()), static_cast<u32>(swap_chain_texture->GetHeight())}},
0u, nullptr};
vkCmdBeginRenderPass(GetCurrentCommandBuffer(), &rp, VK_SUBPASS_CONTENTS_INLINE);
}
void GSDeviceVK::ExecuteCommandBufferForReadback()
{
ExecuteCommandBuffer(true);

View File

@ -367,6 +367,7 @@ public:
private:
std::unique_ptr<VKSwapChain> m_swap_chain;
bool m_is_presenting = false;
VkDescriptorSetLayout m_utility_ds_layout = VK_NULL_HANDLE;
VkPipelineLayout m_utility_pipeline_layout = VK_NULL_HANDLE;
@ -513,6 +514,7 @@ public:
PresentResult BeginPresent(bool frame_skip) override;
void EndPresent() override;
bool IsPresenting() const;
bool SetGPUTimingEnabled(bool enabled) override;
float GetAndResetAccumulatedGPUTime() override;
@ -587,6 +589,7 @@ public:
void ExecuteCommandBuffer(bool wait_for_completion);
void ExecuteCommandBuffer(bool wait_for_completion, const char* reason, ...);
void ExecuteCommandBufferAndRestartRenderPass(bool wait_for_completion, const char* reason);
void ExecuteCommandBufferAndRestartPresent(bool wait_for_completion, const char* reason, ...);
void ExecuteCommandBufferForReadback();
/// Set dirty flags on everything to force re-bind at next draw time.

View File

@ -349,8 +349,18 @@ bool GSTextureVK::Update(const GSVector4i& r, const void* data, int pitch, int l
VKStreamBuffer& sbuffer = GSDeviceVK::GetInstance()->GetTextureUploadBuffer();
if (!sbuffer.ReserveMemory(required_size, GSDeviceVK::GetInstance()->GetBufferCopyOffsetAlignment()))
{
GSDeviceVK::GetInstance()->ExecuteCommandBuffer(
false, "While waiting for %u bytes in texture upload buffer", required_size);
GSDeviceVK* dev = GSDeviceVK::GetInstance();
if (!dev->IsPresenting())
{
dev->ExecuteCommandBuffer(
false, "While waiting for %u bytes in texture upload buffer", required_size);
}
else
{
dev->ExecuteCommandBufferAndRestartPresent(
false, "While waiting for %u bytes in texture upload buffer", required_size);
}
if (!sbuffer.ReserveMemory(required_size, GSDeviceVK::GetInstance()->GetBufferCopyOffsetAlignment()))
{
Console.Error("Failed to reserve texture upload memory (%u bytes).", required_size);
@ -410,8 +420,18 @@ bool GSTextureVK::Map(GSMap& m, const GSVector4i* r, int layer)
if (!buffer.ReserveMemory(required_size, GSDeviceVK::GetInstance()->GetBufferCopyOffsetAlignment()))
{
GSDeviceVK::GetInstance()->ExecuteCommandBuffer(
false, "While waiting for %u bytes in texture upload buffer", required_size);
GSDeviceVK* dev = GSDeviceVK::GetInstance();
if (!dev->IsPresenting())
{
dev->ExecuteCommandBuffer(
false, "While waiting for %u bytes in texture upload buffer", required_size);
}
else
{
dev->ExecuteCommandBufferAndRestartPresent(
false, "While waiting for %u bytes in texture upload buffer", required_size);
}
if (!buffer.ReserveMemory(required_size, GSDeviceVK::GetInstance()->GetBufferCopyOffsetAlignment()))
pxFailRel("Failed to reserve texture upload memory");
}