diff --git a/src/Ryujinx.Graphics.Vulkan/StagingBuffer.cs b/src/Ryujinx.Graphics.Vulkan/StagingBuffer.cs
index 32ec8c7c6d..3a02a28dca 100644
--- a/src/Ryujinx.Graphics.Vulkan/StagingBuffer.cs
+++ b/src/Ryujinx.Graphics.Vulkan/StagingBuffer.cs
@@ -246,7 +246,7 @@ namespace Ryujinx.Graphics.Vulkan
             return true;
         }
 
-        private void FreeCompleted()
+        public void FreeCompleted()
         {
             FenceHolder signalledFence = null;
             while (_pendingCopies.TryPeek(out var pc) && (pc.Fence == signalledFence || pc.Fence.IsSignaled()))
diff --git a/src/Ryujinx.Graphics.Vulkan/VulkanRenderer.cs b/src/Ryujinx.Graphics.Vulkan/VulkanRenderer.cs
index 3383d728ba..7848bc8779 100644
--- a/src/Ryujinx.Graphics.Vulkan/VulkanRenderer.cs
+++ b/src/Ryujinx.Graphics.Vulkan/VulkanRenderer.cs
@@ -475,6 +475,9 @@ namespace Ryujinx.Graphics.Vulkan
         internal void RegisterFlush()
         {
             SyncManager.RegisterFlush();
+
+            // Periodically free unused regions of the staging buffer to avoid doing it all at once.
+            BufferManager.StagingBuffer.FreeCompleted();
         }
 
         public PinnedSpan<byte> GetBufferData(BufferHandle buffer, int offset, int size)