Latte+Vulkan: Code cleanup

Besides a general cleanup:
- Remove deprecated resource destruction queues
- Move functionality from renderer into Latte base classes to deduplicate code
This commit is contained in:
Exzap 2024-03-14 01:04:05 +01:00
parent bc04662525
commit 193767e6cc
23 changed files with 115 additions and 269 deletions

View file

@ -44,9 +44,9 @@ CachedFBOVk::~CachedFBOVk()
while (!m_usedByPipelines.empty())
delete m_usedByPipelines[0];
auto vkr = VulkanRenderer::GetInstance();
vkr->releaseDestructibleObject(m_vkrObjFramebuffer);
vkr->ReleaseDestructibleObject(m_vkrObjFramebuffer);
m_vkrObjFramebuffer = nullptr;
vkr->releaseDestructibleObject(m_vkrObjRenderPass);
vkr->ReleaseDestructibleObject(m_vkrObjRenderPass);
m_vkrObjRenderPass = nullptr;
}

View file

@ -79,14 +79,14 @@ LatteTextureViewVk::~LatteTextureViewVk()
delete list_descriptorSets[0];
if (m_smallCacheView0)
VulkanRenderer::GetInstance()->releaseDestructibleObject(m_smallCacheView0);
VulkanRenderer::GetInstance()->ReleaseDestructibleObject(m_smallCacheView0);
if (m_smallCacheView1)
VulkanRenderer::GetInstance()->releaseDestructibleObject(m_smallCacheView1);
VulkanRenderer::GetInstance()->ReleaseDestructibleObject(m_smallCacheView1);
if (m_fallbackCache)
{
for (auto& itr : *m_fallbackCache)
VulkanRenderer::GetInstance()->releaseDestructibleObject(itr.second);
VulkanRenderer::GetInstance()->ReleaseDestructibleObject(itr.second);
delete m_fallbackCache;
m_fallbackCache = nullptr;
}

View file

@ -46,7 +46,7 @@ LatteTextureVk::LatteTextureVk(class VulkanRenderer* vkRenderer, Latte::E_DIM di
VulkanRenderer::FormatInfoVK texFormatInfo;
vkRenderer->GetTextureFormatInfoVK(format, isDepth, dim, effectiveBaseWidth, effectiveBaseHeight, &texFormatInfo);
hasStencil = (texFormatInfo.vkImageAspect & VK_IMAGE_ASPECT_STENCIL_BIT) != 0;
cemu_assert_debug(hasStencil == ((texFormatInfo.vkImageAspect & VK_IMAGE_ASPECT_STENCIL_BIT) != 0));
imageInfo.format = texFormatInfo.vkImageFormat;
vkObjTex->m_imageAspect = texFormatInfo.vkImageAspect;
@ -117,7 +117,7 @@ LatteTextureVk::~LatteTextureVk()
m_vkr->surfaceCopy_notifyTextureRelease(this);
VulkanRenderer::GetInstance()->releaseDestructibleObject(vkObjTex);
VulkanRenderer::GetInstance()->ReleaseDestructibleObject(vkObjTex);
vkObjTex = nullptr;
}
@ -130,12 +130,8 @@ LatteTextureView* LatteTextureVk::CreateView(Latte::E_DIM dim, Latte::E_GX2SURFF
return new LatteTextureViewVk(m_vkr->GetLogicalDevice(), this, dim, format, firstMip, mipCount, firstSlice, sliceCount);
}
void LatteTextureVk::setAllocation(struct VkImageMemAllocation* memAllocation)
void LatteTextureVk::AllocateOnHost()
{
vkObjTex->m_allocation = memAllocation;
}
struct VkImageMemAllocation* LatteTextureVk::getAllocation() const
{
return vkObjTex->m_allocation;
auto allocationInfo = VulkanRenderer::GetInstance()->GetMemoryManager()->imageMemoryAllocate(GetImageObj()->m_image);
vkObjTex->m_allocation = allocationInfo;
}

