Signed-off-by: Nikolay Sivov <nsivov(a)codeweavers.com>
---
v2: handle surface creation failure on some systems.
dlls/dxgi/tests/dxgi.c | 78 +++++++++++++++++++++++++++++++++++++++++-
dlls/dxgi/utils.c | 4 ++-
2 files changed, 80 insertions(+), 2 deletions(-)
diff --git a/dlls/dxgi/tests/dxgi.c b/dlls/dxgi/tests/dxgi.c
index f04cd2be06..c33b9981f9 100644
--- a/dlls/dxgi/tests/dxgi.c
+++ b/dlls/dxgi/tests/dxgi.c
@@ -44,6 +44,10 @@ static NTSTATUS (WINAPI *pD3DKMTCheckVidPnExclusiveOwnership)(const D3DKMT_CHECK
static NTSTATUS (WINAPI *pD3DKMTCloseAdapter)(const D3DKMT_CLOSEADAPTER *desc);
static NTSTATUS (WINAPI *pD3DKMTOpenAdapterFromGdiDisplayName)(D3DKMT_OPENADAPTERFROMGDIDISPLAYNAME *desc);
+static HRESULT (WINAPI *pD3D11CreateDevice)(IDXGIAdapter *adapter, D3D_DRIVER_TYPE driver_type, HMODULE swrast, UINT flags,
+ const D3D_FEATURE_LEVEL *feature_levels, UINT levels, UINT sdk_version, ID3D11Device **device_out,
+ D3D_FEATURE_LEVEL *obtained_feature_level, ID3D11DeviceContext **immediate_context);
+
static PFN_D3D12_CREATE_DEVICE pD3D12CreateDevice;
static PFN_D3D12_GET_DEBUG_INTERFACE pD3D12GetDebugInterface;
@@ -624,6 +628,40 @@ success:
return dxgi_device;
}
+static IDXGIDevice *create_d3d11_device(void)
+{
+ static const D3D_FEATURE_LEVEL feature_level[] =
+ {
+ D3D_FEATURE_LEVEL_11_0,
+ D3D_FEATURE_LEVEL_10_1,
+ D3D_FEATURE_LEVEL_10_0,
+ };
+ unsigned int feature_level_count = ARRAY_SIZE(feature_level);
+ ID3D11Device *d3d_device;
+ IDXGIDevice *device = NULL;
+ HRESULT hr;
+
+ if (!pD3D11CreateDevice)
+ return NULL;
+
+ hr = pD3D11CreateDevice(NULL, D3D_DRIVER_TYPE_HARDWARE, NULL, 0, feature_level, feature_level_count,
+ D3D11_SDK_VERSION, &d3d_device, NULL, NULL);
+ if (FAILED(hr))
+ hr = pD3D11CreateDevice(NULL, D3D_DRIVER_TYPE_WARP, NULL, 0, feature_level, feature_level_count,
+ D3D11_SDK_VERSION, &d3d_device, NULL, NULL);
+ if (FAILED(hr))
+ hr = pD3D11CreateDevice(NULL, D3D_DRIVER_TYPE_REFERENCE, NULL, 0, feature_level, feature_level_count,
+ D3D11_SDK_VERSION, &d3d_device, NULL, NULL);
+
+ if (SUCCEEDED(hr))
+ {
+ hr = ID3D11Device_QueryInterface(d3d_device, &IID_IDXGIDevice, (void **)&device);
+ ID3D11Device_Release(d3d_device);
+ }
+
+ return device;
+}
+
static ID3D12Device *create_d3d12_device(void)
{
IDXGIAdapter *adapter;
@@ -1079,6 +1117,7 @@ static void test_check_interface_support(void)
static void test_create_surface(void)
{
+ ID3D11Texture2D *texture2d;
DXGI_SURFACE_DESC desc;
IDXGISurface *surface;
IDXGIDevice *device;
@@ -1109,6 +1148,40 @@ static void test_create_surface(void)
IDXGISurface_Release(surface);
refcount = IDXGIDevice_Release(device);
ok(!refcount, "Device has %u references left.\n", refcount);
+
+ /* DXGI_USAGE_UNORDERED_ACCESS */
+ if (!(device = create_d3d11_device()))
+ {
+ skip("Failed to create D3D11 device.\n");
+ return;
+ }
+
+ surface = NULL;
+ hr = IDXGIDevice_CreateSurface(device, &desc, 1, DXGI_USAGE_UNORDERED_ACCESS, NULL, &surface);
+ ok(SUCCEEDED(hr) || broken(hr == E_INVALIDARG), "Failed to create a dxgi surface, hr %#x\n", hr);
+
+ if (surface)
+ {
+ ID3D11UnorderedAccessView *uav;
+ ID3D11Device *d3d_device;
+
+ hr = IDXGISurface_QueryInterface(surface, &IID_ID3D11Texture2D, (void **)&texture2d);
+ ok(hr == S_OK, "Failed to get texture interface, hr %#x.\n", hr);
+
+ ID3D11Texture2D_GetDevice(texture2d, &d3d_device);
+
+ hr = ID3D11Device_CreateUnorderedAccessView(d3d_device, (ID3D11Resource *)texture2d, NULL, &uav);
+ ok(hr == S_OK, "Failed to create unordered access view, hr %#x.\n", hr);
+ ID3D11UnorderedAccessView_Release(uav);
+
+ ID3D11Device_Release(d3d_device);
+ ID3D11Texture2D_Release(texture2d);
+
+ IDXGISurface_Release(surface);
+ }
+
+ refcount = IDXGIDevice_Release(device);
+ ok(!refcount, "Device has %u references left.\n", refcount);
}
static void test_parents(void)
@@ -6483,7 +6556,7 @@ static void run_on_d3d12(void (*test_func)(IUnknown *device, BOOL is_d3d12))
START_TEST(dxgi)
{
- HMODULE dxgi_module, d3d12_module, gdi32_module;
+ HMODULE dxgi_module, d3d11_module, d3d12_module, gdi32_module;
BOOL enable_debug_layer = FALSE;
unsigned int argc, i;
ID3D12Debug *debug;
@@ -6498,6 +6571,9 @@ START_TEST(dxgi)
pD3DKMTCloseAdapter = (void *)GetProcAddress(gdi32_module, "D3DKMTCloseAdapter");
pD3DKMTOpenAdapterFromGdiDisplayName = (void *)GetProcAddress(gdi32_module, "D3DKMTOpenAdapterFromGdiDisplayName");
+ d3d11_module = LoadLibraryA("d3d11.dll");
+ pD3D11CreateDevice = (void *)GetProcAddress(d3d11_module, "D3D11CreateDevice");
+
registry_mode.dmSize = sizeof(registry_mode);
ok(EnumDisplaySettingsW(NULL, ENUM_REGISTRY_SETTINGS, ®istry_mode), "Failed to get display mode.\n");
diff --git a/dlls/dxgi/utils.c b/dlls/dxgi/utils.c
index aece3a6af1..a32c7ee129 100644
--- a/dlls/dxgi/utils.c
+++ b/dlls/dxgi/utils.c
@@ -503,8 +503,10 @@ unsigned int wined3d_bind_flags_from_dxgi_usage(DXGI_USAGE dxgi_usage)
wined3d_bind_flags |= WINED3D_BIND_SHADER_RESOURCE;
if (dxgi_usage & DXGI_USAGE_RENDER_TARGET_OUTPUT)
wined3d_bind_flags |= WINED3D_BIND_RENDER_TARGET;
+ if (dxgi_usage & DXGI_USAGE_UNORDERED_ACCESS)
+ wined3d_bind_flags |= WINED3D_BIND_UNORDERED_ACCESS;
- dxgi_usage &= ~(DXGI_USAGE_SHADER_INPUT | DXGI_USAGE_RENDER_TARGET_OUTPUT);
+ dxgi_usage &= ~(DXGI_USAGE_SHADER_INPUT | DXGI_USAGE_RENDER_TARGET_OUTPUT | DXGI_USAGE_UNORDERED_ACCESS);
if (dxgi_usage)
FIXME("Unhandled DXGI usage %#x.\n", dxgi_usage);
return wined3d_bind_flags;
--
2.26.2