blob: a7717210fc73f93a57be4cc210ae8dd88bc5a1b0 [file] [log] [blame]
From 288ce1b033faf1123b76688d9a02323484f21810 Mon Sep 17 00:00:00 2001
From: Yiwei Zhang <zzyiwei@chromium.org>
Date: Fri, 20 Aug 2021 21:50:14 +0000
Subject: [PATCH 7/8] venus: check descriptor allocations against pool resource
Only kick in when async_set_allocation is enabled.
Signed-off-by: Yiwei Zhang <zzyiwei@chromium.org>
Reviewed-by: Chia-I Wu <olvaffe@gmail.com>
Reviewed-by: Ryan Neph <ryanneph@google.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/12501>
---
src/virtio/vulkan/vn_descriptor_set.c | 80 +++++++++++++++++++++++++++
src/virtio/vulkan/vn_descriptor_set.h | 1 +
2 files changed, 81 insertions(+)
diff --git a/src/virtio/vulkan/vn_descriptor_set.c b/src/virtio/vulkan/vn_descriptor_set.c
index dbf9a879996..b6a1da54a01 100644
--- a/src/virtio/vulkan/vn_descriptor_set.c
+++ b/src/virtio/vulkan/vn_descriptor_set.c
@@ -277,6 +277,73 @@ vn_DestroyDescriptorPool(VkDevice device,
vk_free(alloc, pool);
}
+static bool
+vn_descriptor_pool_alloc_descriptors(
+ struct vn_descriptor_pool *pool,
+ const struct vn_descriptor_set_layout *layout,
+ uint32_t last_binding_descriptor_count)
+{
+ struct vn_descriptor_pool_state recovery;
+
+ if (!pool->async_set_allocation)
+ return true;
+
+ if (pool->used.set_count == pool->max.set_count)
+ return false;
+
+ /* backup current pool state to recovery */
+ recovery = pool->used;
+
+ ++pool->used.set_count;
+
+ for (uint32_t i = 0; i <= layout->last_binding; i++) {
+ const VkDescriptorType type = layout->bindings[i].type;
+ const uint32_t count = i == layout->last_binding
+ ? last_binding_descriptor_count
+ : layout->bindings[i].count;
+
+ pool->used.descriptor_counts[type] += count;
+
+ if (pool->used.descriptor_counts[type] >
+ pool->max.descriptor_counts[type]) {
+ /* restore pool state before this allocation */
+ pool->used = recovery;
+ return false;
+ }
+ }
+
+ return true;
+}
+
+static void
+vn_descriptor_pool_free_descriptors(
+ struct vn_descriptor_pool *pool,
+ const struct vn_descriptor_set_layout *layout,
+ uint32_t last_binding_descriptor_count)
+{
+ if (!pool->async_set_allocation)
+ return;
+
+ for (uint32_t i = 0; i <= layout->last_binding; i++) {
+ const uint32_t count = i == layout->last_binding
+ ? last_binding_descriptor_count
+ : layout->bindings[i].count;
+
+ pool->used.descriptor_counts[layout->bindings[i].type] -= count;
+ }
+
+ --pool->used.set_count;
+}
+
+static void
+vn_descriptor_pool_reset_descriptors(struct vn_descriptor_pool *pool)
+{
+ if (!pool->async_set_allocation)
+ return;
+
+ memset(&pool->used, 0, sizeof(pool->used));
+}
+
VkResult
vn_ResetDescriptorPool(VkDevice device,
VkDescriptorPool descriptorPool,
@@ -298,6 +365,8 @@ vn_ResetDescriptorPool(VkDevice device,
vk_free(alloc, set);
}
+ vn_descriptor_pool_reset_descriptors(pool);
+
return VK_SUCCESS;
}
@@ -347,9 +416,18 @@ vn_AllocateDescriptorSets(VkDevice device,
last_binding_descriptor_count = variable_info->pDescriptorCounts[i];
}
+ if (!vn_descriptor_pool_alloc_descriptors(
+ pool, layout, last_binding_descriptor_count)) {
+ pDescriptorSets[i] = VK_NULL_HANDLE;
+ result = VK_ERROR_OUT_OF_POOL_MEMORY;
+ goto fail;
+ }
+
set = vk_zalloc(alloc, sizeof(*set), VN_DEFAULT_ALIGN,
VK_SYSTEM_ALLOCATION_SCOPE_OBJECT);
if (!set) {
+ vn_descriptor_pool_free_descriptors(pool, layout,
+ last_binding_descriptor_count);
pDescriptorSets[i] = VK_NULL_HANDLE;
result = VK_ERROR_OUT_OF_HOST_MEMORY;
goto fail;
@@ -380,6 +458,8 @@ fail:
if (!set)
break;
+ vn_descriptor_pool_free_descriptors(pool, set->layout,
+ set->last_binding_descriptor_count);
list_del(&set->head);
vn_object_base_fini(&set->base);
vk_free(alloc, set);
diff --git a/src/virtio/vulkan/vn_descriptor_set.h b/src/virtio/vulkan/vn_descriptor_set.h
index 9eb100755aa..5f6afc44fb3 100644
--- a/src/virtio/vulkan/vn_descriptor_set.h
+++ b/src/virtio/vulkan/vn_descriptor_set.h
@@ -50,6 +50,7 @@ struct vn_descriptor_pool {
VkAllocationCallbacks allocator;
bool async_set_allocation;
struct vn_descriptor_pool_state max;
+ struct vn_descriptor_pool_state used;
struct list_head descriptor_sets;
};
--
2.33.0.259.gc128427fd7-goog