From 81fc2e6ab63def4af022db161455c3f16c3b9e3a Mon Sep 17 00:00:00 2001 From: Henri Verbeet Date: Mon, 7 Jun 2021 16:55:10 +0200 Subject: [PATCH] d3d11: Implement d3d11_device_context_ClearUnorderedAccessViewFloat(). Signed-off-by: Henri Verbeet Signed-off-by: Alexandre Julliard --- dlls/d3d11/device.c | 11 ++++++++++- dlls/d3d11/tests/d3d11.c | 26 +++++++++++--------------- dlls/wined3d/adapter_gl.c | 6 +++--- dlls/wined3d/adapter_vk.c | 6 +++--- dlls/wined3d/cs.c | 8 +++++--- dlls/wined3d/device.c | 16 +++++++++++++++- dlls/wined3d/directx.c | 4 ++-- dlls/wined3d/view.c | 18 ++++++++++++------ dlls/wined3d/wined3d.spec | 1 + dlls/wined3d/wined3d_private.h | 14 +++++++------- include/wine/wined3d.h | 2 ++ 11 files changed, 71 insertions(+), 41 deletions(-) diff --git a/dlls/d3d11/device.c b/dlls/d3d11/device.c index 7994da70591..d3e49879676 100644 --- a/dlls/d3d11/device.c +++ b/dlls/d3d11/device.c @@ -1447,8 +1447,17 @@ static void STDMETHODCALLTYPE d3d11_device_context_ClearUnorderedAccessViewUint( static void STDMETHODCALLTYPE d3d11_device_context_ClearUnorderedAccessViewFloat(ID3D11DeviceContext1 *iface, ID3D11UnorderedAccessView *unordered_access_view, const float values[4]) { - FIXME("iface %p, unordered_access_view %p, values %s stub!\n", + struct d3d11_device_context *context = impl_from_ID3D11DeviceContext1(iface); + struct d3d11_unordered_access_view *view; + + TRACE("iface %p, unordered_access_view %p, values %s.\n", iface, unordered_access_view, debug_float4(values)); + + view = unsafe_impl_from_ID3D11UnorderedAccessView(unordered_access_view); + wined3d_mutex_lock(); + wined3d_device_context_clear_uav_float(context->wined3d_context, + view->wined3d_view, (const struct wined3d_vec4 *)values); + wined3d_mutex_unlock(); } static void STDMETHODCALLTYPE d3d11_device_context_ClearDepthStencilView(ID3D11DeviceContext1 *iface, diff --git a/dlls/d3d11/tests/d3d11.c b/dlls/d3d11/tests/d3d11.c index f729a38b4c2..ae48e9748c9 100644 --- a/dlls/d3d11/tests/d3d11.c +++ b/dlls/d3d11/tests/d3d11.c @@ -16451,22 +16451,19 @@ static void test_clear_image_unordered_access_view(void) unsigned int expected; BOOL is_float; unsigned int clamped; - BOOL is_todo; } tests[] = { /* Test clearing a specific mip level. */ {DXGI_FORMAT_R32_FLOAT, 2, 1, 0, 0, 1, {1, 0, 0, 0}, 0x00000001}, {DXGI_FORMAT_R32_FLOAT, 2, 1, 1, 0, 1, {1, 0, 0, 0}, 0x00000001}, - {DXGI_FORMAT_R32_FLOAT, 2, 1, 0, 0, 1, {0x3f000000, 0, 0, 0}, 0x3f000000, TRUE, 0, TRUE}, - {DXGI_FORMAT_R32_FLOAT, 2, 1, 1, 0, 1, {0x3f000000, 0, 0, 0}, 0x3f000000, TRUE, 0, TRUE}, + {DXGI_FORMAT_R32_FLOAT, 2, 1, 0, 0, 1, {0x3f000000, 0, 0, 0}, 0x3f000000, TRUE}, + {DXGI_FORMAT_R32_FLOAT, 2, 1, 1, 0, 1, {0x3f000000, 0, 0, 0}, 0x3f000000, TRUE}, /* Test clearing specific array layers. */ {DXGI_FORMAT_R32_FLOAT, 1, IMAGE_SIZE, 0, 0, IMAGE_SIZE, {1, 0, 0, 0}, 0x00000001}, {DXGI_FORMAT_R32_FLOAT, 1, IMAGE_SIZE, 0, 3, 2, {1, 0, 0, 0}, 0x00000001}, - {DXGI_FORMAT_R32_FLOAT, 1, IMAGE_SIZE, 0, 0, IMAGE_SIZE, - {0x3f000000, 0, 0, 0}, 0x3f000000, TRUE, 0, TRUE}, - {DXGI_FORMAT_R32_FLOAT, 1, IMAGE_SIZE, 0, 3, 2, - {0x3f000000, 0, 0, 0}, 0x3f000000, TRUE, 0, TRUE}, + {DXGI_FORMAT_R32_FLOAT, 1, IMAGE_SIZE, 0, 0, IMAGE_SIZE, {0x3f000000, 0, 0, 0}, 0x3f000000, TRUE}, + {DXGI_FORMAT_R32_FLOAT, 1, IMAGE_SIZE, 0, 3, 2, {0x3f000000, 0, 0, 0}, 0x3f000000, TRUE}, /* Test uint clears with formats. */ {DXGI_FORMAT_R16G16_UINT, 1, 1, 0, 0, 1, {1, 2, 3, 4}, 0x00020001}, {DXGI_FORMAT_R16G16_UINT, 1, 1, 0, 0, 1, {0x12345, 0, 0, 0}, 0x00002345, FALSE, 0x0000ffff}, @@ -16478,16 +16475,16 @@ static void test_clear_image_unordered_access_view(void) {DXGI_FORMAT_R11G11B10_FLOAT, 1, 1, 0, 0, 1, {1, 2, 3, 4}, 0x00c01001}, /* Test float clears with formats. */ {DXGI_FORMAT_R16G16_UNORM, 1, 1, 0, 0, 1, - {0x3f000000 /* 0.5f */, 0x3f800000 /* 1.0f */, 0, 0}, 0xffff8000, TRUE, 0, TRUE}, + {0x3f000000 /* 0.5f */, 0x3f800000 /* 1.0f */, 0, 0}, 0xffff8000, TRUE}, {DXGI_FORMAT_R16G16_FLOAT, 1, 1, 0, 0, 1, - {0x3f000000 /* 0.5f */, 0x3f800000 /* 1.0f */, 0, 0}, 0x3c003800, TRUE, 0, TRUE}, + {0x3f000000 /* 0.5f */, 0x3f800000 /* 1.0f */, 0, 0}, 0x3c003800, TRUE}, {DXGI_FORMAT_R8G8B8A8_UNORM, 1, 1, 0, 0, 1, - {0x3f000000 /* 0.5f */, 0x3f800000 /* 1.0f */, 0, 0}, 0x0000ff80, TRUE, 0, TRUE}, + {0x3f000000 /* 0.5f */, 0x3f800000 /* 1.0f */, 0, 0}, 0x0000ff80, TRUE}, {DXGI_FORMAT_R8G8B8A8_UNORM, 1, 1, 0, 0, 1, - {0, 0, 0x3f000000 /* 0.5f */, 0x3f800000 /* 1.0f */}, 0xff800000, TRUE, 0, TRUE}, + {0, 0, 0x3f000000 /* 0.5f */, 0x3f800000 /* 1.0f */}, 0xff800000, TRUE}, {DXGI_FORMAT_R11G11B10_FLOAT, 1, 1, 0, 0, 1, {0x3f000000 /* 1.0f */, 0 /* 0.0f */, 0xbf800000 /* -1.0f */, 0x3f000000 /* 1.0f */}, - 0x00000380, TRUE, 0, TRUE}, + 0x00000380, TRUE}, }; static const struct @@ -16624,9 +16621,8 @@ static void test_clear_image_unordered_access_view(void) || broken(is_inside && !tests[i].is_float && is_small_float_format && !actual_colour))) break; } - todo_wine_if(tests[i].is_todo && expected_colour) - ok(success, "At layer %u, (%u,%u,%u), expected 0x%08x, got 0x%08x.\n", - layer, x, y, z, expected_colour, actual_colour); + ok(success, "At layer %u, (%u,%u,%u), expected 0x%08x, got 0x%08x.\n", + layer, x, y, z, expected_colour, actual_colour); release_resource_readback(&rb); } diff --git a/dlls/wined3d/adapter_gl.c b/dlls/wined3d/adapter_gl.c index f6ef04a5fbb..b014790af51 100644 --- a/dlls/wined3d/adapter_gl.c +++ b/dlls/wined3d/adapter_gl.c @@ -5015,12 +5015,12 @@ static void adapter_gl_flush_context(struct wined3d_context *context) } static void adapter_gl_clear_uav(struct wined3d_context *context, - struct wined3d_unordered_access_view *view, const struct wined3d_uvec4 *clear_value) + struct wined3d_unordered_access_view *view, const struct wined3d_uvec4 *clear_value, bool fp) { TRACE("context %p, view %p, clear_value %s.\n", context, view, debug_uvec4(clear_value)); - wined3d_unordered_access_view_gl_clear_uint(wined3d_unordered_access_view_gl(view), - clear_value, wined3d_context_gl(context)); + wined3d_unordered_access_view_gl_clear(wined3d_unordered_access_view_gl(view), + clear_value, wined3d_context_gl(context), fp); } static void adapter_gl_generate_mipmap(struct wined3d_context *context, struct wined3d_shader_resource_view *view) diff --git a/dlls/wined3d/adapter_vk.c b/dlls/wined3d/adapter_vk.c index 99d7547b834..9f36ee39080 100644 --- a/dlls/wined3d/adapter_vk.c +++ b/dlls/wined3d/adapter_vk.c @@ -1744,12 +1744,12 @@ static void adapter_vk_dispatch_compute(struct wined3d_device *device, } static void adapter_vk_clear_uav(struct wined3d_context *context, - struct wined3d_unordered_access_view *view, const struct wined3d_uvec4 *clear_value) + struct wined3d_unordered_access_view *view, const struct wined3d_uvec4 *clear_value, bool fp) { TRACE("context %p, view %p, clear_value %s.\n", context, view, debug_uvec4(clear_value)); - wined3d_unordered_access_view_vk_clear_uint(wined3d_unordered_access_view_vk(view), - clear_value, wined3d_context_vk(context)); + wined3d_unordered_access_view_vk_clear(wined3d_unordered_access_view_vk(view), + clear_value, wined3d_context_vk(context), fp); } static void adapter_vk_generate_mipmap(struct wined3d_context *context, struct wined3d_shader_resource_view *view) diff --git a/dlls/wined3d/cs.c b/dlls/wined3d/cs.c index 50a08334dab..544b76534d0 100644 --- a/dlls/wined3d/cs.c +++ b/dlls/wined3d/cs.c @@ -504,6 +504,7 @@ struct wined3d_cs_clear_unordered_access_view enum wined3d_cs_op opcode; struct wined3d_unordered_access_view *view; struct wined3d_uvec4 clear_value; + bool fp; }; struct wined3d_cs_copy_uav_counter @@ -2721,14 +2722,14 @@ static void wined3d_cs_exec_clear_unordered_access_view(struct wined3d_cs *cs, c struct wined3d_context *context; context = context_acquire(cs->c.device, NULL, 0); - cs->c.device->adapter->adapter_ops->adapter_clear_uav(context, view, &op->clear_value); + cs->c.device->adapter->adapter_ops->adapter_clear_uav(context, view, &op->clear_value, op->fp); context_release(context); wined3d_resource_release(view->resource); } -void wined3d_device_context_emit_clear_uav_uint(struct wined3d_device_context *context, - struct wined3d_unordered_access_view *view, const struct wined3d_uvec4 *clear_value) +void wined3d_device_context_emit_clear_uav(struct wined3d_device_context *context, + struct wined3d_unordered_access_view *view, const struct wined3d_uvec4 *clear_value, bool fp) { struct wined3d_cs_clear_unordered_access_view *op; @@ -2736,6 +2737,7 @@ void wined3d_device_context_emit_clear_uav_uint(struct wined3d_device_context *c op->opcode = WINED3D_CS_OP_CLEAR_UNORDERED_ACCESS_VIEW; op->view = view; op->clear_value = *clear_value; + op->fp = fp; wined3d_device_context_acquire_resource(context, view->resource); diff --git a/dlls/wined3d/device.c b/dlls/wined3d/device.c index 5092d8129b9..a11f137729f 100644 --- a/dlls/wined3d/device.c +++ b/dlls/wined3d/device.c @@ -4799,12 +4799,26 @@ HRESULT CDECL wined3d_device_context_clear_rendertarget_view(struct wined3d_devi return WINED3D_OK; } +void CDECL wined3d_device_context_clear_uav_float(struct wined3d_device_context *context, + struct wined3d_unordered_access_view *view, const struct wined3d_vec4 *clear_value) +{ + TRACE("context %p, view %p, clear_value %s.\n", context, view, debug_vec4(clear_value)); + + if (!(view->format->flags[WINED3D_GL_RES_TYPE_TEX_2D] & (WINED3DFMT_FLAG_FLOAT | WINED3DFMT_FLAG_NORMALISED))) + { + WARN("Not supported for view format %s.\n", debug_d3dformat(view->format->id)); + return; + } + + wined3d_device_context_emit_clear_uav(context, view, (const struct wined3d_uvec4 *)clear_value, true); +} + void CDECL wined3d_device_context_clear_uav_uint(struct wined3d_device_context *context, struct wined3d_unordered_access_view *view, const struct wined3d_uvec4 *clear_value) { TRACE("context %p, view %p, clear_value %s.\n", context, view, debug_uvec4(clear_value)); - wined3d_device_context_emit_clear_uav_uint(context, view, clear_value); + wined3d_device_context_emit_clear_uav(context, view, clear_value, false); } static unsigned int sanitise_map_flags(const struct wined3d_resource *resource, unsigned int flags) diff --git a/dlls/wined3d/directx.c b/dlls/wined3d/directx.c index be43d2ffb86..0e8a396a598 100644 --- a/dlls/wined3d/directx.c +++ b/dlls/wined3d/directx.c @@ -3046,9 +3046,9 @@ static void adapter_no3d_dispatch_compute(struct wined3d_device *device, } static void adapter_no3d_clear_uav(struct wined3d_context *context, - struct wined3d_unordered_access_view *view, const struct wined3d_uvec4 *clear_value) + struct wined3d_unordered_access_view *view, const struct wined3d_uvec4 *clear_value, bool fp) { - ERR("context %p, view %p, clear_value %s.\n", context, view, debug_uvec4(clear_value)); + ERR("context %p, view %p, clear_value %s, fp %#x.\n", context, view, debug_uvec4(clear_value), fp); } static const struct wined3d_adapter_ops wined3d_adapter_no3d_ops = diff --git a/dlls/wined3d/view.c b/dlls/wined3d/view.c index 2d2622e1191..cda16b690f8 100644 --- a/dlls/wined3d/view.c +++ b/dlls/wined3d/view.c @@ -1446,8 +1446,8 @@ void wined3d_unordered_access_view_invalidate_location(struct wined3d_unordered_ wined3d_view_invalidate_location(view->resource, &view->desc, location); } -void wined3d_unordered_access_view_gl_clear_uint(struct wined3d_unordered_access_view_gl *view_gl, - const struct wined3d_uvec4 *clear_value, struct wined3d_context_gl *context_gl) +void wined3d_unordered_access_view_gl_clear(struct wined3d_unordered_access_view_gl *view_gl, + const struct wined3d_uvec4 *clear_value, struct wined3d_context_gl *context_gl, bool fp) { const struct wined3d_gl_info *gl_info = context_gl->gl_info; const struct wined3d_format_gl *format_gl; @@ -1478,7 +1478,7 @@ void wined3d_unordered_access_view_gl_clear_uint(struct wined3d_unordered_access base_layer = view_gl->v.desc.u.texture.layer_idx; base_level = view_gl->v.desc.u.texture.level_idx; - if (format_gl->f.byte_count <= 4) + if (format_gl->f.byte_count <= 4 && !fp) { gl_format = format_gl->format; gl_type = format_gl->type; @@ -1552,6 +1552,12 @@ void wined3d_unordered_access_view_gl_clear_uint(struct wined3d_unordered_access return; } + if (fp) + { + FIXME("Floating-point buffer clears not implemented.\n"); + return; + } + buffer_gl = wined3d_buffer_gl(buffer_from_resource(resource)); wined3d_buffer_load_location(&buffer_gl->b, &context_gl->c, WINED3D_LOCATION_BUFFER); wined3d_unordered_access_view_invalidate_location(&view_gl->v, ~WINED3D_LOCATION_BUFFER); @@ -1700,8 +1706,8 @@ HRESULT wined3d_unordered_access_view_gl_init(struct wined3d_unordered_access_vi return hr; } -void wined3d_unordered_access_view_vk_clear_uint(struct wined3d_unordered_access_view_vk *view_vk, - const struct wined3d_uvec4 *clear_value, struct wined3d_context_vk *context_vk) +void wined3d_unordered_access_view_vk_clear(struct wined3d_unordered_access_view_vk *view_vk, + const struct wined3d_uvec4 *clear_value, struct wined3d_context_vk *context_vk, bool fp) { const struct wined3d_vk_info *vk_info; const struct wined3d_format *format; @@ -1712,7 +1718,7 @@ void wined3d_unordered_access_view_vk_clear_uint(struct wined3d_unordered_access VkAccessFlags access_mask; unsigned int offset, size; - TRACE("view_vk %p, clear_value %s, context_vk %p.\n", view_vk, debug_uvec4(clear_value), context_vk); + TRACE("view_vk %p, clear_value %s, context_vk %p, fp %#x.\n", view_vk, debug_uvec4(clear_value), context_vk, fp); resource = view_vk->v.resource; if (resource->type != WINED3D_RTYPE_BUFFER) diff --git a/dlls/wined3d/wined3d.spec b/dlls/wined3d/wined3d.spec index 7b0737386b7..11351b60a7f 100644 --- a/dlls/wined3d/wined3d.spec +++ b/dlls/wined3d/wined3d.spec @@ -87,6 +87,7 @@ @ cdecl wined3d_device_context_blt(ptr ptr long ptr ptr long ptr long ptr long) @ cdecl wined3d_device_context_clear_rendertarget_view(ptr ptr ptr long ptr float long) +@ cdecl wined3d_device_context_clear_uav_float(ptr ptr ptr) @ cdecl wined3d_device_context_clear_uav_uint(ptr ptr ptr) @ cdecl wined3d_device_context_copy_resource(ptr ptr ptr) @ cdecl wined3d_device_context_copy_sub_resource_region(ptr ptr long long long long ptr long ptr long) diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h index d08c523bd9f..4e3be01ed5a 100644 --- a/dlls/wined3d/wined3d_private.h +++ b/dlls/wined3d/wined3d_private.h @@ -3355,7 +3355,7 @@ struct wined3d_adapter_ops void (*adapter_dispatch_compute)(struct wined3d_device *device, const struct wined3d_state *state, const struct wined3d_dispatch_parameters *parameters); void (*adapter_clear_uav)(struct wined3d_context *context, - struct wined3d_unordered_access_view *view, const struct wined3d_uvec4 *clear_value); + struct wined3d_unordered_access_view *view, const struct wined3d_uvec4 *clear_value, bool fp); void (*adapter_generate_mipmap)(struct wined3d_context *context, struct wined3d_shader_resource_view *view); }; @@ -4735,8 +4735,8 @@ void wined3d_cs_emit_add_dirty_texture_region(struct wined3d_cs *cs, struct wined3d_texture *texture, unsigned int layer) DECLSPEC_HIDDEN; void wined3d_cs_emit_clear(struct wined3d_cs *cs, DWORD rect_count, const RECT *rects, DWORD flags, const struct wined3d_color *color, float depth, DWORD stencil) DECLSPEC_HIDDEN; -void wined3d_device_context_emit_clear_uav_uint(struct wined3d_device_context *context, - struct wined3d_unordered_access_view *view, const struct wined3d_uvec4 *clear_value) DECLSPEC_HIDDEN; +void wined3d_device_context_emit_clear_uav(struct wined3d_device_context *context, + struct wined3d_unordered_access_view *view, const struct wined3d_uvec4 *clear_value, bool fp) DECLSPEC_HIDDEN; void wined3d_cs_emit_preload_resource(struct wined3d_cs *cs, struct wined3d_resource *resource) DECLSPEC_HIDDEN; void wined3d_cs_emit_present(struct wined3d_cs *cs, struct wined3d_swapchain *swapchain, const RECT *src_rect, const RECT *dst_rect, HWND dst_window_override, unsigned int swap_interval, DWORD flags) DECLSPEC_HIDDEN; @@ -5168,8 +5168,8 @@ static inline struct wined3d_unordered_access_view_gl *wined3d_unordered_access_ return CONTAINING_RECORD(view, struct wined3d_unordered_access_view_gl, v); } -void wined3d_unordered_access_view_gl_clear_uint(struct wined3d_unordered_access_view_gl *view_gl, - const struct wined3d_uvec4 *clear_value, struct wined3d_context_gl *context_gl) DECLSPEC_HIDDEN; +void wined3d_unordered_access_view_gl_clear(struct wined3d_unordered_access_view_gl *view_gl, + const struct wined3d_uvec4 *clear_value, struct wined3d_context_gl *context_gl, bool fp) DECLSPEC_HIDDEN; HRESULT wined3d_unordered_access_view_gl_init(struct wined3d_unordered_access_view_gl *view_gl, const struct wined3d_view_desc *desc, struct wined3d_resource *resource, void *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN; @@ -5197,8 +5197,8 @@ static inline void wined3d_unordered_access_view_vk_barrier(struct wined3d_unord wined3d_resource_vk_barrier(uav_vk->v.resource, context_vk, bind_mask); } -void wined3d_unordered_access_view_vk_clear_uint(struct wined3d_unordered_access_view_vk *view_vk, - const struct wined3d_uvec4 *clear_value, struct wined3d_context_vk *context_vk) DECLSPEC_HIDDEN; +void wined3d_unordered_access_view_vk_clear(struct wined3d_unordered_access_view_vk *view_vk, + const struct wined3d_uvec4 *clear_value, struct wined3d_context_vk *context_vk, bool fp) DECLSPEC_HIDDEN; HRESULT wined3d_unordered_access_view_vk_init(struct wined3d_unordered_access_view_vk *view_vk, const struct wined3d_view_desc *desc, struct wined3d_resource *resource, void *parent, const struct wined3d_parent_ops *parent_ops) DECLSPEC_HIDDEN; diff --git a/include/wine/wined3d.h b/include/wine/wined3d.h index 7133280a724..53ae13b7df5 100644 --- a/include/wine/wined3d.h +++ b/include/wine/wined3d.h @@ -2422,6 +2422,8 @@ HRESULT __cdecl wined3d_device_context_blt(struct wined3d_device_context *contex HRESULT __cdecl wined3d_device_context_clear_rendertarget_view(struct wined3d_device_context *context, struct wined3d_rendertarget_view *view, const RECT *rect, unsigned int flags, const struct wined3d_color *color, float depth, unsigned int stencil); +void __cdecl wined3d_device_context_clear_uav_float(struct wined3d_device_context *context, + struct wined3d_unordered_access_view *view, const struct wined3d_vec4 *clear_value); void __cdecl wined3d_device_context_clear_uav_uint(struct wined3d_device_context *context, struct wined3d_unordered_access_view *view, const struct wined3d_uvec4 *clear_value); void __cdecl wined3d_device_context_copy_resource(struct wined3d_device_context *context, -- 2.11.4.GIT