radv: fix capture/replay with sparse images and descriptor buffer

The sparse image VA needs to be returned to the application for replay.

Reported by Baldur.

VKCTS has coverage but it doesn't verify this yet.

Cc: mesa-stable
Signed-off-by: Samuel Pitoiset <samuel.pitoiset@gmail.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/35162>
(cherry picked from commit 63758bc093)
This commit is contained in:
Samuel Pitoiset 2025-05-26 14:12:12 +02:00 committed by Eric Engestrom
parent 726cfb8a41
commit 3a98f0e86f
3 changed files with 29 additions and 5 deletions

View file

@ -584,7 +584,7 @@
"description": "radv: fix capture/replay with sparse images and descriptor buffer",
"nominated": true,
"nomination_type": 1,
"resolution": 0,
"resolution": 1,
"main_sha": null,
"because_sha": null,
"notes": null

View file

@ -1378,6 +1378,7 @@ radv_image_create(VkDevice _device, const struct radv_image_create_info *create_
assert(pCreateInfo->sType == VK_STRUCTURE_TYPE_IMAGE_CREATE_INFO);
const struct VkVideoProfileListInfoKHR *profile_list =
vk_find_struct_const(pCreateInfo->pNext, VIDEO_PROFILE_LIST_INFO_KHR);
uint64_t replay_address = 0;
unsigned plane_count = radv_get_internal_plane_count(pdev, format);
@ -1437,12 +1438,23 @@ radv_image_create(VkDevice _device, const struct radv_image_create_info *create_
}
if (image->vk.create_flags & VK_IMAGE_CREATE_SPARSE_BINDING_BIT) {
enum radeon_bo_flag flags = RADEON_FLAG_VIRTUAL;
if (image->vk.create_flags & VK_IMAGE_CREATE_DESCRIPTOR_BUFFER_CAPTURE_REPLAY_BIT_EXT) {
flags |= RADEON_FLAG_REPLAYABLE;
const VkOpaqueCaptureDescriptorDataCreateInfoEXT *opaque_info =
vk_find_struct_const(create_info->vk_info->pNext, OPAQUE_CAPTURE_DESCRIPTOR_DATA_CREATE_INFO_EXT);
if (opaque_info)
replay_address = *((const uint64_t *)opaque_info->opaqueCaptureDescriptorData);
}
image->alignment = MAX2(image->alignment, 4096);
image->size = align64(image->size, image->alignment);
image->bindings[0].offset = 0;
result = radv_bo_create(device, &image->vk.base, image->size, image->alignment, 0, RADEON_FLAG_VIRTUAL,
RADV_BO_PRIORITY_VIRTUAL, 0, true, &image->bindings[0].bo);
result = radv_bo_create(device, &image->vk.base, image->size, image->alignment, 0, flags,
RADV_BO_PRIORITY_VIRTUAL, replay_address, true, &image->bindings[0].bo);
if (result != VK_SUCCESS) {
radv_destroy_image(device, alloc, image);
return vk_error(device, result);
@ -1907,3 +1919,13 @@ radv_GetImageDrmFormatModifierPropertiesEXT(VkDevice _device, VkImage _image,
pProperties->drmFormatModifier = image->planes[0].surface.modifier;
return VK_SUCCESS;
}
VKAPI_ATTR VkResult VKAPI_CALL
radv_GetImageOpaqueCaptureDescriptorDataEXT(VkDevice device, const VkImageCaptureDescriptorDataInfoEXT *pInfo,
void *pData)
{
VK_FROM_HANDLE(radv_image, image, pInfo->image);
*(uint64_t *)pData = image->bindings[0].bo_va;
return VK_SUCCESS;
}

View file

@ -1815,9 +1815,11 @@ radv_get_physical_device_properties(struct radv_physical_device *pdev)
.maxSamplerDescriptorBufferBindings = MAX_SETS,
.maxEmbeddedImmutableSamplerBindings = MAX_SETS,
.maxEmbeddedImmutableSamplers = radv_max_descriptor_set_size(),
/* No data required for capture/replay but these values need to be non-zero. */
/* No data required for capture/replay (except for sparse images) but these values need to be
* non-zero.
*/
.bufferCaptureReplayDescriptorDataSize = 1,
.imageCaptureReplayDescriptorDataSize = 1,
.imageCaptureReplayDescriptorDataSize = 8,
.imageViewCaptureReplayDescriptorDataSize = 1,
.samplerCaptureReplayDescriptorDataSize = 1,
.accelerationStructureCaptureReplayDescriptorDataSize = 1,