[PATCH 3/4] wined3d: Avoid the pipeline barrier when mapping buffer objects backing textures.
Jan Sikorski
jsikorski at codeweavers.com
Thu Sep 2 08:14:22 CDT 2021
Signed-off-by: Jan Sikorski <jsikorski at codeweavers.com>
---
dlls/wined3d/adapter_vk.c | 43 +++++++++++++++++++---------------
dlls/wined3d/context_vk.c | 2 ++
dlls/wined3d/texture.c | 3 +++
dlls/wined3d/wined3d_private.h | 1 +
4 files changed, 30 insertions(+), 19 deletions(-)
diff --git a/dlls/wined3d/adapter_vk.c b/dlls/wined3d/adapter_vk.c
index 1db25a4d72f..7342ebe3959 100644
--- a/dlls/wined3d/adapter_vk.c
+++ b/dlls/wined3d/adapter_vk.c
@@ -934,9 +934,11 @@ static void *adapter_vk_map_bo_address(struct wined3d_context *context,
{
if (wined3d_context_vk_create_bo(context_vk, bo->size, bo->usage, bo->memory_type, &tmp))
{
+ bool host_synced = bo->host_synced;
list_move_head(&tmp.users, &bo->users);
wined3d_context_vk_destroy_bo(context_vk, bo);
*bo = tmp;
+ bo->host_synced = host_synced;
list_init(&bo->users);
list_move_head(&bo->users, &tmp.users);
LIST_FOR_EACH_ENTRY(bo_user, &bo->users, struct wined3d_bo_user, entry)
@@ -952,25 +954,30 @@ static void *adapter_vk_map_bo_address(struct wined3d_context *context,
if (map_flags & WINED3D_MAP_READ)
{
- if (!(vk_command_buffer = wined3d_context_vk_get_command_buffer(context_vk)))
+ if (!bo->host_synced)
{
- ERR("Failed to get command buffer.\n");
- return NULL;
- }
-
- wined3d_context_vk_end_current_render_pass(context_vk);
+ if (!(vk_command_buffer = wined3d_context_vk_get_command_buffer(context_vk)))
+ {
+ ERR("Failed to get command buffer.\n");
+ return NULL;
+ }
- vk_barrier.sType = VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER;
- vk_barrier.pNext = NULL;
- vk_barrier.srcAccessMask = vk_access_mask_from_buffer_usage(bo->usage);
- vk_barrier.dstAccessMask = VK_ACCESS_HOST_READ_BIT;
- vk_barrier.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
- vk_barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
- vk_barrier.buffer = bo->vk_buffer;
- vk_barrier.offset = bo->buffer_offset + (uintptr_t)data->addr;
- vk_barrier.size = size;
- VK_CALL(vkCmdPipelineBarrier(vk_command_buffer, VK_PIPELINE_STAGE_ALL_COMMANDS_BIT,
- VK_PIPELINE_STAGE_HOST_BIT, 0, 0, NULL, 1, &vk_barrier, 0, NULL));
+ wined3d_context_vk_end_current_render_pass(context_vk);
+
+ vk_barrier.sType = VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER;
+ vk_barrier.pNext = NULL;
+ vk_barrier.srcAccessMask = vk_access_mask_from_buffer_usage(bo->usage);
+ vk_barrier.dstAccessMask = VK_ACCESS_HOST_READ_BIT;
+ vk_barrier.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
+ vk_barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
+ vk_barrier.buffer = bo->vk_buffer;
+ vk_barrier.offset = bo->buffer_offset + (uintptr_t)data->addr;
+ vk_barrier.size = size;
+ VK_CALL(vkCmdPipelineBarrier(vk_command_buffer, VK_PIPELINE_STAGE_ALL_COMMANDS_BIT,
+ VK_PIPELINE_STAGE_HOST_BIT, 0, 0, NULL, 1, &vk_barrier, 0, NULL));
+
+ wined3d_context_vk_reference_bo(context_vk, bo);
+ }
if (!(bo->memory_type & VK_MEMORY_PROPERTY_HOST_COHERENT_BIT))
{
@@ -981,8 +988,6 @@ static void *adapter_vk_map_bo_address(struct wined3d_context *context,
range.size = size;
VK_CALL(vkInvalidateMappedMemoryRanges(device_vk->vk_device, 1, &range));
}
-
- wined3d_context_vk_reference_bo(context_vk, bo);
}
if (bo->command_buffer_id == context_vk->current_command_buffer.id)
diff --git a/dlls/wined3d/context_vk.c b/dlls/wined3d/context_vk.c
index 8df416851f2..86e9306e301 100644
--- a/dlls/wined3d/context_vk.c
+++ b/dlls/wined3d/context_vk.c
@@ -415,6 +415,7 @@ static bool wined3d_context_vk_create_slab_bo(struct wined3d_context_vk *context
bo->size = size;
list_init(&bo->users);
bo->command_buffer_id = 0;
+ bo->host_synced = false;
TRACE("Using buffer 0x%s, memory 0x%s, offset 0x%s for bo %p.\n",
wine_dbgstr_longlong(bo->vk_buffer), wine_dbgstr_longlong(bo->vk_memory),
@@ -494,6 +495,7 @@ BOOL wined3d_context_vk_create_bo(struct wined3d_context_vk *context_vk, VkDevic
list_init(&bo->users);
bo->command_buffer_id = 0;
bo->slab = NULL;
+ bo->host_synced = false;
TRACE("Created buffer 0x%s, memory 0x%s for bo %p.\n",
wine_dbgstr_longlong(bo->vk_buffer), wine_dbgstr_longlong(bo->vk_memory), bo);
diff --git a/dlls/wined3d/texture.c b/dlls/wined3d/texture.c
index 49a8d4ead8b..2cf1a44a213 100644
--- a/dlls/wined3d/texture.c
+++ b/dlls/wined3d/texture.c
@@ -5200,6 +5200,9 @@ static BOOL wined3d_texture_vk_prepare_buffer_object(struct wined3d_texture_vk *
VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT, bo))
return FALSE;
+ /* Texture buffer objects receive a barrier to HOST_READ in wined3d_texture_vk_download_data(),
+ * so they don't need it when they are mapped for reading. */
+ bo->host_synced = true;
TRACE("Created buffer object %p for texture %p, sub-resource %u.\n", bo, texture_vk, sub_resource_idx);
return TRUE;
}
diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h
index dab19383b2d..4b7087a3807 100644
--- a/dlls/wined3d/wined3d_private.h
+++ b/dlls/wined3d/wined3d_private.h
@@ -1625,6 +1625,7 @@ struct wined3d_bo_vk
struct list users;
uint64_t command_buffer_id;
+ bool host_synced;
};
struct wined3d_bo_slab_vk_key
--
2.30.2
More information about the wine-devel
mailing list