[PATCH vkd3d 10/13] vkd3d: Re-implement ClearUnorderedAccessViewUint.
Philip Rebohle
philip.rebohle at tu-dortmund.de
Mon Nov 11 10:03:45 CST 2019
Addresses the following limitations of the previous implementation:
- Only R32_{UINT,TYPELESS} were supported for buffers.
- Clearing an image UAV did not behave correctly for images with non-UINT formats.
- Due to the use of transfer operations, extra memory barriers were needed.
If necessary, this will create a temporary view with a bit-compatible
UINT format for the resource in order to perform a bit-exact clear.
Signed-off-by: Philip Rebohle <philip.rebohle at tu-dortmund.de>
---
libs/vkd3d/command.c | 113 ++++++++++++++++---------------------------
1 file changed, 41 insertions(+), 72 deletions(-)
diff --git a/libs/vkd3d/command.c b/libs/vkd3d/command.c
index 3648ea4..e5fe0ad 100644
--- a/libs/vkd3d/command.c
+++ b/libs/vkd3d/command.c
@@ -4930,96 +4930,65 @@ static void STDMETHODCALLTYPE d3d12_command_list_ClearUnorderedAccessViewUint(ID
const UINT values[4], UINT rect_count, const D3D12_RECT *rects)
{
struct d3d12_command_list *list = impl_from_ID3D12GraphicsCommandList1(iface);
- const struct vkd3d_vk_device_procs *vk_procs;
- const struct vkd3d_vulkan_info *vk_info;
- const struct d3d12_desc *cpu_descriptor;
+ struct vkd3d_view *base_view, *uint_view;
+ struct vkd3d_texture_view_desc view_desc;
+ const struct vkd3d_format *uint_format;
struct d3d12_resource *resource_impl;
- VkBufferMemoryBarrier buffer_barrier;
- VkImageMemoryBarrier image_barrier;
- VkPipelineStageFlags stage_mask;
- VkImageSubresourceRange range;
VkClearColorValue color;
TRACE("iface %p, gpu_handle %#"PRIx64", cpu_handle %lx, resource %p, values %p, rect_count %u, rects %p.\n",
iface, gpu_handle.ptr, cpu_handle.ptr, resource, values, rect_count, rects);
- vk_procs = &list->device->vk_procs;
- vk_info = &list->device->vk_info;
+ memcpy(color.uint32, values, sizeof(color.uint32));
resource_impl = unsafe_impl_from_ID3D12Resource(resource);
- d3d12_command_list_track_resource_usage(list, resource_impl);
+ base_view = d3d12_desc_from_cpu_handle(cpu_handle)->u.view;
+ uint_view = NULL;
- if (rect_count)
+ if (base_view->format->type != VKD3D_FORMAT_TYPE_UINT)
{
- FIXME("Clear rects not supported.\n");
- return;
- }
-
- d3d12_command_list_end_current_render_pass(list);
+ uint_format = vkd3d_find_uint_format(list->device, base_view->format->dxgi_format);
- cpu_descriptor = d3d12_desc_from_cpu_handle(cpu_handle);
-
- if (d3d12_resource_is_buffer(resource_impl))
- {
- if (cpu_descriptor->u.view->format->vk_format != VK_FORMAT_R32_UINT)
+ if (!uint_format)
{
- FIXME("Not supported for UAV descriptor %p.\n", cpu_descriptor);
+ ERR("Unhandled format %d.\n", base_view->format->dxgi_format);
return;
}
- VK_CALL(vkCmdFillBuffer(list->vk_command_buffer, resource_impl->u.vk_buffer,
- cpu_descriptor->u.view->info.buffer.offset, cpu_descriptor->u.view->info.buffer.size, values[0]));
-
- buffer_barrier.sType = VK_STRUCTURE_TYPE_BUFFER_MEMORY_BARRIER;
- buffer_barrier.pNext = NULL;
- buffer_barrier.srcAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
- buffer_barrier.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
- buffer_barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
- buffer_barrier.buffer = resource_impl->u.vk_buffer;
- buffer_barrier.offset = cpu_descriptor->u.view->info.buffer.offset;
- buffer_barrier.size = cpu_descriptor->u.view->info.buffer.size;
-
- vk_barrier_parameters_from_d3d12_resource_state(D3D12_RESOURCE_STATE_UNORDERED_ACCESS, 0,
- resource_impl, list->vk_queue_flags, vk_info, &buffer_barrier.dstAccessMask, &stage_mask, NULL);
-
- VK_CALL(vkCmdPipelineBarrier(list->vk_command_buffer,
- VK_PIPELINE_STAGE_TRANSFER_BIT, stage_mask, 0,
- 0, NULL, 1, &buffer_barrier, 0, NULL));
+ if (d3d12_resource_is_texture(resource_impl))
+ {
+ memset(&view_desc, 0, sizeof(view_desc));
+ view_desc.view_type = base_view->info.texture.vk_view_type;
+ view_desc.format = uint_format;
+ view_desc.miplevel_idx = base_view->info.texture.miplevel_idx;
+ view_desc.miplevel_count = 1;
+ view_desc.layer_idx = base_view->info.texture.layer_idx;
+ view_desc.layer_count = base_view->info.texture.layer_count;
+ view_desc.allowed_swizzle = false;
+
+ if (!vkd3d_create_texture_view(list->device, resource_impl->u.vk_image, &view_desc, &uint_view))
+ {
+ ERR("Failed to create image view.\n");
+ return;
+ }
+ }
+ else
+ {
+ if (!vkd3d_create_buffer_view(list->device, resource_impl->u.vk_buffer, uint_format,
+ base_view->info.buffer.offset, base_view->info.buffer.size, &uint_view))
+ {
+ ERR("Failed to create buffer view.\n");
+ return;
+ }
+ }
}
- else
- {
- color.uint32[0] = values[0];
- color.uint32[1] = values[1];
- color.uint32[2] = values[2];
- color.uint32[3] = values[3];
-
- range.aspectMask = cpu_descriptor->u.view->format->vk_aspect_mask;
- range.baseMipLevel = cpu_descriptor->u.view->info.texture.miplevel_idx;
- range.levelCount = 1;
- range.baseArrayLayer = cpu_descriptor->u.view->info.texture.layer_idx;
- range.layerCount = cpu_descriptor->u.view->info.texture.layer_count;
-
- VK_CALL(vkCmdClearColorImage(list->vk_command_buffer,
- resource_impl->u.vk_image, VK_IMAGE_LAYOUT_GENERAL, &color, 1, &range));
-
- image_barrier.sType = VK_STRUCTURE_TYPE_IMAGE_MEMORY_BARRIER;
- image_barrier.pNext = NULL;
- image_barrier.srcAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT;
- image_barrier.oldLayout = VK_IMAGE_LAYOUT_GENERAL;
- image_barrier.newLayout = VK_IMAGE_LAYOUT_GENERAL;
- image_barrier.srcQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
- image_barrier.dstQueueFamilyIndex = VK_QUEUE_FAMILY_IGNORED;
- image_barrier.image = resource_impl->u.vk_image;
- image_barrier.subresourceRange = range;
-
- vk_barrier_parameters_from_d3d12_resource_state(D3D12_RESOURCE_STATE_UNORDERED_ACCESS, 0,
- resource_impl, list->vk_queue_flags, vk_info, &image_barrier.dstAccessMask, &stage_mask, NULL);
- VK_CALL(vkCmdPipelineBarrier(list->vk_command_buffer,
- VK_PIPELINE_STAGE_TRANSFER_BIT, stage_mask, 0,
- 0, NULL, 0, NULL, 1, &image_barrier));
- }
+ d3d12_command_list_clear_unordered_access_view(list, resource_impl,
+ uint_view ? uint_view : base_view, &color, rect_count, rects);
+
+ if (uint_view)
+ vkd3d_view_decref(uint_view, list->device);
}
static void STDMETHODCALLTYPE d3d12_command_list_ClearUnorderedAccessViewFloat(ID3D12GraphicsCommandList1 *iface,
--
2.24.0
More information about the wine-devel
mailing list