wined3d: Prevent buildup of retired buffer objects' memory.

Submit current command buffer in wined3d_context_vk_get_command_buffer()
and return a new one if the total size of retired buffer objects on that
command buffer crosses a predefined threshold.

One way this issue may arise is when an application, by repeatedly doing
resource updates, does not trigger a flush of the command buffer and
accumulates transient staging buffers.

Signed-off-by: Jan Sikorski <jsikorski@codeweavers.com>
Signed-off-by: Henri Verbeet <hverbeet@codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
Jan Sikorski 2021-04-20 17:21:05 +02:00 committed by Alexandre Julliard
parent 77319190d1
commit d71358f5e9
2 changed files with 14 additions and 3 deletions

View File

@ -921,6 +921,9 @@ void wined3d_context_vk_destroy_bo(struct wined3d_context_vk *context_vk, const
if (bo->map_ptr) if (bo->map_ptr)
VK_CALL(vkUnmapMemory(device_vk->vk_device, bo->vk_memory)); VK_CALL(vkUnmapMemory(device_vk->vk_device, bo->vk_memory));
wined3d_context_vk_destroy_vk_memory(context_vk, bo->vk_memory, bo->command_buffer_id); wined3d_context_vk_destroy_vk_memory(context_vk, bo->vk_memory, bo->command_buffer_id);
if (bo->command_buffer_id == context_vk->current_command_buffer.id)
context_vk->retired_bo_size += bo->size;
} }
void wined3d_context_vk_poll_command_buffers(struct wined3d_context_vk *context_vk) void wined3d_context_vk_poll_command_buffers(struct wined3d_context_vk *context_vk)
@ -1509,9 +1512,14 @@ VkCommandBuffer wined3d_context_vk_get_command_buffer(struct wined3d_context_vk
buffer = &context_vk->current_command_buffer; buffer = &context_vk->current_command_buffer;
if (buffer->vk_command_buffer) if (buffer->vk_command_buffer)
{ {
TRACE("Returning existing command buffer %p with id 0x%s.\n", if (context_vk->retired_bo_size > WINED3D_RETIRED_BO_SIZE_THRESHOLD)
buffer->vk_command_buffer, wine_dbgstr_longlong(buffer->id)); wined3d_context_vk_submit_command_buffer(context_vk, 0, NULL, NULL, 0, NULL);
return buffer->vk_command_buffer; else
{
TRACE("Returning existing command buffer %p with id 0x%s.\n",
buffer->vk_command_buffer, wine_dbgstr_longlong(buffer->id));
return buffer->vk_command_buffer;
}
} }
command_buffer_info.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_ALLOCATE_INFO; command_buffer_info.sType = VK_STRUCTURE_TYPE_COMMAND_BUFFER_ALLOCATE_INFO;
@ -1628,6 +1636,7 @@ void wined3d_context_vk_submit_command_buffer(struct wined3d_context_vk *context
context_vk->completed_command_buffer_id = 0; context_vk->completed_command_buffer_id = 0;
buffer->id = 1; buffer->id = 1;
} }
context_vk->retired_bo_size = 0;
wined3d_context_vk_cleanup_resources(context_vk); wined3d_context_vk_cleanup_resources(context_vk);
} }

View File

@ -2549,6 +2549,7 @@ struct wined3d_context_vk
VkCommandPool vk_command_pool; VkCommandPool vk_command_pool;
struct wined3d_command_buffer_vk current_command_buffer; struct wined3d_command_buffer_vk current_command_buffer;
uint64_t completed_command_buffer_id; uint64_t completed_command_buffer_id;
VkDeviceSize retired_bo_size;
struct struct
{ {
@ -3921,6 +3922,7 @@ struct wined3d_null_views_vk
#define WINED3D_ALLOCATOR_CHUNK_ORDER_COUNT 15 #define WINED3D_ALLOCATOR_CHUNK_ORDER_COUNT 15
#define WINED3D_ALLOCATOR_MIN_BLOCK_SIZE (WINED3D_ALLOCATOR_CHUNK_SIZE >> (WINED3D_ALLOCATOR_CHUNK_ORDER_COUNT - 1)) #define WINED3D_ALLOCATOR_MIN_BLOCK_SIZE (WINED3D_ALLOCATOR_CHUNK_SIZE >> (WINED3D_ALLOCATOR_CHUNK_ORDER_COUNT - 1))
#define WINED3D_SLAB_BO_MIN_OBJECT_ALIGN 16 #define WINED3D_SLAB_BO_MIN_OBJECT_ALIGN 16
#define WINED3D_RETIRED_BO_SIZE_THRESHOLD (64 * 1024 * 1024)
struct wined3d_allocator_chunk struct wined3d_allocator_chunk
{ {