Module: Mesa Branch: main Commit: 580728564e562bd8a86a78323e4a99d9b3b97e71 URL: http://cgit.freedesktop.org/mesa/mesa/commit/?id=580728564e562bd8a86a78323e4a99d9b3b97e71
Author: Rohan Garg <[email protected]> Date: Fri Jun 24 16:53:42 2022 +0200 anv: Emit a EXECUTE_INDIRECT_DISPATCH when available On newer platforms (Arrowlake and above) we can issue a EXECUTE_INDIRECT_DISPATCH that allows us to: * Skip issuing mi load/store instructions for indirect parameters Signed-off-by: Rohan Garg <[email protected]> Reviewed-by: Lionel Landwerlin <[email protected]> Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/26421> --- src/intel/vulkan/genX_cmd_buffer.c | 49 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 49 insertions(+) diff --git a/src/intel/vulkan/genX_cmd_buffer.c b/src/intel/vulkan/genX_cmd_buffer.c index 504f5acb590..c9e38e7e757 100644 --- a/src/intel/vulkan/genX_cmd_buffer.c +++ b/src/intel/vulkan/genX_cmd_buffer.c @@ -5863,6 +5863,47 @@ get_interface_descriptor_data(struct anv_cmd_buffer *cmd_buffer, }; } +static inline void +emit_indirect_compute_walker(struct anv_cmd_buffer *cmd_buffer, + const struct anv_shader_bin *shader, + const struct brw_cs_prog_data *prog_data, + struct anv_address indirect_addr) +{ + const struct intel_device_info *devinfo = cmd_buffer->device->info; + assert(devinfo->has_indirect_unroll); + + struct anv_cmd_compute_state *comp_state = &cmd_buffer->state.compute; + bool predicate = cmd_buffer->state.conditional_render_enabled; + + const struct brw_cs_dispatch_info dispatch = + brw_cs_get_dispatch_info(devinfo, prog_data, NULL); + const int dispatch_size = dispatch.simd_size / 16; + + struct GENX(COMPUTE_WALKER_BODY) body = { + .SIMDSize = dispatch_size, + .MessageSIMD = dispatch_size, + .IndirectDataStartAddress = comp_state->push_data.offset, + .IndirectDataLength = comp_state->push_data.alloc_size, + .LocalXMaximum = prog_data->local_size[0] - 1, + .LocalYMaximum = prog_data->local_size[1] - 1, + .LocalZMaximum = prog_data->local_size[2] - 1, + .ExecutionMask = dispatch.right_mask, + .PostSync.MOCS = anv_mocs(cmd_buffer->device, NULL, 0), + .InterfaceDescriptor = + get_interface_descriptor_data(cmd_buffer, shader, prog_data, + &dispatch), + }; + + anv_batch_emit(&cmd_buffer->batch, GENX(EXECUTE_INDIRECT_DISPATCH), ind) { + ind.PredicateEnable = predicate; + ind.MaxCount = 1; + ind.COMPUTE_WALKER_BODY = body; + ind.ArgumentBufferStartAddress = indirect_addr; + ind.MOCS = anv_mocs(cmd_buffer->device, + indirect_addr.bo, 0); + } +} + static inline void emit_compute_walker(struct anv_cmd_buffer *cmd_buffer, const struct anv_compute_pipeline *pipeline, bool indirect, @@ -5946,6 +5987,14 @@ emit_cs_walker(struct anv_cmd_buffer *cmd_buffer, { bool is_indirect = !anv_address_is_null(indirect_addr); +#if GFX_VERx10 >= 125 + if (is_indirect && cmd_buffer->device->info->has_indirect_unroll) { + emit_indirect_compute_walker(cmd_buffer, pipeline->cs, prog_data, + indirect_addr); + return; + } +#endif + if (is_indirect) compute_load_indirect_params(cmd_buffer, indirect_addr);
