From de1338cbbc6e334315ed4c53bfa6e382e32b20e1 Mon Sep 17 00:00:00 2001 From: Stenzek Date: Fri, 8 Mar 2024 14:16:52 +1000 Subject: [PATCH] VulkanDevice: Add additional semaphore on swap chain We don't actually need +1 semaphores, or, more than one really. But, the validation layer gets cranky if we don't fence wait before the next image acquire. So, add an additional semaphore to ensure that we're never acquiring before fence waiting. --- src/util/vulkan_device.cpp | 9 ++++----- src/util/vulkan_device.h | 2 +- src/util/vulkan_swap_chain.cpp | 10 +++++++--- 3 files changed, 12 insertions(+), 9 deletions(-) diff --git a/src/util/vulkan_device.cpp b/src/util/vulkan_device.cpp index db86e5e70..326846819 100644 --- a/src/util/vulkan_device.cpp +++ b/src/util/vulkan_device.cpp @@ -1272,7 +1272,7 @@ void VulkanDevice::SubmitCommandBuffer(VulkanSwapChain* present_swap_chain /* = { DoSubmitCommandBuffer(m_current_frame, present_swap_chain); if (present_swap_chain) - DoPresent(present_swap_chain, false); + DoPresent(present_swap_chain); return; } @@ -1317,7 +1317,7 @@ void VulkanDevice::DoSubmitCommandBuffer(u32 index, VulkanSwapChain* present_swa } } -void VulkanDevice::DoPresent(VulkanSwapChain* present_swap_chain, bool acquire_next) +void VulkanDevice::DoPresent(VulkanSwapChain* present_swap_chain) { const VkPresentInfoKHR present_info = {VK_STRUCTURE_TYPE_PRESENT_INFO_KHR, nullptr, @@ -1344,8 +1344,7 @@ void VulkanDevice::DoPresent(VulkanSwapChain* present_swap_chain, bool acquire_n // Grab the next image as soon as possible, that way we spend less time blocked on the next // submission. Don't care if it fails, we'll deal with that at the presentation call site. // Credit to dxvk for the idea. - if (acquire_next) - present_swap_chain->AcquireNextImage(); + present_swap_chain->AcquireNextImage(); } void VulkanDevice::WaitForPresentComplete() @@ -1379,7 +1378,7 @@ void VulkanDevice::PresentThread() DoSubmitCommandBuffer(m_queued_present.command_buffer_index, m_queued_present.swap_chain); if (m_queued_present.swap_chain) - DoPresent(m_queued_present.swap_chain, true); + DoPresent(m_queued_present.swap_chain); m_present_done.store(true, std::memory_order_release); m_present_done_cv.notify_one(); } diff --git a/src/util/vulkan_device.h b/src/util/vulkan_device.h index cef3c54fb..38517b5e4 100644 --- a/src/util/vulkan_device.h +++ b/src/util/vulkan_device.h @@ -379,7 +379,7 @@ private: void WaitForCommandBufferCompletion(u32 index); void DoSubmitCommandBuffer(u32 index, VulkanSwapChain* present_swap_chain); - void DoPresent(VulkanSwapChain* present_swap_chain, bool acquire_next); + void DoPresent(VulkanSwapChain* present_swap_chain); void WaitForPresentComplete(std::unique_lock& lock); void PresentThread(); void StartPresentThread(); diff --git a/src/util/vulkan_swap_chain.cpp b/src/util/vulkan_swap_chain.cpp index 81c302a07..78af7250e 100644 --- a/src/util/vulkan_swap_chain.cpp +++ b/src/util/vulkan_swap_chain.cpp @@ -534,9 +534,13 @@ bool VulkanSwapChain::CreateSwapChain() m_images.push_back(image); } - m_semaphores.reserve(image_count); - m_current_semaphore = (image_count - 1); - for (u32 i = 0; i < image_count; i++) + // We don't actually need +1 semaphores, or, more than one really. + // But, the validation layer gets cranky if we don't fence wait before the next image acquire. + // So, add an additional semaphore to ensure that we're never acquiring before fence waiting. + const u32 semaphore_count = image_count + 1; + m_semaphores.reserve(semaphore_count); + m_current_semaphore = 0; + for (u32 i = 0; i < semaphore_count; i++) { ImageSemaphores sema;