From c8f9292babd5aa6021ce1bd6a977130baebb7de3 Mon Sep 17 00:00:00 2001 From: Emmanuel Hansen Date: Tue, 16 Aug 2022 16:32:37 +0000 Subject: Avalonia - Couple fixes and improvements to vulkan (#3483) * drop split devices, rebase * add fallback to opengl if vulkan is not available * addressed review * ensure present image references are incremented and decremented when necessary * allow changing vsync for vulkan * fix screenshot on avalonia vulkan * save favorite when toggled * improve sync between popups * use separate devices for each new window * fix crash when closing window * addressed review * don't create the main window with immediate mode * change skia vk delegate to method * update vulkan throwonerror * addressed review --- .../Ui/Backend/Vulkan/VulkanCommandBufferPool.cs | 51 ++++++++++++++++++---- 1 file changed, 42 insertions(+), 9 deletions(-) (limited to 'Ryujinx.Ava/Ui/Backend/Vulkan/VulkanCommandBufferPool.cs') diff --git a/Ryujinx.Ava/Ui/Backend/Vulkan/VulkanCommandBufferPool.cs b/Ryujinx.Ava/Ui/Backend/Vulkan/VulkanCommandBufferPool.cs index 240035ca..a00ecf2b 100644 --- a/Ryujinx.Ava/Ui/Backend/Vulkan/VulkanCommandBufferPool.cs +++ b/Ryujinx.Ava/Ui/Backend/Vulkan/VulkanCommandBufferPool.cs @@ -10,6 +10,7 @@ namespace Ryujinx.Ava.Ui.Vulkan private readonly CommandPool _commandPool; private readonly List _usedCommandBuffers = new(); + private readonly object _lock = new object(); public unsafe VulkanCommandBufferPool(VulkanDevice device, VulkanPhysicalDevice physicalDevice) { @@ -36,9 +37,12 @@ namespace Ryujinx.Ava.Ui.Vulkan Level = CommandBufferLevel.Primary }; - _device.Api.AllocateCommandBuffers(_device.InternalHandle, commandBufferAllocateInfo, out var commandBuffer); + lock (_lock) + { + _device.Api.AllocateCommandBuffers(_device.InternalHandle, commandBufferAllocateInfo, out var commandBuffer); - return commandBuffer; + return commandBuffer; + } } public VulkanCommandBuffer CreateCommandBuffer() @@ -48,7 +52,7 @@ namespace Ryujinx.Ava.Ui.Vulkan public void FreeUsedCommandBuffers() { - lock (_usedCommandBuffers) + lock (_lock) { foreach (var usedCommandBuffer in _usedCommandBuffers) { @@ -61,7 +65,7 @@ namespace Ryujinx.Ava.Ui.Vulkan private void DisposeCommandBuffer(VulkanCommandBuffer commandBuffer) { - lock (_usedCommandBuffers) + lock (_lock) { _usedCommandBuffers.Add(commandBuffer); } @@ -69,8 +73,11 @@ namespace Ryujinx.Ava.Ui.Vulkan public void Dispose() { - FreeUsedCommandBuffers(); - _device.Api.DestroyCommandPool(_device.InternalHandle, _commandPool, Span.Empty); + lock (_lock) + { + FreeUsedCommandBuffers(); + _device.Api.DestroyCommandPool(_device.InternalHandle, _commandPool, Span.Empty); + } } public class VulkanCommandBuffer : IDisposable @@ -80,6 +87,8 @@ namespace Ryujinx.Ava.Ui.Vulkan private readonly Fence _fence; private bool _hasEnded; private bool _hasStarted; + private bool _isDisposed; + private object _lock = new object(); public IntPtr Handle => InternalHandle.Handle; @@ -101,6 +110,22 @@ namespace Ryujinx.Ava.Ui.Vulkan device.Api.CreateFence(device.InternalHandle, fenceCreateInfo, null, out _fence); } + public void WaitForFence() + { + if (_isDisposed) + { + return; + } + + lock (_lock) + { + if (!_isDisposed) + { + _device.Api.WaitForFences(_device.InternalHandle, 1, _fence, true, ulong.MaxValue); + } + } + } + public void BeginRecording() { if (!_hasStarted) @@ -173,9 +198,17 @@ namespace Ryujinx.Ava.Ui.Vulkan public void Dispose() { - _device.Api.WaitForFences(_device.InternalHandle, 1, _fence, true, ulong.MaxValue); - _device.Api.FreeCommandBuffers(_device.InternalHandle, _commandBufferPool._commandPool, 1, InternalHandle); - _device.Api.DestroyFence(_device.InternalHandle, _fence, Span.Empty); + lock (_lock) + { + if (!_isDisposed) + { + _isDisposed = true; + + _device.Api.WaitForFences(_device.InternalHandle, 1, _fence, true, ulong.MaxValue); + _device.Api.FreeCommandBuffers(_device.InternalHandle, _commandBufferPool._commandPool, 1, InternalHandle); + _device.Api.DestroyFence(_device.InternalHandle, _fence, Span.Empty); + } + } } } } -- cgit v1.2.3