View file

@ -14,14 +14,13 @@ public:
~LatteTextureVk();
void AllocateOnHost() override;
VKRObjectTexture* GetImageObj() const { return vkObjTex; };
VkFormat GetFormat() const { return vkObjTex->m_format; }
VkImageAspectFlags GetImageAspect() const { return vkObjTex->m_imageAspect; }
void setAllocation(struct VkImageMemAllocation* memAllocation);
struct VkImageMemAllocation* getAllocation() const;
VkImageLayout GetImageLayout(VkImageSubresource& subresource)
{
cemu_assert_debug(subresource.mipLevel < m_layoutsMips);

View file

@ -207,7 +207,8 @@ RendererShaderVk::RendererShaderVk(ShaderType type, uint64 baseHash, uint64 auxH
RendererShaderVk::~RendererShaderVk()
{
VulkanRenderer::GetInstance()->destroyShader(this);
while (!list_pipelineInfo.empty())
delete list_pipelineInfo[0];
}
void RendererShaderVk::Init()

View file

@ -84,7 +84,7 @@ PipelineInfo::~PipelineInfo()
// queue pipeline for destruction
if (m_vkrObjPipeline)
{
VulkanRenderer::GetInstance()->releaseDestructibleObject(m_vkrObjPipeline);
VulkanRenderer::GetInstance()->ReleaseDestructibleObject(m_vkrObjPipeline);
m_vkrObjPipeline = nullptr;
}

View file

@ -300,7 +300,7 @@ void VulkanPipelineStableCache::LoadPipelineFromCache(std::span<uint8> fileData)
delete pipelineInfo;
delete lcr;
delete cachedPipeline;
VulkanRenderer::GetInstance()->releaseDestructibleObject(renderPass);
VulkanRenderer::GetInstance()->ReleaseDestructibleObject(renderPass);
s_spinlockSharedInternal.unlock();
}

View file

@ -1803,44 +1803,6 @@ void VulkanRenderer::PreparePresentationFrame(bool mainWindow)
AcquireNextSwapchainImage(mainWindow);
}
void VulkanRenderer::ProcessDestructionQueues(size_t commandBufferIndex)
{
auto& current_descriptor_cache = m_destructionQueues.m_cmd_descriptor_set_objects[commandBufferIndex];
if (!current_descriptor_cache.empty())
{
assert_dbg();
//for (const auto& descriptor : current_descriptor_cache)
//{
// vkFreeDescriptorSets(m_logicalDevice, m_descriptorPool, 1, &descriptor);
// performanceMonitor.vk.numDescriptorSets.decrement();
//}
current_descriptor_cache.clear();
}
// destroy buffers
for (auto& itr : m_destructionQueues.m_buffers[commandBufferIndex])
vkDestroyBuffer(m_logicalDevice, itr, nullptr);
m_destructionQueues.m_buffers[commandBufferIndex].clear();
// destroy device memory objects
for (auto& itr : m_destructionQueues.m_memory[commandBufferIndex])
vkFreeMemory(m_logicalDevice, itr, nullptr);
m_destructionQueues.m_memory[commandBufferIndex].clear();
// destroy image views
for (auto& itr : m_destructionQueues.m_cmd_image_views[commandBufferIndex])
vkDestroyImageView(m_logicalDevice, itr, nullptr);
m_destructionQueues.m_cmd_image_views[commandBufferIndex].clear();
// destroy host textures
for (auto itr : m_destructionQueues.m_host_textures[commandBufferIndex])
delete itr;
m_destructionQueues.m_host_textures[commandBufferIndex].clear();
ProcessDestructionQueue2();
}
void VulkanRenderer::InitFirstCommandBuffer()
{
cemu_assert_debug(m_state.currentCommandBuffer == nullptr);
@ -1869,7 +1831,7 @@ void VulkanRenderer::ProcessFinishedCommandBuffers()
VkResult fenceStatus = vkGetFenceStatus(m_logicalDevice, m_cmd_buffer_fences[m_commandBufferSyncIndex]);
if (fenceStatus == VK_SUCCESS)
{
ProcessDestructionQueues(m_commandBufferSyncIndex);
ProcessDestructionQueue();
m_commandBufferSyncIndex = (m_commandBufferSyncIndex + 1) % m_commandBuffers.size();
memoryManager->cleanupBuffers(m_countCommandBufferFinished);
m_countCommandBufferFinished++;
@ -3035,48 +2997,7 @@ TextureDecoder* VulkanRenderer::texture_chooseDecodedFormat(Latte::E_GX2SURFFMT
return texFormatInfo.decoder;
}
void VulkanRenderer::texture_reserveTextureOnGPU(LatteTexture* hostTexture)
{
LatteTextureVk* vkTexture = (LatteTextureVk*)hostTexture;
auto allocationInfo = memoryManager->imageMemoryAllocate(vkTexture->GetImageObj()->m_image);
vkTexture->setAllocation(allocationInfo);
}
void VulkanRenderer::texture_destroy(LatteTexture* hostTexture)
{
LatteTextureVk* texVk = (LatteTextureVk*)hostTexture;
delete texVk;
}
void VulkanRenderer::destroyViewDepr(VkImageView imageView)
{
cemu_assert_debug(false);
m_destructionQueues.m_cmd_image_views[m_commandBufferIndex].emplace_back(imageView);
}
void VulkanRenderer::destroyBuffer(VkBuffer buffer)
{
m_destructionQueues.m_buffers[m_commandBufferIndex].emplace_back(buffer);
}
void VulkanRenderer::destroyDeviceMemory(VkDeviceMemory mem)
{
m_destructionQueues.m_memory[m_commandBufferIndex].emplace_back(mem);
}
void VulkanRenderer::destroyPipelineInfo(PipelineInfo* pipelineInfo)
{
cemu_assert_debug(false);
}
void VulkanRenderer::destroyShader(RendererShaderVk* shader)
{
while (!shader->list_pipelineInfo.empty())
delete shader->list_pipelineInfo[0];
}
void VulkanRenderer::releaseDestructibleObject(VKRDestructibleObject* destructibleObject)
void VulkanRenderer::ReleaseDestructibleObject(VKRDestructibleObject* destructibleObject)
{
// destroy immediately if possible
if (destructibleObject->canDestroy())
@ -3090,7 +3011,7 @@ void VulkanRenderer::releaseDestructibleObject(VKRDestructibleObject* destructib
m_spinlockDestructionQueue.unlock();
}
void VulkanRenderer::ProcessDestructionQueue2()
void VulkanRenderer::ProcessDestructionQueue()
{
m_spinlockDestructionQueue.lock();
for (auto it = m_destructionQueue.begin(); it != m_destructionQueue.end();)
@ -3139,7 +3060,7 @@ VkDescriptorSetInfo::~VkDescriptorSetInfo()
performanceMonitor.vk.numDescriptorDynUniformBuffers.decrement(statsNumDynUniformBuffers);
performanceMonitor.vk.numDescriptorStorageBuffers.decrement(statsNumStorageBuffers);
VulkanRenderer::GetInstance()->releaseDestructibleObject(m_vkObjDescriptorSet);
VulkanRenderer::GetInstance()->ReleaseDestructibleObject(m_vkObjDescriptorSet);
m_vkObjDescriptorSet = nullptr;
}

View file

@ -231,7 +231,6 @@ public:
void DrawEmptyFrame(bool mainWindow) override;
void PreparePresentationFrame(bool mainWindow);
void ProcessDestructionQueues(size_t commandBufferIndex);
void InitFirstCommandBuffer();
void ProcessFinishedCommandBuffers();
void WaitForNextFinishedCommandBuffer();
@ -244,15 +243,9 @@ public:
bool HasCommandBufferFinished(uint64 commandBufferId) const;
void WaitCommandBufferFinished(uint64 commandBufferId);
// clean up (deprecated)
void destroyViewDepr(VkImageView imageView);
void destroyBuffer(VkBuffer buffer);
void destroyDeviceMemory(VkDeviceMemory mem);
void destroyPipelineInfo(PipelineInfo* pipelineInfo);
void destroyShader(RendererShaderVk* shader);
// clean up (new)
void releaseDestructibleObject(VKRDestructibleObject* destructibleObject);
void ProcessDestructionQueue2();
// resource destruction queue
void ReleaseDestructibleObject(VKRDestructibleObject* destructibleObject);
void ProcessDestructionQueue();
FSpinlock m_spinlockDestructionQueue;
std::vector<VKRDestructibleObject*> m_destructionQueue;
@ -290,9 +283,6 @@ public:
TextureDecoder* texture_chooseDecodedFormat(Latte::E_GX2SURFFMT format, bool isDepth, Latte::E_DIM dim, uint32 width, uint32 height) override;
void texture_reserveTextureOnGPU(LatteTexture* hostTexture) override;
void texture_destroy(LatteTexture* hostTexture) override;
void texture_clearSlice(LatteTexture* hostTexture, sint32 sliceIndex, sint32 mipIndex) override;
void texture_clearColorSlice(LatteTexture* hostTexture, sint32 sliceIndex, sint32 mipIndex, float r, float g, float b, float a) override;
void texture_clearDepthSlice(LatteTexture* hostTexture, uint32 sliceIndex, sint32 mipIndex, bool clearDepth, bool clearStencil, float depthValue, uint32 stencilValue) override;
@ -634,15 +624,6 @@ private:
// command buffer, garbage collection, synchronization
static constexpr uint32 kCommandBufferPoolSize = 128;
struct
{
std::array<std::vector<VkDescriptorSet>, kCommandBufferPoolSize> m_cmd_descriptor_set_objects;
std::array<std::vector<VkImageView>, kCommandBufferPoolSize> m_cmd_image_views;
std::array<std::vector<LatteTextureVk*>, kCommandBufferPoolSize> m_host_textures;
std::array<std::vector<VkBuffer>, kCommandBufferPoolSize> m_buffers;
std::array<std::vector<VkDeviceMemory>, kCommandBufferPoolSize> m_memory;
}m_destructionQueues;
size_t m_commandBufferIndex = 0; // current buffer being filled
size_t m_commandBufferSyncIndex = 0; // latest buffer that finished execution (updated on submit)
std::array<VkFence, kCommandBufferPoolSize> m_cmd_buffer_fences;

View file

@ -813,9 +813,9 @@ void VulkanRenderer::surfaceCopy_notifyTextureRelease(LatteTextureVk* hostTextur
{
if (p)
{
VulkanRenderer::GetInstance()->releaseDestructibleObject(p->vkObjDescriptorSet);
VulkanRenderer::GetInstance()->ReleaseDestructibleObject(p->vkObjDescriptorSet);
p->vkObjDescriptorSet = nullptr;
VulkanRenderer::GetInstance()->releaseDestructibleObject(p->vkObjImageView);
VulkanRenderer::GetInstance()->ReleaseDestructibleObject(p->vkObjImageView);
p->vkObjImageView = nullptr;
}
}
@ -829,9 +829,9 @@ void VulkanRenderer::surfaceCopy_notifyTextureRelease(LatteTextureVk* hostTextur
{
if (p)
{
VulkanRenderer::GetInstance()->releaseDestructibleObject(p->vkObjFramebuffer);
VulkanRenderer::GetInstance()->ReleaseDestructibleObject(p->vkObjFramebuffer);
p->vkObjFramebuffer = nullptr;
VulkanRenderer::GetInstance()->releaseDestructibleObject(p->vkObjImageView);
VulkanRenderer::GetInstance()->ReleaseDestructibleObject(p->vkObjImageView);
p->vkObjImageView = nullptr;
}
}