anv: Support fast clears in anv_CmdClearColorImage

At least two game traces make use of this path: TWWH3 and Factorio.

Reviewed-by: Lionel Landwerlin <lionel.g.landwerlin@intel.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/31167>
This commit is contained in:
Nanley Chery
2024-09-09 07:45:52 -04:00
committed by Marge Bot
parent 46d58583ff
commit 1c7fe9ad1b
2 changed files with 52 additions and 12 deletions

View File

@@ -1423,33 +1423,69 @@ void anv_CmdClearColorImage(
struct anv_format_plane src_format =
anv_get_format_aspect(cmd_buffer->device->info, image->vk.format,
VK_IMAGE_ASPECT_COLOR_BIT, image->vk.tiling);
union isl_color_value clear_color = vk_to_isl_color(*pColor);
unsigned base_layer = pRanges[r].baseArrayLayer;
uint32_t layer_count =
vk_image_subresource_layer_count(&image->vk, &pRanges[r]);
uint32_t level_count =
vk_image_subresource_level_count(&image->vk, &pRanges[r]);
for (uint32_t i = 0; i < level_count; i++) {
const unsigned level = pRanges[r].baseMipLevel + i;
const unsigned level_width = u_minify(image->vk.extent.width, level);
const unsigned level_height = u_minify(image->vk.extent.height, level);
const VkExtent3D level_extent =
vk_image_mip_level_extent(&image->vk, level);
VkClearRect clear_rect = {};
clear_rect.rect.extent.width = level_extent.width;
clear_rect.rect.extent.height = level_extent.height;
if (image->vk.image_type == VK_IMAGE_TYPE_3D) {
base_layer = 0;
layer_count = u_minify(image->vk.extent.depth, level);
clear_rect.baseArrayLayer = 0;
clear_rect.layerCount = level_extent.depth;
} else {
clear_rect.baseArrayLayer = pRanges[r].baseArrayLayer;
clear_rect.layerCount =
vk_image_subresource_layer_count(&image->vk, &pRanges[r]);
}
if (anv_can_fast_clear_color(cmd_buffer, image, level, &clear_rect,
imageLayout, src_format.isl_format,
src_format.swizzle, clear_color)) {
assert(level == 0);
assert(clear_rect.baseArrayLayer == 0);
if (image->vk.samples == 1) {
exec_ccs_op(cmd_buffer, &batch, image, src_format.isl_format,
src_format.swizzle, VK_IMAGE_ASPECT_COLOR_BIT,
0, 0, 1, ISL_AUX_OP_FAST_CLEAR, &clear_color);
} else {
exec_mcs_op(cmd_buffer, &batch, image, src_format.isl_format,
src_format.swizzle, VK_IMAGE_ASPECT_COLOR_BIT,
0, 1, ISL_AUX_OP_FAST_CLEAR, &clear_color);
}
if (cmd_buffer->device->info->ver < 20) {
anv_cmd_buffer_mark_image_fast_cleared(cmd_buffer, image,
src_format.isl_format,
clear_color);
}
clear_rect.baseArrayLayer++;
if (--clear_rect.layerCount == 0)
continue;
}
anv_cmd_buffer_mark_image_written(cmd_buffer, image,
pRanges[r].aspectMask,
surf.aux_usage, level,
base_layer, layer_count);
clear_rect.baseArrayLayer,
clear_rect.layerCount);
blorp_clear(&batch, &surf,
src_format.isl_format, src_format.swizzle,
level, base_layer, layer_count,
0, 0, level_width, level_height,
vk_to_isl_color(*pColor), 0 /* color_write_disable */);
src_format.isl_format, src_format.swizzle, level,
clear_rect.baseArrayLayer,
clear_rect.layerCount,
clear_rect.rect.offset.x,
clear_rect.rect.offset.y,
clear_rect.rect.extent.width,
clear_rect.rect.extent.height,
clear_color, 0 /* color_write_disable */);
}
}

View File

@@ -3266,6 +3266,10 @@ anv_can_fast_clear_color(const struct anv_cmd_buffer *cmd_buffer,
if (INTEL_DEBUG(DEBUG_NO_FAST_CLEAR))
return false;
/* We only have fast-clears implemented for the render engine. */
if (cmd_buffer->queue_family->engine_class != INTEL_ENGINE_CLASS_RENDER)
return false;
/* Start by getting the fast clear type. We use the first subpass
* layout here because we don't want to fast-clear if the first subpass
* to use the attachment can't handle fast-clears.