radeonsi: make si_shader_selector::main_shader_part_* an iterable union

for the next commit

Fixes: 8ba718fb7d - radeonsi/gfx12: use ACO for streamout because it's faster

Reviewed-by: Pierre-Eric Pelloux-Prayer <pierre-eric.pelloux-prayer@amd.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/34491>
This commit is contained in:
Marek Olšák
2025-04-10 12:34:16 -04:00
committed by Marge Bot
parent 1adf969318
commit 4865ac57cc
3 changed files with 30 additions and 42 deletions

View File

@@ -3285,8 +3285,8 @@ static bool si_shader_select_tcs_parts(struct si_screen *sscreen, struct ac_llvm
{
if (sscreen->info.gfx_level >= GFX9) {
assert(shader->wave_size == 32 || shader->wave_size == 64);
unsigned index = shader->wave_size / 32 - 1;
shader->previous_stage = shader->key.ge.part.tcs.ls->main_shader_part_ls[index];
unsigned wave_size_index = shader->wave_size == 64;
shader->previous_stage = shader->key.ge.part.tcs.ls->main_parts.named.ls[wave_size_index];
}
return true;
@@ -3301,10 +3301,10 @@ static bool si_shader_select_gs_parts(struct si_screen *sscreen, struct ac_llvm_
if (sscreen->info.gfx_level >= GFX9) {
if (shader->key.ge.as_ngg) {
assert(shader->wave_size == 32 || shader->wave_size == 64);
unsigned index = shader->wave_size / 32 - 1;
shader->previous_stage = shader->key.ge.part.gs.es->main_shader_part_ngg_es[index];
unsigned wave_size_index = shader->wave_size == 64;
shader->previous_stage = shader->key.ge.part.gs.es->main_parts.named.ngg_es[wave_size_index];
} else {
shader->previous_stage = shader->key.ge.part.gs.es->main_shader_part_es;
shader->previous_stage = shader->key.ge.part.gs.es->main_parts.named.es;
}
}

View File

@@ -587,6 +587,18 @@ struct si_shader_info {
uint8_t reads_frag_coord_mask;
};
union si_main_shader_parts {
struct si_main_shader_parts_named {
/* indices: [wave_size == 64] */
struct si_shader *other[2];
struct si_shader *ls[2]; /* as_ls is set in the key */
struct si_shader *es; /* as_es && !as_ngg in the key */
struct si_shader *ngg[2]; /* !as_es && as_ngg in the key */
struct si_shader *ngg_es[2]; /* as_es && as_ngg in the key */
} named;
struct si_shader *variants[sizeof(struct si_main_shader_parts_named) / sizeof(struct si_shader*)];
};
/* A shader selector is a gallium CSO and contains shader variants and
* binaries for one NIR program. This can be shared by multiple contexts.
*/
@@ -605,14 +617,8 @@ struct si_shader_selector {
/* The compiled NIR shader without a prolog and/or epilog (not
* uploaded to a buffer object).
*
* [0] for wave32, [1] for wave64.
*/
struct si_shader *main_shader_part[2];
struct si_shader *main_shader_part_ls[2]; /* as_ls is set in the key */
struct si_shader *main_shader_part_es; /* as_es && !as_ngg in the key */
struct si_shader *main_shader_part_ngg[2]; /* !as_es && as_ngg in the key */
struct si_shader *main_shader_part_ngg_es[2]; /* as_es && as_ngg in the key */
union si_main_shader_parts main_parts;
struct nir_shader *nir;
void *nir_binary;
@@ -1108,22 +1114,22 @@ static inline struct si_shader **si_get_main_shader_part(struct si_shader_select
unsigned wave_size)
{
assert(wave_size == 32 || wave_size == 64);
unsigned index = wave_size / 32 - 1;
unsigned wave_size_index = wave_size == 64;
if (sel->stage <= MESA_SHADER_GEOMETRY) {
if (key->ge.as_ls)
return &sel->main_shader_part_ls[index];
return &sel->main_parts.named.ls[wave_size_index];
if (key->ge.as_es && key->ge.as_ngg)
return &sel->main_shader_part_ngg_es[index];
return &sel->main_parts.named.ngg_es[wave_size_index];
if (key->ge.as_es) {
/* legacy GS only support wave 64 */
assert(wave_size == 64);
return &sel->main_shader_part_es;
return &sel->main_parts.named.es;
}
if (key->ge.as_ngg)
return &sel->main_shader_part_ngg[index];
return &sel->main_parts.named.ngg[wave_size_index];
}
return &sel->main_shader_part[index];
return &sel->main_parts.named.other[wave_size_index];
}
static inline bool gfx10_has_variable_edgeflags(struct si_shader *shader)

View File

@@ -3696,19 +3696,10 @@ static void *si_create_shader(struct pipe_context *ctx, const struct pipe_shader
ctx, &sscreen->live_shader_cache, state, &cache_hit);
if (sel && cache_hit && sctx->debug.debug_message) {
for (unsigned i = 0; i < 2; i++) {
if (sel->main_shader_part[i])
si_shader_dump_stats_for_shader_db(sscreen, sel->main_shader_part[i], &sctx->debug);
if (sel->main_shader_part_ls[i])
si_shader_dump_stats_for_shader_db(sscreen, sel->main_shader_part_ls[i], &sctx->debug);
if (sel->main_shader_part_ngg[i])
si_shader_dump_stats_for_shader_db(sscreen, sel->main_shader_part_ngg[i], &sctx->debug);
if (sel->main_shader_part_ngg_es[i])
si_shader_dump_stats_for_shader_db(sscreen, sel->main_shader_part_ngg_es[i], &sctx->debug);
for (unsigned i = 0; i < ARRAY_SIZE(sel->main_parts.variants); i++) {
if (sel->main_parts.variants[i])
si_shader_dump_stats_for_shader_db(sscreen, sel->main_parts.variants[i], &sctx->debug);
}
if (sel->main_shader_part_es)
si_shader_dump_stats_for_shader_db(sscreen, sel->main_shader_part_es, &sctx->debug);
}
return sel;
}
@@ -4149,20 +4140,11 @@ static void si_destroy_shader_selector(struct pipe_context *ctx, void *cso)
si_delete_shader(sctx, sel->variants[i]);
}
for (unsigned i = 0; i < 2; i++) {
if (sel->main_shader_part[i])
si_delete_shader(sctx, sel->main_shader_part[i]);
if (sel->main_shader_part_ls[i])
si_delete_shader(sctx, sel->main_shader_part_ls[i]);
if (sel->main_shader_part_ngg[i])
si_delete_shader(sctx, sel->main_shader_part_ngg[i]);
if (sel->main_shader_part_ngg_es[i])
si_delete_shader(sctx, sel->main_shader_part_ngg_es[i]);
for (unsigned i = 0; i < ARRAY_SIZE(sel->main_parts.variants); i++) {
if (sel->main_parts.variants[i])
si_delete_shader(sctx, sel->main_parts.variants[i]);
}
if (sel->main_shader_part_es)
si_delete_shader(sctx, sel->main_shader_part_es);
free(sel->keys);
free(sel->variants);