anv: defer binding table block allocation to when necessary

There are cases where we never need a binding table block, for example
compute only command buffers.

This has also the nice effect of not having
dEQP-VK.api.object_management.* tests allocate 1Gb of binding tables
which are staying around forever after you run those tests.

Signed-off-by: Lionel Landwerlin <lionel.g.landwerlin@intel.com>
Closes: https://gitlab.freedesktop.org/mesa/mesa/-/issues/8806
Reviewed-by: José Roberto de Souza <jose.souza@intel.com>
Reviewed-by: Ivan Briano <ivan.briano@intel.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/23079>
This commit is contained in:
Lionel Landwerlin
2023-05-17 15:48:55 +03:00
committed by Marge Bot
parent 29d324cc75
commit eb2b309328

View File

@@ -425,6 +425,22 @@ anv_cmd_buffer_current_generation_batch_bo(struct anv_cmd_buffer *cmd_buffer)
struct anv_address
anv_cmd_buffer_surface_base_address(struct anv_cmd_buffer *cmd_buffer)
{
/* Compute only queues don't need binding tables. */
if (!(cmd_buffer->queue_family->queueFlags & VK_QUEUE_GRAPHICS_BIT))
return ANV_NULL_ADDRESS;
/* If we've never allocated a binding table block, do it now. Otherwise we
* would trigger another STATE_BASE_ADDRESS emission which would require an
* additional bunch of flushes/stalls.
*/
if (u_vector_length(&cmd_buffer->bt_block_states) == 0) {
VkResult result = anv_cmd_buffer_new_binding_table_block(cmd_buffer);
if (result != VK_SUCCESS) {
anv_batch_set_error(&cmd_buffer->batch, result);
return ANV_NULL_ADDRESS;
}
}
struct anv_state_pool *pool = &cmd_buffer->device->binding_table_pool;
struct anv_state *bt_block = u_vector_head(&cmd_buffer->bt_block_states);
return (struct anv_address) {
@@ -670,6 +686,9 @@ struct anv_state
anv_cmd_buffer_alloc_binding_table(struct anv_cmd_buffer *cmd_buffer,
uint32_t entries, uint32_t *state_offset)
{
if (u_vector_length(&cmd_buffer->bt_block_states) == 0)
return (struct anv_state) { 0 };
struct anv_state *bt_block = u_vector_head(&cmd_buffer->bt_block_states);
uint32_t bt_size = align(entries * 4, 32);
@@ -841,10 +860,6 @@ anv_cmd_buffer_init_batch_bo_chain(struct anv_cmd_buffer *cmd_buffer)
if (result != VK_SUCCESS)
goto fail_bt_blocks;
result = anv_cmd_buffer_new_binding_table_block(cmd_buffer);
if (result != VK_SUCCESS)
goto fail_bt_blocks;
return VK_SUCCESS;
fail_bt_blocks:
@@ -899,13 +914,11 @@ anv_cmd_buffer_reset_batch_bo_chain(struct anv_cmd_buffer *cmd_buffer)
&cmd_buffer->batch,
GFX8_MI_BATCH_BUFFER_START_length * 4);
while (u_vector_length(&cmd_buffer->bt_block_states) > 1) {
while (u_vector_length(&cmd_buffer->bt_block_states) > 0) {
struct anv_state *bt_block = u_vector_remove(&cmd_buffer->bt_block_states);
anv_binding_table_pool_free(cmd_buffer->device, *bt_block);
}
assert(u_vector_length(&cmd_buffer->bt_block_states) == 1);
cmd_buffer->bt_next = *(struct anv_state *)u_vector_head(&cmd_buffer->bt_block_states);
cmd_buffer->bt_next.offset = 0;
cmd_buffer->bt_next = ANV_STATE_NULL;
anv_reloc_list_clear(&cmd_buffer->surface_relocs);