From 03b4477c8feb4b0b235c9558b73495bb4c815fa8 Mon Sep 17 00:00:00 2001 From: Samuel Pitoiset Date: Thu, 12 Sep 2024 12:27:56 +0200 Subject: [PATCH] radv: fix returning non-zero captured address without binding The Vulkan spec says: "If the buffer was created with a non-zero value of VkBufferOpaqueCaptureAddressCreateInfo::opaqueCaptureAddress or VkBufferDeviceAddressCreateInfoEXT::deviceAddress, the return value will be the same address that was returned at capture time." My interpretation is that you can get the buffer device address before binding if you passed a non-zero address during buffer creation. The returned BDA would be similar if a memory object is bound to the buffer later. Cc: mesa-stable Signed-off-by: Samuel Pitoiset Part-of: --- src/amd/vulkan/radv_buffer.c | 21 +++++++++++++-------- 1 file changed, 13 insertions(+), 8 deletions(-) diff --git a/src/amd/vulkan/radv_buffer.c b/src/amd/vulkan/radv_buffer.c index 4e1031937b4..0bff0f7b20d 100644 --- a/src/amd/vulkan/radv_buffer.c +++ b/src/amd/vulkan/radv_buffer.c @@ -85,6 +85,15 @@ radv_create_buffer(struct radv_device *device, const VkBufferCreateInfo *pCreate buffer->bo_va = 0; buffer->range = 0; + uint64_t replay_address = 0; + const VkBufferOpaqueCaptureAddressCreateInfo *replay_info = + vk_find_struct_const(pCreateInfo->pNext, BUFFER_OPAQUE_CAPTURE_ADDRESS_CREATE_INFO); + if (replay_info && replay_info->opaqueCaptureAddress) + replay_address = replay_info->opaqueCaptureAddress; + + if (pCreateInfo->flags & VK_BUFFER_CREATE_DEVICE_ADDRESS_CAPTURE_REPLAY_BIT) + buffer->bo_va = replay_address; + if (pCreateInfo->flags & VK_BUFFER_CREATE_SPARSE_BINDING_BIT) { enum radeon_bo_flag flags = RADEON_FLAG_VIRTUAL; if (pCreateInfo->flags & VK_BUFFER_CREATE_DEVICE_ADDRESS_CAPTURE_REPLAY_BIT) @@ -93,18 +102,14 @@ radv_create_buffer(struct radv_device *device, const VkBufferCreateInfo *pCreate (VK_BUFFER_USAGE_2_RESOURCE_DESCRIPTOR_BUFFER_BIT_EXT | VK_BUFFER_USAGE_2_SAMPLER_DESCRIPTOR_BUFFER_BIT_EXT)) flags |= RADEON_FLAG_32BIT; - uint64_t replay_address = 0; - const VkBufferOpaqueCaptureAddressCreateInfo *replay_info = - vk_find_struct_const(pCreateInfo->pNext, BUFFER_OPAQUE_CAPTURE_ADDRESS_CREATE_INFO); - if (replay_info && replay_info->opaqueCaptureAddress) - replay_address = replay_info->opaqueCaptureAddress; - VkResult result = radv_bo_create(device, &buffer->vk.base, align64(buffer->vk.size, 4096), 4096, 0, flags, RADV_BO_PRIORITY_VIRTUAL, replay_address, is_internal, &buffer->bo); if (result != VK_SUCCESS) { radv_destroy_buffer(device, pAllocator, buffer); return vk_error(device, result); } + + buffer->bo_va = radv_buffer_get_va(buffer->bo); } *pBuffer = radv_buffer_to_handle(buffer); @@ -259,14 +264,14 @@ VKAPI_ATTR VkDeviceAddress VKAPI_CALL radv_GetBufferDeviceAddress(VkDevice device, const VkBufferDeviceAddressInfo *pInfo) { VK_FROM_HANDLE(radv_buffer, buffer, pInfo->buffer); - return radv_buffer_get_va(buffer->bo) + buffer->offset; + return buffer->bo_va + buffer->offset; } VKAPI_ATTR uint64_t VKAPI_CALL radv_GetBufferOpaqueCaptureAddress(VkDevice device, const VkBufferDeviceAddressInfo *pInfo) { VK_FROM_HANDLE(radv_buffer, buffer, pInfo->buffer); - return buffer->bo ? radv_buffer_get_va(buffer->bo) + buffer->offset : 0; + return buffer->bo_va + buffer->offset; } VkResult