+/* Asynchronous compute shader compilation. */
+static void si_create_compute_state_async(void *job, int thread_index)
+{
+ struct si_compute *program = (struct si_compute *)job;
+ struct si_shader *shader = &program->shader;
+ struct si_shader_selector sel;
+ LLVMTargetMachineRef tm;
+ struct pipe_debug_callback *debug = &program->compiler_ctx_state.debug;
+
+ if (thread_index >= 0) {
+ assert(thread_index < ARRAY_SIZE(program->screen->tm));
+ tm = program->screen->tm[thread_index];
+ if (!debug->async)
+ debug = NULL;
+ } else {
+ tm = program->compiler_ctx_state.tm;
+ }
+
+ memset(&sel, 0, sizeof(sel));
+
+ sel.screen = program->screen;
+ tgsi_scan_shader(program->tokens, &sel.info);
+ sel.tokens = program->tokens;
+ sel.type = PIPE_SHADER_COMPUTE;
+ sel.local_size = program->local_size;
+ si_get_active_slot_masks(&sel.info,
+ &program->active_const_and_shader_buffers,
+ &program->active_samplers_and_images);
+
+ program->shader.selector = &sel;
+ program->shader.is_monolithic = true;
+ program->uses_grid_size = sel.info.uses_grid_size;
+ program->uses_block_size = sel.info.uses_block_size;
+ program->uses_bindless_samplers = sel.info.uses_bindless_samplers;
+ program->uses_bindless_images = sel.info.uses_bindless_images;
+
+ if (si_shader_create(program->screen, tm, &program->shader, debug)) {
+ program->shader.compilation_failed = true;
+ } else {
+ bool scratch_enabled = shader->config.scratch_bytes_per_wave > 0;
+ unsigned user_sgprs = SI_NUM_RESOURCE_SGPRS +
+ (sel.info.uses_grid_size ? 3 : 0) +
+ (sel.info.uses_block_size ? 3 : 0);
+
+ shader->config.rsrc1 =
+ S_00B848_VGPRS((shader->config.num_vgprs - 1) / 4) |
+ S_00B848_SGPRS((shader->config.num_sgprs - 1) / 8) |
+ S_00B848_DX10_CLAMP(1) |
+ S_00B848_FLOAT_MODE(shader->config.float_mode);
+
+ shader->config.rsrc2 =
+ S_00B84C_USER_SGPR(user_sgprs) |
+ S_00B84C_SCRATCH_EN(scratch_enabled) |
+ S_00B84C_TGID_X_EN(sel.info.uses_block_id[0]) |
+ S_00B84C_TGID_Y_EN(sel.info.uses_block_id[1]) |
+ S_00B84C_TGID_Z_EN(sel.info.uses_block_id[2]) |
+ S_00B84C_TIDIG_COMP_CNT(sel.info.uses_thread_id[2] ? 2 :
+ sel.info.uses_thread_id[1] ? 1 : 0) |
+ S_00B84C_LDS_SIZE(shader->config.lds_size);
+
+ program->variable_group_size =
+ sel.info.properties[TGSI_PROPERTY_CS_FIXED_BLOCK_WIDTH] == 0;
+ }
+
+ FREE(program->tokens);
+ program->shader.selector = NULL;
+}
+