[PATCH vkd3d 3/3] tests: Add test for custom PRESENT state transitions.

Józef Kucia joseph.kucia at gmail.com
Thu Mar 29 11:21:48 CDT 2018


From: Józef Kucia <jkucia at codeweavers.com>

Signed-off-by: Józef Kucia <jkucia at codeweavers.com>
---
 tests/vkd3d_api.c | 228 +++++++++++++++++++++++++++++++++++++++++++++++-------
 1 file changed, 198 insertions(+), 30 deletions(-)

diff --git a/tests/vkd3d_api.c b/tests/vkd3d_api.c
index abef8675a7ac..4b3466edc919 100644
--- a/tests/vkd3d_api.c
+++ b/tests/vkd3d_api.c
@@ -24,6 +24,23 @@
 #include "vkd3d_test.h"
 #include <vkd3d.h>
 
+#include "vkd3d_d3d12_test.h"
+
+HRESULT WINAPI D3D12SerializeRootSignature(const D3D12_ROOT_SIGNATURE_DESC *root_signature_desc,
+        D3D_ROOT_SIGNATURE_VERSION version, ID3DBlob **blob, ID3DBlob **error_blob)
+{
+    return vkd3d_serialize_root_signature(root_signature_desc, version, blob, error_blob);
+}
+
+static void wait_queue_idle_(unsigned int line, ID3D12Device *device, ID3D12CommandQueue *queue)
+{
+    VkQueue vk_queue;
+
+    vk_queue = vkd3d_acquire_vk_queue(queue);
+    vkQueueWaitIdle(vk_queue);
+    vkd3d_release_vk_queue(queue);
+}
+
 static ULONG get_refcount(void *iface)
 {
     IUnknown *unk = iface;
@@ -82,36 +99,6 @@ static ID3D12CommandQueue *create_command_queue(ID3D12Device *device,
     return queue;
 }
 
-static ID3D12Resource *create_buffer(ID3D12Device *device, D3D12_HEAP_TYPE heap_type,
-        size_t size, D3D12_RESOURCE_FLAGS resource_flags, D3D12_RESOURCE_STATES initial_resource_state)
-{
-    D3D12_HEAP_PROPERTIES heap_properties;
-    D3D12_RESOURCE_DESC resource_desc;
-    ID3D12Resource *buffer;
-    HRESULT hr;
-
-    memset(&heap_properties, 0, sizeof(heap_properties));
-    heap_properties.Type = heap_type;
-
-    resource_desc.Dimension = D3D12_RESOURCE_DIMENSION_BUFFER;
-    resource_desc.Alignment = 0;
-    resource_desc.Width = size;
-    resource_desc.Height = 1;
-    resource_desc.DepthOrArraySize = 1;
-    resource_desc.MipLevels = 1;
-    resource_desc.Format = DXGI_FORMAT_UNKNOWN;
-    resource_desc.SampleDesc.Count = 1;
-    resource_desc.SampleDesc.Quality = 0;
-    resource_desc.Layout = D3D12_TEXTURE_LAYOUT_ROW_MAJOR;
-    resource_desc.Flags = resource_flags;
-
-    hr = ID3D12Device_CreateCommittedResource(device, &heap_properties,
-            D3D12_HEAP_FLAG_NONE, &resource_desc, initial_resource_state,
-            NULL, &IID_ID3D12Resource, (void **)&buffer);
-    ok(hr == S_OK, "Failed to create buffer, hr %#x.\n", hr);
-    return buffer;
-}
-
 static void test_create_instance(void)
 {
     struct vkd3d_instance_create_info create_info;
@@ -730,6 +717,186 @@ static void test_resource_internal_refcount(void)
     ok(!refcount, "Device has %u references left.\n", refcount);
 }
 
+static VkImage create_vulkan_image(ID3D12Device *device,
+        unsigned int width, unsigned int height, VkFormat vk_format, VkImageUsageFlags usage)
+{
+    VkImageCreateInfo image_info;
+    VkDevice vk_device;
+    VkImage vk_image;
+    VkResult vr;
+
+    vk_device = vkd3d_get_vk_device(device);
+
+    image_info.sType = VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO;
+    image_info.pNext = NULL;
+    image_info.imageType = VK_IMAGE_TYPE_2D;
+    image_info.format = vk_format;
+    image_info.extent.width = width;
+    image_info.extent.height = height;
+    image_info.extent.depth = 1;
+    image_info.arrayLayers = 1;
+    image_info.mipLevels = 1;
+    image_info.samples = VK_SAMPLE_COUNT_1_BIT;
+    image_info.tiling = VK_IMAGE_TILING_OPTIMAL;
+    image_info.usage = VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT;
+    image_info.usage |= usage;
+    image_info.flags = 0;
+    image_info.sharingMode = VK_SHARING_MODE_EXCLUSIVE;
+    image_info.queueFamilyIndexCount = 0;
+    image_info.pQueueFamilyIndices = NULL;
+    image_info.initialLayout = VK_IMAGE_LAYOUT_UNDEFINED;
+
+    vr = vkCreateImage(vk_device, &image_info, NULL, &vk_image);
+    ok(vr == VK_SUCCESS, "Failed to create image, vr %d.\n", vr);
+
+    return vk_image;
+}
+
+static unsigned int select_vulkan_memory_type(ID3D12Device *device,
+        uint32_t memory_type_mask, VkMemoryPropertyFlags required_flags)
+{
+    VkPhysicalDeviceMemoryProperties memory_info;
+    VkPhysicalDevice vk_physical_device;
+    unsigned int i;
+
+    vk_physical_device = vkd3d_get_vk_physical_device(device);
+
+    vkGetPhysicalDeviceMemoryProperties(vk_physical_device, &memory_info);
+
+    for (i = 0; i < memory_info.memoryTypeCount; ++i)
+    {
+        if (!(memory_type_mask & (1u << i)))
+            continue;
+        if ((memory_info.memoryTypes[i].propertyFlags & required_flags) == required_flags)
+            return i;
+    }
+
+    return ~0u;
+}
+
+static VkDeviceMemory allocate_vulkan_device_memory(ID3D12Device *device,
+        VkMemoryPropertyFlags required_flags, const VkMemoryRequirements *memory_requirements)
+{
+    VkMemoryAllocateInfo allocate_info;
+    VkDeviceMemory vk_memory;
+    VkDevice vk_device;
+    VkResult vr;
+
+    vk_device = vkd3d_get_vk_device(device);
+
+    allocate_info.sType = VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO;
+    allocate_info.pNext = NULL;
+    allocate_info.allocationSize = memory_requirements->size;
+    allocate_info.memoryTypeIndex = select_vulkan_memory_type(device,
+            memory_requirements->memoryTypeBits, required_flags);
+    ok(allocate_info.memoryTypeIndex != ~0u, "Failed to find memory type.\n");
+
+    vr = vkAllocateMemory(vk_device, &allocate_info, NULL, &vk_memory);
+    ok(vr == VK_SUCCESS, "Got unexpected VkResult %d.\n", vr);
+
+    return vk_memory;
+}
+
+static VkDeviceMemory allocate_vulkan_image_memory(ID3D12Device *device,
+        VkMemoryPropertyFlags required_flags, VkImage vk_image)
+{
+    VkMemoryRequirements memory_requirements;
+    VkDeviceMemory vk_memory;
+    VkDevice vk_device;
+    VkResult vr;
+
+    vk_device = vkd3d_get_vk_device(device);
+
+    vkGetImageMemoryRequirements(vk_device, vk_image, &memory_requirements);
+    vk_memory = allocate_vulkan_device_memory(device, required_flags, &memory_requirements);
+
+    vr = vkBindImageMemory(vk_device, vk_image, vk_memory, 0);
+    ok(vr == VK_SUCCESS, "Got unexpected VkResult %d.\n", vr);
+
+    return vk_memory;
+}
+
+static void test_vulkan_resource_present_state(void)
+{
+    static const float white[] = {1.0f, 1.0f, 1.0f, 1.0f};
+
+    struct vkd3d_image_resource_create_info resource_create_info;
+    ID3D12GraphicsCommandList *command_list;
+    ID3D12Resource *vk_resource, *resource;
+    D3D12_CPU_DESCRIPTOR_HANDLE rtv;
+    struct test_context_desc desc;
+    struct test_context context;
+    ID3D12CommandQueue *queue;
+    VkDeviceMemory vk_memory;
+    ID3D12Device *device;
+    VkDevice vk_device;
+    VkImage vk_image;
+    HRESULT hr;
+
+    memset(&desc, 0, sizeof(desc));
+    desc.rt_width = desc.rt_height = 32;
+    if (!init_test_context(&context, &desc))
+        return;
+    device = context.device;
+    command_list = context.list;
+    queue = context.queue;
+
+    resource = create_default_texture(device, 32, 32, DXGI_FORMAT_R8G8B8A8_UNORM,
+            D3D12_RESOURCE_FLAG_NONE, D3D12_RESOURCE_STATE_COPY_DEST);
+
+    vk_image = create_vulkan_image(device, 32, 32,
+            VK_FORMAT_R8G8B8A8_UNORM, VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT);
+    vk_memory = allocate_vulkan_image_memory(device,
+            VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT, vk_image);
+
+    resource_create_info.vk_image = vk_image;
+    resource_create_info.desc.Dimension = D3D12_RESOURCE_DIMENSION_TEXTURE2D;
+    resource_create_info.desc.Alignment = 0;
+    resource_create_info.desc.Width = 32;
+    resource_create_info.desc.Height = 32;
+    resource_create_info.desc.DepthOrArraySize = 1;
+    resource_create_info.desc.MipLevels = 1;
+    resource_create_info.desc.Format = DXGI_FORMAT_R8G8B8A8_UNORM;
+    resource_create_info.desc.SampleDesc.Count = 1;
+    resource_create_info.desc.SampleDesc.Quality = 0;
+    resource_create_info.desc.Layout = D3D12_TEXTURE_LAYOUT_UNKNOWN;
+    resource_create_info.desc.Flags = D3D12_RESOURCE_FLAG_ALLOW_RENDER_TARGET;
+    resource_create_info.flags = VKD3D_RESOURCE_INITIAL_STATE_TRANSITION | VKD3D_RESOURCE_PRESENT_STATE_TRANSITION;
+    resource_create_info.present_state = D3D12_RESOURCE_STATE_COPY_SOURCE;
+    hr = vkd3d_create_image_resource(device, &resource_create_info, &vk_resource);
+    ok(hr == S_OK, "Failed to create D3D12 resource for Vulkan image, hr %#x.\n", hr);
+
+    rtv = get_cpu_descriptor_handle(&context, context.rtv_heap, 0);
+    ID3D12Device_CreateRenderTargetView(device, vk_resource, NULL, rtv);
+
+    transition_resource_state(command_list, vk_resource,
+            D3D12_RESOURCE_STATE_PRESENT, D3D12_RESOURCE_STATE_RENDER_TARGET);
+
+    ID3D12GraphicsCommandList_ClearRenderTargetView(command_list, rtv, white, 0, NULL);
+    ID3D12GraphicsCommandList_OMSetRenderTargets(command_list, 1, &rtv, FALSE, NULL);
+    ID3D12GraphicsCommandList_SetGraphicsRootSignature(command_list, context.root_signature);
+    ID3D12GraphicsCommandList_SetPipelineState(command_list, context.pipeline_state);
+    ID3D12GraphicsCommandList_IASetPrimitiveTopology(command_list, D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST);
+    ID3D12GraphicsCommandList_RSSetViewports(command_list, 1, &context.viewport);
+    ID3D12GraphicsCommandList_RSSetScissorRects(command_list, 1, &context.scissor_rect);
+    ID3D12GraphicsCommandList_DrawInstanced(command_list, 3, 1, 0, 0);
+
+    transition_resource_state(command_list, vk_resource,
+            D3D12_RESOURCE_STATE_RENDER_TARGET, D3D12_RESOURCE_STATE_PRESENT);
+    ID3D12GraphicsCommandList_CopyResource(command_list, resource, vk_resource);
+    transition_resource_state(command_list, resource,
+            D3D12_RESOURCE_STATE_COPY_DEST, D3D12_RESOURCE_STATE_COPY_SOURCE);
+
+    check_sub_resource_uint(resource, 0, queue, command_list, 0xff00ff00, 0);
+
+    ID3D12Resource_Release(vk_resource);
+    vk_device = vkd3d_get_vk_device(device);
+    vkDestroyImage(vk_device, vk_image, NULL);
+    vkFreeMemory(vk_device, vk_memory, NULL);
+    ID3D12Resource_Release(resource);
+    destroy_test_context(&context);
+}
+
 static bool have_d3d12_device(void)
 {
     ID3D12Device *device;
@@ -757,4 +924,5 @@ START_TEST(vkd3d_api)
     run_test(test_device_parent);
     run_test(test_vkd3d_queue);
     run_test(test_resource_internal_refcount);
+    run_test(test_vulkan_resource_present_state);
 }
-- 
2.16.1




More information about the wine-devel mailing list