From eda65c8dd3edcc5807c2a0370967f289ac00cd81 Mon Sep 17 00:00:00 2001 From: riperiperi Date: Sat, 12 Mar 2022 16:50:12 +0000 Subject: [PATCH] Copy query results after RP ends, rather than ending to copy We need to end the render pass to get the data (submit command buffer) anyways... Reduces render passes created in games that use queries. --- Ryujinx.Graphics.Vulkan/PipelineBase.cs | 5 +++ Ryujinx.Graphics.Vulkan/PipelineFull.cs | 42 +++++++++++++++++-------- 2 files changed, 34 insertions(+), 13 deletions(-) diff --git a/Ryujinx.Graphics.Vulkan/PipelineBase.cs b/Ryujinx.Graphics.Vulkan/PipelineBase.cs index 1b9f61e2c..c08db6a68 100644 --- a/Ryujinx.Graphics.Vulkan/PipelineBase.cs +++ b/Ryujinx.Graphics.Vulkan/PipelineBase.cs @@ -1148,10 +1148,15 @@ namespace Ryujinx.Graphics.Vulkan PauseTransformFeedbackInternal(); // System.Console.WriteLine("render pass ended " + caller); Gd.Api.CmdEndRenderPass(CommandBuffer); + SignalRenderPassEnd(); _renderPassActive = false; } } + protected virtual void SignalRenderPassEnd() + { + } + private void PauseTransformFeedbackInternal() { if (_tfEnabled && _tfActive) diff --git a/Ryujinx.Graphics.Vulkan/PipelineFull.cs b/Ryujinx.Graphics.Vulkan/PipelineFull.cs index e496649b8..06336da2e 100644 --- a/Ryujinx.Graphics.Vulkan/PipelineFull.cs +++ b/Ryujinx.Graphics.Vulkan/PipelineFull.cs @@ -13,13 +13,36 @@ namespace Ryujinx.Graphics.Vulkan private readonly List _activeQueries; private CounterQueueEvent _activeConditionalRender; + private readonly List<(QueryPool Pool, BufferHolder Holder)> _pendingQueryCopies; + public PipelineFull(VulkanGraphicsDevice gd, Device device) : base(gd, device) { _activeQueries = new List(); + _pendingQueryCopies = new(); CommandBuffer = (Cbs = gd.CommandBufferPool.Rent()).CommandBuffer; } + private void CopyPendingQuery() + { + foreach (var item in _pendingQueryCopies) + { + var buffer = item.Holder.GetBuffer(CommandBuffer, true).Get(Cbs, 0, sizeof(long)).Value; + + Gd.Api.CmdCopyQueryPoolResults( + CommandBuffer, + item.Pool, + 0, + 1, + buffer, + 0, + sizeof(long), + QueryResultFlags.QueryResult64Bit | QueryResultFlags.QueryResultWaitBit); + } + + _pendingQueryCopies.Clear(); + } + protected override unsafe DescriptorSetLayout[] CreateDescriptorSetLayouts(VulkanGraphicsDevice gd, Device device, out PipelineLayout layout) { DescriptorSetLayoutBinding* uLayoutBindings = stackalloc DescriptorSetLayoutBinding[Constants.MaxUniformBufferBindings]; @@ -298,19 +321,7 @@ namespace Ryujinx.Graphics.Vulkan public void CopyQueryResults(QueryPool pool, BufferHolder holder) { - EndRenderPass(); - - var buffer = holder.GetBuffer(CommandBuffer, true).Get(Cbs, 0, sizeof(long)).Value; - - Gd.Api.CmdCopyQueryPoolResults( - CommandBuffer, - pool, - 0, - 1, - buffer, - 0, - sizeof(long), - QueryResultFlags.QueryResult64Bit | QueryResultFlags.QueryResultWaitBit); + _pendingQueryCopies.Add((pool, holder)); _hasPendingQuery = true; } @@ -319,5 +330,10 @@ namespace Ryujinx.Graphics.Vulkan { FlushPendingQuery(); } + + protected override void SignalRenderPassEnd() + { + CopyPendingQuery(); + } } }