mesa/src/panfrost/vulkan/panvk_cmd_pool.c
Boris Brezillon 084f87915b panvk: Catch indirect allocation failures
The kmod layer allocates memory through the vulkan allocator for its
internal objects. When the allocation fails, we should return
VK_ERROR_OUT_OF_HOST_MEMORY, and the
dEQP-VK.api.object_management.alloc_callback_fail.* tests check this.

Generalize the errno trick we have and hide it behind panvk_error[f]()
macros, which serve as a replacement for vk_error[f]().

We also catch allocation failures in the panvk_cmd_alloc_xxx() path
so we can report the right error on the command buffer.

Signed-off-by: Boris Brezillon <boris.brezillon@collabora.com>
Reviewed-by: Mary Guillemard <mary.guillemard@collabora.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/31382>
2024-10-01 14:36:38 +00:00

73 lines
2.1 KiB
C

/*
* Copyright © 2021 Collabora Ltd.
*
* Derived from tu_cmd_buffer.c which is:
* Copyright © 2016 Red Hat.
* Copyright © 2016 Bas Nieuwenhuizen
* Copyright © 2015 Intel Corporation
*
* SPDX-License-Identifier: MIT
*/
#include "panvk_cmd_pool.h"
#include "panvk_device.h"
#include "panvk_entrypoints.h"
#include "vk_alloc.h"
#include "vk_log.h"
VKAPI_ATTR VkResult VKAPI_CALL
panvk_CreateCommandPool(VkDevice _device,
const VkCommandPoolCreateInfo *pCreateInfo,
const VkAllocationCallbacks *pAllocator,
VkCommandPool *pCmdPool)
{
VK_FROM_HANDLE(panvk_device, device, _device);
struct panvk_cmd_pool *pool;
pool = vk_alloc2(&device->vk.alloc, pAllocator, sizeof(*pool), 8,
VK_SYSTEM_ALLOCATION_SCOPE_OBJECT);
if (pool == NULL)
return panvk_error(device, VK_ERROR_OUT_OF_HOST_MEMORY);
VkResult result =
vk_command_pool_init(&device->vk, &pool->vk, pCreateInfo, pAllocator);
if (result != VK_SUCCESS) {
vk_free2(&device->vk.alloc, pAllocator, pool);
return result;
}
panvk_bo_pool_init(&pool->cs_bo_pool);
panvk_bo_pool_init(&pool->desc_bo_pool);
panvk_bo_pool_init(&pool->varying_bo_pool);
panvk_bo_pool_init(&pool->tls_bo_pool);
list_inithead(&pool->push_sets);
*pCmdPool = panvk_cmd_pool_to_handle(pool);
return VK_SUCCESS;
}
VKAPI_ATTR void VKAPI_CALL
panvk_DestroyCommandPool(VkDevice _device, VkCommandPool commandPool,
const VkAllocationCallbacks *pAllocator)
{
VK_FROM_HANDLE(panvk_device, device, _device);
VK_FROM_HANDLE(panvk_cmd_pool, pool, commandPool);
if (!pool)
return;
vk_command_pool_finish(&pool->vk);
panvk_bo_pool_cleanup(&pool->cs_bo_pool);
panvk_bo_pool_cleanup(&pool->desc_bo_pool);
panvk_bo_pool_cleanup(&pool->varying_bo_pool);
panvk_bo_pool_cleanup(&pool->tls_bo_pool);
list_for_each_entry_safe(struct panvk_cmd_pool_obj, obj, &pool->push_sets,
node) {
list_del(&obj->node);
vk_free(&pool->vk.alloc, obj);
}
vk_free2(&device->vk.alloc, pAllocator, pool);
}