diff --git a/src/freedreno/fdl/fd6_format_table.c b/src/freedreno/fdl/fd6_format_table.c index 8f200db40e1..d99d0299c6b 100644 --- a/src/freedreno/fdl/fd6_format_table.c +++ b/src/freedreno/fdl/fd6_format_table.c @@ -67,6 +67,7 @@ static const struct fd6_format formats[PIPE_FORMAT_COUNT] = { V__(R8_USCALED, 8_UINT, WZYX), V__(R8_SSCALED, 8_SINT, WZYX), _TC(R8_SRGB, 8_UNORM, WZYX), + _TC(Y8_UNORM, NV12_Y, WZYX), FMT(A8_UNORM, NONE, 8_UNORM, A8_UNORM, WZYX), _TC(L8_UNORM, 8_UNORM, WZYX), @@ -389,14 +390,19 @@ fd6_texture_format(enum pipe_format format, enum a6xx_tile_mode tile_mode) if (!formats[format].present) return FMT6_NONE; - /* Linear ARGB/ABGR1555 has a special format for sampling (tiled 1555/5551 - * formats always have the same swizzle and layout). - */ if (!tile_mode) { switch (format) { + /* Linear ARGB/ABGR1555 has a special format for sampling (tiled + * 1555/5551 formats always have the same swizzle and layout). + */ case PIPE_FORMAT_A1R5G5B5_UNORM: case PIPE_FORMAT_A1B5G5R5_UNORM: return FMT6_1_5_5_5_UNORM; + /* note: this may be more about UBWC than tiling, but we don't support + * tiled non-UBWC NV12 + */ + case PIPE_FORMAT_Y8_UNORM: + return FMT6_8_UNORM; default: break; } @@ -428,6 +434,10 @@ fd6_color_format(enum pipe_format format, enum a6xx_tile_mode tile_mode) { if (!formats[format].present) return FMT6_NONE; + + if (!tile_mode && format == PIPE_FORMAT_Y8_UNORM) + return FMT6_8_UNORM; + return formats[format].rb; } diff --git a/src/freedreno/vulkan/tu_clear_blit.c b/src/freedreno/vulkan/tu_clear_blit.c index e4afb6d7d95..2e1f10ab3c8 100644 --- a/src/freedreno/vulkan/tu_clear_blit.c +++ b/src/freedreno/vulkan/tu_clear_blit.c @@ -1188,7 +1188,7 @@ copy_format(VkFormat vk_format, VkImageAspectFlags aspect_mask, bool copy_buffer if (aspect_mask == VK_IMAGE_ASPECT_PLANE_1_BIT) return PIPE_FORMAT_R8G8_UNORM; else - return PIPE_FORMAT_R8_UNORM; + return PIPE_FORMAT_Y8_UNORM; case PIPE_FORMAT_R8_G8_B8_420_UNORM: return PIPE_FORMAT_R8_UNORM; @@ -1502,9 +1502,9 @@ tu_copy_buffer_to_image(struct tu_cmd_buffer *cmd, ops = &r3d_ops; } - /* TODO: G8_B8R8_2PLANE_420_UNORM Y plane has different hardware format, - * which matters for UBWC. buffer_to_image/etc can fail because of this - */ + /* note: could use "R8_UNORM" when no UBWC */ + if (src_format == PIPE_FORMAT_Y8_UNORM) + ops = &r3d_ops; VkOffset3D offset = info->imageOffset; VkExtent3D extent = info->imageExtent; @@ -1575,14 +1575,19 @@ tu_copy_image_to_buffer(struct tu_cmd_buffer *cmd, copy_format(src_image->vk_format, info->imageSubresource.aspectMask, true); enum pipe_format src_format = copy_format(src_image->vk_format, info->imageSubresource.aspectMask, false); + const struct blit_ops *ops = &r2d_ops; bool stencil_read = false; if (src_image->vk_format == VK_FORMAT_D24_UNORM_S8_UINT && info->imageSubresource.aspectMask == VK_IMAGE_ASPECT_STENCIL_BIT) { + ops = &r3d_ops; stencil_read = true; } - const struct blit_ops *ops = stencil_read ? &r3d_ops : &r2d_ops; + /* note: could use "R8_UNORM" when no UBWC */ + if (dst_format == PIPE_FORMAT_Y8_UNORM) + ops = &r3d_ops; + VkOffset3D offset = info->imageOffset; VkExtent3D extent = info->imageExtent; uint32_t dst_width = info->bufferRowLength ?: extent.width; @@ -1707,6 +1712,11 @@ tu_copy_image_to_image(struct tu_cmd_buffer *cmd, enum pipe_format dst_format = copy_format(dst_image->vk_format, info->dstSubresource.aspectMask, false); enum pipe_format src_format = copy_format(src_image->vk_format, info->srcSubresource.aspectMask, false); + /* note: could use "R8_UNORM" when no UBWC */ + if (dst_format == PIPE_FORMAT_Y8_UNORM || + src_format == PIPE_FORMAT_Y8_UNORM) + ops = &r3d_ops; + bool use_staging_blit = false; if (src_format == dst_format) { diff --git a/src/freedreno/vulkan/tu_formats.c b/src/freedreno/vulkan/tu_formats.c index e783e9b2b6d..0eaf284788d 100644 --- a/src/freedreno/vulkan/tu_formats.c +++ b/src/freedreno/vulkan/tu_formats.c @@ -252,16 +252,17 @@ tu_physical_device_get_format_properties( if (tu6_pipe2depth(vk_format) != (enum a6xx_depth_format)~0) optimal |= VK_FORMAT_FEATURE_DEPTH_STENCIL_ATTACHMENT_BIT; + if (vk_format == VK_FORMAT_G8B8G8R8_422_UNORM || + vk_format == VK_FORMAT_B8G8R8G8_422_UNORM || + vk_format == VK_FORMAT_G8_B8_R8_3PLANE_420_UNORM) { + /* these formats don't support UBWC or tiling */ + optimal = 0; + } + if (vk_format == VK_FORMAT_G8B8G8R8_422_UNORM || vk_format == VK_FORMAT_B8G8R8G8_422_UNORM || vk_format == VK_FORMAT_G8_B8R8_2PLANE_420_UNORM || vk_format == VK_FORMAT_G8_B8_R8_3PLANE_420_UNORM) { - /* no tiling for special UBWC formats - * TODO: NV12 can be UBWC but has a special UBWC format for accessing the Y plane aspect - * for 3plane, tiling/UBWC might be supported, but the blob doesn't use tiling - */ - optimal = 0; - /* Disable buffer texturing of subsampled (422) and planar YUV textures. * The subsampling requirement comes from "If format is a block-compressed * format, then bufferFeatures must not support any features for the diff --git a/src/freedreno/vulkan/tu_image.c b/src/freedreno/vulkan/tu_image.c index 4d9b2e953fa..8beb8436cbf 100644 --- a/src/freedreno/vulkan/tu_image.c +++ b/src/freedreno/vulkan/tu_image.c @@ -56,8 +56,7 @@ tu6_plane_format(VkFormat format, uint32_t plane) { switch (format) { case VK_FORMAT_G8_B8R8_2PLANE_420_UNORM: - /* note: with UBWC, and Y plane UBWC is different from R8_UNORM */ - return plane ? PIPE_FORMAT_R8G8_UNORM : PIPE_FORMAT_R8_UNORM; + return plane ? PIPE_FORMAT_R8G8_UNORM : PIPE_FORMAT_Y8_UNORM; case VK_FORMAT_G8_B8_R8_3PLANE_420_UNORM: return PIPE_FORMAT_R8_UNORM; case VK_FORMAT_D32_SFLOAT_S8_UINT: @@ -249,6 +248,19 @@ tu_image_view_init(struct tu_image_view *iview, else format = tu_vk_format_to_pipe_format(vk_format); + if (image->vk_format == VK_FORMAT_G8_B8R8_2PLANE_420_UNORM && + aspect_mask == VK_IMAGE_ASPECT_PLANE_0_BIT) { + if (vk_format == VK_FORMAT_R8_UNORM) { + /* The 0'th plane of this format has a different UBWC compression. */ + format = PIPE_FORMAT_Y8_UNORM; + } else { + /* If the user wants to reinterpret this plane, then they should've + * set MUTABLE_FORMAT_BIT which should disable UBWC and tiling. + */ + assert(!layouts[0]->ubwc); + } + } + if (aspect_mask == VK_IMAGE_ASPECT_COLOR_BIT && (vk_format == VK_FORMAT_G8_B8R8_2PLANE_420_UNORM || vk_format == VK_FORMAT_G8_B8_R8_3PLANE_420_UNORM)) {