Module: Mesa Branch: staging/22.1 Commit: f9cc403ebed850cd627e622b850f37e4b99ea408 URL: http://cgit.freedesktop.org/mesa/mesa/commit/?id=f9cc403ebed850cd627e622b850f37e4b99ea408
Author: Mike Blumenkrantz <[email protected]> Date: Fri Apr 22 14:16:42 2022 -0400 lavapipe: fix CmdPushDescriptorSetWithTemplateKHR with refcounting this is a cmdbuf function, which means it gets enqueued, which means the template can't be destroyed until the cmdbuf has finished using it cc: mesa-stable Reviewed-by: Dave Airlie <[email protected]> Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/16137> (cherry picked from commit 49df9eeb9d6a1a659786ef226f6ece0f9950e6ba) --- .pick_status.json | 2 +- src/gallium/frontends/lavapipe/lvp_cmd_buffer.c | 11 +++++++++++ .../frontends/lavapipe/lvp_descriptor_set.c | 20 +++++++++++++------- src/gallium/frontends/lavapipe/lvp_private.h | 22 ++++++++++++++++++++++ 4 files changed, 47 insertions(+), 8 deletions(-) diff --git a/.pick_status.json b/.pick_status.json index ea72a44baab..5dd90c08ea8 100644 --- a/.pick_status.json +++ b/.pick_status.json @@ -382,7 +382,7 @@ "description": "lavapipe: fix CmdPushDescriptorSetWithTemplateKHR with refcounting", "nominated": true, "nomination_type": 0, - "resolution": 0, + "resolution": 1, "main_sha": null, "because_sha": null }, diff --git a/src/gallium/frontends/lavapipe/lvp_cmd_buffer.c b/src/gallium/frontends/lavapipe/lvp_cmd_buffer.c index d9da1477dd2..84f20f99cc5 100644 --- a/src/gallium/frontends/lavapipe/lvp_cmd_buffer.c +++ b/src/gallium/frontends/lavapipe/lvp_cmd_buffer.c @@ -266,6 +266,14 @@ VKAPI_ATTR void VKAPI_CALL lvp_TrimCommandPool( list_inithead(&pool->free_cmd_buffers); } +static void +lvp_free_CmdPushDescriptorSetWithTemplateKHR(struct vk_cmd_queue *queue, struct vk_cmd_queue_entry *cmd) +{ + struct lvp_device *device = cmd->driver_data; + LVP_FROM_HANDLE(lvp_descriptor_update_template, templ, cmd->u.push_descriptor_set_with_template_khr.descriptor_update_template); + lvp_descriptor_template_templ_unref(device, templ); +} + VKAPI_ATTR void VKAPI_CALL lvp_CmdPushDescriptorSetWithTemplateKHR( VkCommandBuffer commandBuffer, VkDescriptorUpdateTemplate descriptorUpdateTemplate, @@ -285,8 +293,11 @@ VKAPI_ATTR void VKAPI_CALL lvp_CmdPushDescriptorSetWithTemplateKHR( cmd->type = VK_CMD_PUSH_DESCRIPTOR_SET_WITH_TEMPLATE_KHR; list_addtail(&cmd->cmd_link, &cmd_buffer->vk.cmd_queue.cmds); + cmd->driver_free_cb = lvp_free_CmdPushDescriptorSetWithTemplateKHR; + cmd->driver_data = cmd_buffer->device; cmd->u.push_descriptor_set_with_template_khr.descriptor_update_template = descriptorUpdateTemplate; + lvp_descriptor_template_templ_ref(templ); cmd->u.push_descriptor_set_with_template_khr.layout = layout; cmd->u.push_descriptor_set_with_template_khr.set = set; diff --git a/src/gallium/frontends/lavapipe/lvp_descriptor_set.c b/src/gallium/frontends/lavapipe/lvp_descriptor_set.c index 458d50c7845..bca412c36ee 100644 --- a/src/gallium/frontends/lavapipe/lvp_descriptor_set.c +++ b/src/gallium/frontends/lavapipe/lvp_descriptor_set.c @@ -684,13 +684,14 @@ VKAPI_ATTR VkResult VKAPI_CALL lvp_CreateDescriptorUpdateTemplate(VkDevice _devi struct lvp_descriptor_update_template *templ; - templ = vk_alloc2(&device->vk.alloc, pAllocator, size, 8, VK_SYSTEM_ALLOCATION_SCOPE_OBJECT); + templ = vk_alloc(&device->vk.alloc, size, 8, VK_SYSTEM_ALLOCATION_SCOPE_OBJECT); if (!templ) return vk_error(device, VK_ERROR_OUT_OF_HOST_MEMORY); vk_object_base_init(&device->vk, &templ->base, VK_OBJECT_TYPE_DESCRIPTOR_UPDATE_TEMPLATE); + templ->ref_cnt = 1; templ->type = pCreateInfo->templateType; templ->bind_point = pCreateInfo->pipelineBindPoint; templ->set = pCreateInfo->set; @@ -710,18 +711,23 @@ VKAPI_ATTR VkResult VKAPI_CALL lvp_CreateDescriptorUpdateTemplate(VkDevice _devi return VK_SUCCESS; } +void +lvp_descriptor_template_destroy(struct lvp_device *device, struct lvp_descriptor_update_template *templ) +{ + if (!templ) + return; + + vk_object_base_finish(&templ->base); + vk_free(&device->vk.alloc, templ); +} + VKAPI_ATTR void VKAPI_CALL lvp_DestroyDescriptorUpdateTemplate(VkDevice _device, VkDescriptorUpdateTemplate descriptorUpdateTemplate, const VkAllocationCallbacks *pAllocator) { LVP_FROM_HANDLE(lvp_device, device, _device); LVP_FROM_HANDLE(lvp_descriptor_update_template, templ, descriptorUpdateTemplate); - - if (!templ) - return; - - vk_object_base_finish(&templ->base); - vk_free2(&device->vk.alloc, pAllocator, templ); + lvp_descriptor_template_templ_unref(device, templ); } VKAPI_ATTR void VKAPI_CALL lvp_UpdateDescriptorSetWithTemplate(VkDevice _device, diff --git a/src/gallium/frontends/lavapipe/lvp_private.h b/src/gallium/frontends/lavapipe/lvp_private.h index 94e2ca8df86..2fae582260c 100644 --- a/src/gallium/frontends/lavapipe/lvp_private.h +++ b/src/gallium/frontends/lavapipe/lvp_private.h @@ -380,6 +380,7 @@ struct lvp_descriptor_pool { struct lvp_descriptor_update_template { struct vk_object_base base; + unsigned ref_cnt; uint32_t entry_count; uint32_t set; VkDescriptorUpdateTemplateType type; @@ -388,6 +389,27 @@ struct lvp_descriptor_update_template { VkDescriptorUpdateTemplateEntry entry[0]; }; +static inline void +lvp_descriptor_template_templ_ref(struct lvp_descriptor_update_template *templ) +{ + assert(templ && templ->ref_cnt >= 1); + p_atomic_inc(&templ->ref_cnt); +} + +void +lvp_descriptor_template_destroy(struct lvp_device *device, struct lvp_descriptor_update_template *templ); + +static inline void +lvp_descriptor_template_templ_unref(struct lvp_device *device, + struct lvp_descriptor_update_template *templ) +{ + if (!templ) + return; + assert(templ->ref_cnt >= 1); + if (p_atomic_dec_zero(&templ->ref_cnt)) + lvp_descriptor_template_destroy(device, templ); +} + VkResult lvp_descriptor_set_create(struct lvp_device *device, struct lvp_descriptor_set_layout *layout,
