diff --git a/dlls/d3d11/tests/d3d11.c b/dlls/d3d11/tests/d3d11.c index d1b09baa641..b690f94af92 100644 --- a/dlls/d3d11/tests/d3d11.c +++ b/dlls/d3d11/tests/d3d11.c @@ -27928,9 +27928,8 @@ static void test_format_compatibility(void) colour = get_readback_color(&rb, x, y, 0); expected = test_data[i].success && x >= texel_dwords && y ? bitmap_data[j - (4 + texel_dwords)] : initial_data[j]; - todo_wine_if(test_data[i].src_format == DXGI_FORMAT_R9G9B9E5_SHAREDEXP && expected) - ok(colour == expected, "Test %u: Got unexpected colour 0x%08x at (%u, %u), expected 0x%08x.\n", - i, colour, x, y, expected); + ok(colour == expected, "Test %u: Got unexpected colour 0x%08x at (%u, %u), expected 0x%08x.\n", + i, colour, x, y, expected); } release_resource_readback(&rb); @@ -27943,9 +27942,8 @@ static void test_format_compatibility(void) y = j / 4; colour = get_readback_color(&rb, x, y, 0); expected = test_data[i].success ? bitmap_data[j] : initial_data[j]; - todo_wine_if(test_data[i].src_format == DXGI_FORMAT_R9G9B9E5_SHAREDEXP && expected) - ok(colour == expected, "Test %u: Got unexpected colour 0x%08x at (%u, %u), expected 0x%08x.\n", - i, colour, x, y, expected); + ok(colour == expected, "Test %u: Got unexpected colour 0x%08x at (%u, %u), expected 0x%08x.\n", + i, colour, x, y, expected); } release_resource_readback(&rb); diff --git a/dlls/wined3d/device.c b/dlls/wined3d/device.c index feaef2ef18f..ac8d5d78b61 100644 --- a/dlls/wined3d/device.c +++ b/dlls/wined3d/device.c @@ -4520,6 +4520,24 @@ void CDECL wined3d_device_copy_uav_counter(struct wined3d_device *device, wined3d_cs_emit_copy_uav_counter(device->cs, dst_buffer, offset, uav); } +static bool resources_format_compatible(const struct wined3d_resource *src_resource, + const struct wined3d_resource *dst_resource) +{ + if (src_resource->format->id == dst_resource->format->id) + return true; + if (src_resource->format->typeless_id && src_resource->format->typeless_id == dst_resource->format->typeless_id) + return true; + if (src_resource->device->feature_level < WINED3D_FEATURE_LEVEL_10_1) + return false; + if ((src_resource->format_flags & WINED3DFMT_FLAG_BLOCKS) + && (dst_resource->format_flags & WINED3DFMT_FLAG_CAST_TO_BLOCK)) + return src_resource->format->block_byte_count == dst_resource->format->byte_count; + if ((src_resource->format_flags & WINED3DFMT_FLAG_CAST_TO_BLOCK) + && (dst_resource->format_flags & WINED3DFMT_FLAG_BLOCKS)) + return src_resource->format->byte_count == dst_resource->format->block_byte_count; + return false; +} + void CDECL wined3d_device_copy_resource(struct wined3d_device *device, struct wined3d_resource *dst_resource, struct wined3d_resource *src_resource) { @@ -4553,8 +4571,7 @@ void CDECL wined3d_device_copy_resource(struct wined3d_device *device, return; } - if (src_resource->format->typeless_id != dst_resource->format->typeless_id - || (!src_resource->format->typeless_id && src_resource->format->id != dst_resource->format->id)) + if (!resources_format_compatible(src_resource, dst_resource)) { WARN("Resource formats %s and %s are incompatible.\n", debug_d3dformat(dst_resource->format->id), @@ -4616,8 +4633,7 @@ HRESULT CDECL wined3d_device_copy_sub_resource_region(struct wined3d_device *dev return WINED3DERR_INVALIDCALL; } - if (src_resource->format->typeless_id != dst_resource->format->typeless_id - || (!src_resource->format->typeless_id && src_resource->format->id != dst_resource->format->id)) + if (!resources_format_compatible(src_resource, dst_resource)) { WARN("Resource formats %s and %s are incompatible.\n", debug_d3dformat(dst_resource->format->id), diff --git a/dlls/wined3d/utils.c b/dlls/wined3d/utils.c index daf079f50dc..6839065365f 100644 --- a/dlls/wined3d/utils.c +++ b/dlls/wined3d/utils.c @@ -330,19 +330,37 @@ struct wined3d_format_base_flags * resource size. */ static const struct wined3d_format_base_flags format_base_flags[] = { - {WINED3DFMT_ATI1N, WINED3DFMT_FLAG_MAPPABLE | WINED3DFMT_FLAG_BROKEN_PITCH}, - {WINED3DFMT_ATI2N, WINED3DFMT_FLAG_MAPPABLE | WINED3DFMT_FLAG_BROKEN_PITCH}, - {WINED3DFMT_D16_LOCKABLE, WINED3DFMT_FLAG_MAPPABLE}, - {WINED3DFMT_INTZ, WINED3DFMT_FLAG_MAPPABLE}, - {WINED3DFMT_R11G11B10_FLOAT, WINED3DFMT_FLAG_FLOAT}, - {WINED3DFMT_D32_FLOAT, WINED3DFMT_FLAG_FLOAT}, - {WINED3DFMT_S8_UINT_D24_FLOAT, WINED3DFMT_FLAG_FLOAT}, - {WINED3DFMT_D32_FLOAT_S8X24_UINT, WINED3DFMT_FLAG_FLOAT}, - {WINED3DFMT_INST, WINED3DFMT_FLAG_EXTENSION}, - {WINED3DFMT_NULL, WINED3DFMT_FLAG_EXTENSION}, - {WINED3DFMT_NVDB, WINED3DFMT_FLAG_EXTENSION}, - {WINED3DFMT_ATOC, WINED3DFMT_FLAG_EXTENSION}, - {WINED3DFMT_RESZ, WINED3DFMT_FLAG_EXTENSION}, + {WINED3DFMT_ATI1N, WINED3DFMT_FLAG_MAPPABLE | WINED3DFMT_FLAG_BROKEN_PITCH}, + {WINED3DFMT_ATI2N, WINED3DFMT_FLAG_MAPPABLE | WINED3DFMT_FLAG_BROKEN_PITCH}, + {WINED3DFMT_D16_LOCKABLE, WINED3DFMT_FLAG_MAPPABLE}, + {WINED3DFMT_INTZ, WINED3DFMT_FLAG_MAPPABLE}, + {WINED3DFMT_R11G11B10_FLOAT, WINED3DFMT_FLAG_FLOAT}, + {WINED3DFMT_D32_FLOAT, WINED3DFMT_FLAG_FLOAT}, + {WINED3DFMT_S8_UINT_D24_FLOAT, WINED3DFMT_FLAG_FLOAT}, + {WINED3DFMT_D32_FLOAT_S8X24_UINT, WINED3DFMT_FLAG_FLOAT}, + {WINED3DFMT_INST, WINED3DFMT_FLAG_EXTENSION}, + {WINED3DFMT_NULL, WINED3DFMT_FLAG_EXTENSION}, + {WINED3DFMT_NVDB, WINED3DFMT_FLAG_EXTENSION}, + {WINED3DFMT_ATOC, WINED3DFMT_FLAG_EXTENSION}, + {WINED3DFMT_RESZ, WINED3DFMT_FLAG_EXTENSION}, + {WINED3DFMT_R32G32B32A32_TYPELESS, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R32G32B32A32_FLOAT, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R32G32B32A32_UINT, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R32G32B32A32_SINT, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R16G16B16A16_TYPELESS, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R16G16B16A16_FLOAT, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R16G16B16A16_UNORM, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R16G16B16A16_UINT, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R16G16B16A16_SNORM, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R16G16B16A16_SINT, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R32G32_TYPELESS, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R32G32_FLOAT, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R32G32_UINT, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R32G32_SINT, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R32_TYPELESS, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R32_FLOAT, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R32_UINT, WINED3DFMT_FLAG_CAST_TO_BLOCK}, + {WINED3DFMT_R32_SINT, WINED3DFMT_FLAG_CAST_TO_BLOCK}, }; static void rgb888_from_rgb565(WORD rgb565, BYTE *r, BYTE *g, BYTE *b) @@ -580,25 +598,26 @@ struct wined3d_format_block_info static const struct wined3d_format_block_info format_block_info[] = { - {WINED3DFMT_DXT1, 4, 4, 8, WINED3DFMT_FLAG_COMPRESSED}, - {WINED3DFMT_DXT2, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, - {WINED3DFMT_DXT3, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, - {WINED3DFMT_DXT4, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, - {WINED3DFMT_DXT5, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, - {WINED3DFMT_BC1_UNORM, 4, 4, 8, WINED3DFMT_FLAG_COMPRESSED}, - {WINED3DFMT_BC2_UNORM, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, - {WINED3DFMT_BC3_UNORM, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, - {WINED3DFMT_BC4_UNORM, 4, 4, 8, WINED3DFMT_FLAG_COMPRESSED}, - {WINED3DFMT_BC4_SNORM, 4, 4, 8, WINED3DFMT_FLAG_COMPRESSED}, - {WINED3DFMT_BC5_UNORM, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, - {WINED3DFMT_BC5_SNORM, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, - {WINED3DFMT_BC6H_UF16, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, - {WINED3DFMT_BC6H_SF16, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, - {WINED3DFMT_BC7_UNORM, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, - {WINED3DFMT_ATI1N, 4, 4, 8, WINED3DFMT_FLAG_COMPRESSED | WINED3DFMT_FLAG_BLOCKS_NO_VERIFY}, - {WINED3DFMT_ATI2N, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED | WINED3DFMT_FLAG_BLOCKS_NO_VERIFY}, - {WINED3DFMT_YUY2, 2, 1, 4, WINED3DFMT_FLAG_BLOCKS_NO_VERIFY}, - {WINED3DFMT_UYVY, 2, 1, 4, WINED3DFMT_FLAG_BLOCKS_NO_VERIFY}, + {WINED3DFMT_DXT1, 4, 4, 8, WINED3DFMT_FLAG_COMPRESSED}, + {WINED3DFMT_DXT2, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, + {WINED3DFMT_DXT3, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, + {WINED3DFMT_DXT4, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, + {WINED3DFMT_DXT5, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, + {WINED3DFMT_BC1_UNORM, 4, 4, 8, WINED3DFMT_FLAG_COMPRESSED}, + {WINED3DFMT_BC2_UNORM, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, + {WINED3DFMT_BC3_UNORM, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, + {WINED3DFMT_BC4_UNORM, 4, 4, 8, WINED3DFMT_FLAG_COMPRESSED}, + {WINED3DFMT_BC4_SNORM, 4, 4, 8, WINED3DFMT_FLAG_COMPRESSED}, + {WINED3DFMT_BC5_UNORM, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, + {WINED3DFMT_BC5_SNORM, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, + {WINED3DFMT_BC6H_UF16, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, + {WINED3DFMT_BC6H_SF16, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, + {WINED3DFMT_BC7_UNORM, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED}, + {WINED3DFMT_ATI1N, 4, 4, 8, WINED3DFMT_FLAG_COMPRESSED | WINED3DFMT_FLAG_BLOCKS_NO_VERIFY}, + {WINED3DFMT_ATI2N, 4, 4, 16, WINED3DFMT_FLAG_COMPRESSED | WINED3DFMT_FLAG_BLOCKS_NO_VERIFY}, + {WINED3DFMT_YUY2, 2, 1, 4, WINED3DFMT_FLAG_BLOCKS_NO_VERIFY}, + {WINED3DFMT_UYVY, 2, 1, 4, WINED3DFMT_FLAG_BLOCKS_NO_VERIFY}, + {WINED3DFMT_R9G9B9E5_SHAREDEXP, 1, 1, 4}, }; struct wined3d_format_vertex_info diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h index bb68b780c7d..2a75ab5d43d 100644 --- a/dlls/wined3d/wined3d_private.h +++ b/dlls/wined3d/wined3d_private.h @@ -5713,6 +5713,7 @@ extern enum wined3d_format_id pixelformat_for_depth(DWORD depth) DECLSPEC_HIDDEN #define WINED3DFMT_FLAG_VERTEX_ATTRIBUTE 0x01000000 #define WINED3DFMT_FLAG_BLIT 0x02000000 #define WINED3DFMT_FLAG_MAPPABLE 0x04000000 +#define WINED3DFMT_FLAG_CAST_TO_BLOCK 0x08000000 struct wined3d_rational {