From 5676d51c1c94bb9e60e802c00ecfc2a597f2b134 Mon Sep 17 00:00:00 2001 From: Lionel Landwerlin Date: Fri, 24 Feb 2023 11:45:04 +0200 Subject: [PATCH] anv: handle null surface in the binding table with direct descriptors Signed-off-by: Lionel Landwerlin Reviewed-by: Kenneth Graunke Part-of: --- src/intel/vulkan/anv_device.c | 36 +++++++++++++++++++++--------- src/intel/vulkan/anv_private.h | 11 +++++++++ src/intel/vulkan/genX_cmd_buffer.c | 33 ++++++++++----------------- 3 files changed, 48 insertions(+), 32 deletions(-) diff --git a/src/intel/vulkan/anv_device.c b/src/intel/vulkan/anv_device.c index 2fab7714724..3510691826d 100644 --- a/src/intel/vulkan/anv_device.c +++ b/src/intel/vulkan/anv_device.c @@ -3324,17 +3324,31 @@ VkResult anv_CreateDevice( anv_genX(device->info, init_cps_device_state)(device); } - /* Allocate a null surface state at surface state offset 0. This makes - * NULL descriptor handling trivial because we can just memset structures - * to zero and they have a valid descriptor. - */ - device->null_surface_state = - anv_state_pool_alloc(&device->bindless_surface_state_pool, - device->isl_dev.ss.size, - device->isl_dev.ss.align); - isl_null_fill_state(&device->isl_dev, device->null_surface_state.map, - .size = isl_extent3d(1, 1, 1) /* This shouldn't matter */); - assert(device->null_surface_state.offset == 0); + if (device->physical->indirect_descriptors) { + /* Allocate a null surface state at surface state offset 0. This makes + * NULL descriptor handling trivial because we can just memset + * structures to zero and they have a valid descriptor. + */ + device->null_surface_state = + anv_state_pool_alloc(&device->bindless_surface_state_pool, + device->isl_dev.ss.size, + device->isl_dev.ss.align); + isl_null_fill_state(&device->isl_dev, device->null_surface_state.map, + .size = isl_extent3d(1, 1, 1) /* This shouldn't matter */); + assert(device->null_surface_state.offset == 0); + } else { + /* When using direct descriptors, those can hold the null surface state + * directly. We still need a null surface for the binding table entries + * though but this one can live anywhere the internal surface state + * pool. + */ + device->null_surface_state = + anv_state_pool_alloc(&device->internal_surface_state_pool, + device->isl_dev.ss.size, + device->isl_dev.ss.align); + isl_null_fill_state(&device->isl_dev, device->null_surface_state.map, + .size = isl_extent3d(1, 1, 1) /* This shouldn't matter */); + } anv_scratch_pool_init(device, &device->scratch_pool); diff --git a/src/intel/vulkan/anv_private.h b/src/intel/vulkan/anv_private.h index 99da336078d..d1bcaed18c9 100644 --- a/src/intel/vulkan/anv_private.h +++ b/src/intel/vulkan/anv_private.h @@ -1279,6 +1279,17 @@ anv_binding_table_pool_free(struct anv_device *device, struct anv_state state) anv_state_pool_free(&device->binding_table_pool, state); } +static inline struct anv_state +anv_null_surface_state_for_binding_table(struct anv_device *device) +{ + struct anv_state state = device->null_surface_state; + if (device->physical->indirect_descriptors) { + state.offset += device->physical->va.bindless_surface_state_pool.addr - + device->physical->va.internal_surface_state_pool.addr; + } + return state; +} + static inline struct anv_state anv_bindless_state_for_binding_table(struct anv_device *device, struct anv_state state) diff --git a/src/intel/vulkan/genX_cmd_buffer.c b/src/intel/vulkan/genX_cmd_buffer.c index e6aea19dde6..7fe6572fd27 100644 --- a/src/intel/vulkan/genX_cmd_buffer.c +++ b/src/intel/vulkan/genX_cmd_buffer.c @@ -2029,9 +2029,8 @@ emit_binding_table(struct anv_cmd_buffer *cmd_buffer, assert(desc_idx < MAX_PUSH_DESCRIPTORS); if (shader->push_desc_info.fully_promoted_ubo_descriptors & BITFIELD_BIT(desc_idx)) { - surface_state = anv_bindless_state_for_binding_table( - cmd_buffer->device, - cmd_buffer->device->null_surface_state); + surface_state = + anv_null_surface_state_for_binding_table(cmd_buffer->device); break; } } @@ -2062,9 +2061,7 @@ emit_binding_table(struct anv_cmd_buffer *cmd_buffer, assert(surface_state.alloc_size); } else { surface_state = - anv_bindless_state_for_binding_table( - cmd_buffer->device, - cmd_buffer->device->null_surface_state); + anv_null_surface_state_for_binding_table(cmd_buffer->device); } break; } @@ -2077,9 +2074,8 @@ emit_binding_table(struct anv_cmd_buffer *cmd_buffer, cmd_buffer->device, sstate.state); assert(surface_state.alloc_size); } else { - surface_state = anv_bindless_state_for_binding_table( - cmd_buffer->device, - cmd_buffer->device->null_surface_state); + surface_state = + anv_null_surface_state_for_binding_table(cmd_buffer->device); } break; } @@ -2090,9 +2086,8 @@ emit_binding_table(struct anv_cmd_buffer *cmd_buffer, surface_state = desc->set_buffer_view->general.state; assert(surface_state.alloc_size); } else { - surface_state = anv_bindless_state_for_binding_table( - cmd_buffer->device, - cmd_buffer->device->null_surface_state); + surface_state = + anv_null_surface_state_for_binding_table(cmd_buffer->device); } break; @@ -2103,9 +2098,8 @@ emit_binding_table(struct anv_cmd_buffer *cmd_buffer, desc->buffer_view->general.state); assert(surface_state.alloc_size); } else { - surface_state = anv_bindless_state_for_binding_table( - cmd_buffer->device, - cmd_buffer->device->null_surface_state); + surface_state = + anv_null_surface_state_for_binding_table(cmd_buffer->device); } break; @@ -2145,9 +2139,7 @@ emit_binding_table(struct anv_cmd_buffer *cmd_buffer, usage, address, range, 1); } else { surface_state = - anv_bindless_state_for_binding_table( - cmd_buffer->device, - cmd_buffer->device->null_surface_state); + anv_null_surface_state_for_binding_table(cmd_buffer->device); } break; } @@ -2159,9 +2151,8 @@ emit_binding_table(struct anv_cmd_buffer *cmd_buffer, desc->buffer_view->storage.state); assert(surface_state.alloc_size); } else { - surface_state = anv_bindless_state_for_binding_table( - cmd_buffer->device, - cmd_buffer->device->null_surface_state); + surface_state = + anv_null_surface_state_for_binding_table(cmd_buffer->device); } break;