diff --git a/Ryujinx.Graphics.Gpu/Memory/BufferCache.cs b/Ryujinx.Graphics.Gpu/Memory/BufferCache.cs
index 63d221508..14b177aa4 100644
--- a/Ryujinx.Graphics.Gpu/Memory/BufferCache.cs
+++ b/Ryujinx.Graphics.Gpu/Memory/BufferCache.cs
@@ -17,6 +17,8 @@ namespace Ryujinx.Graphics.Gpu.Memory
         private const ulong BufferAlignmentSize = 0x1000;
         private const ulong BufferAlignmentMask = BufferAlignmentSize - 1;
 
+        private const ulong MaxDynamicGrowthSize = 0x100000;
+
         private readonly GpuContext _context;
         private readonly PhysicalMemory _physicalMemory;
 
@@ -166,10 +168,35 @@ namespace Ryujinx.Graphics.Gpu.Memory
                 // Otherwise, we must delete the overlapping buffers and create a bigger buffer
                 // that fits all the data we need. We also need to copy the contents from the
                 // old buffer(s) to the new buffer.
+
                 ulong endAddress = address + size;
 
                 if (_bufferOverlaps[0].Address > address || _bufferOverlaps[0].EndAddress < endAddress)
                 {
+                    // Check if the following conditions are met:
+                    // - We have a single overlap.
+                    // - The overlap starts at or before the requested range. That is, the overlap happens at the end.
+                    // - The size delta between the new, merged buffer and the old one is of at most 2 pages.
+                    // In this case, we attempt to extend the buffer further than the requested range,
+                    // this can potentially avoid future resizes if the application keeps using overlapping
+                    // sequential memory.
+                    // Allowing for 2 pages (rather than just one) is necessary to catch cases where the
+                    // range crosses a page, and after alignment, ends having a size of 2 pages.
+                    if (overlapsCount == 1 &&
+                        address >= _bufferOverlaps[0].Address &&
+                        endAddress - _bufferOverlaps[0].EndAddress <= BufferAlignmentSize * 2)
+                    {
+                        // Try to grow the buffer by 1.5x of its current size.
+                        // This improves performance in the cases where the buffer is resized often by small amounts.
+                        ulong existingSize = _bufferOverlaps[0].Size;
+                        ulong growthSize = (existingSize + Math.Min(existingSize >> 1, MaxDynamicGrowthSize)) & ~BufferAlignmentMask;
+
+                        size = Math.Max(size, growthSize);
+                        endAddress = address + size;
+
+                        overlapsCount = _buffers.FindOverlapsNonOverlapping(address, size, ref _bufferOverlaps);
+                    }
+
                     for (int index = 0; index < overlapsCount; index++)
                     {
                         Buffer buffer = _bufferOverlaps[index];
@@ -183,7 +210,9 @@ namespace Ryujinx.Graphics.Gpu.Memory
                         }
                     }
 
-                    Buffer newBuffer = new Buffer(_context, _physicalMemory, address, endAddress - address, _bufferOverlaps.Take(overlapsCount));
+                    ulong newSize = endAddress - address;
+
+                    Buffer newBuffer = new Buffer(_context, _physicalMemory, address, newSize, _bufferOverlaps.Take(overlapsCount));
 
                     lock (_buffers)
                     {
@@ -202,7 +231,7 @@ namespace Ryujinx.Graphics.Gpu.Memory
                         buffer.DisposeData();
                     }
 
-                    newBuffer.SynchronizeMemory(address, endAddress - address);
+                    newBuffer.SynchronizeMemory(address, newSize);
 
                     // Existing buffers were modified, we need to rebind everything.
                     NotifyBuffersModified?.Invoke();