radeonsi/gfx10: keep track of whether NGG is used

We always use NGG by default, except when tessellation is enabled with
extreme geometry shader amplification.

Acked-by: Bas Nieuwenhuizen <bas@basnieuwenhuizen.nl>
This commit is contained in:
Nicolai Hähnle 2019-05-07 23:00:43 +02:00 committed by Marek Olšák
parent 226f650d92
commit b45c3debe8
4 changed files with 31 additions and 1 deletions

View file

@ -7,5 +7,6 @@ OPT_BOOL(debug_disassembly, false, "Report shader disassembly as part of driver
OPT_BOOL(halt_shaders, false, "Halt shaders at the start (will hang)")
OPT_BOOL(vs_fetch_always_opencode, false, "Always open code vertex fetches (less efficient, purely for testing)")
OPT_BOOL(prim_restart_tri_strips_only, false, "Only enable primitive restart for triangle strips")
OPT_BOOL(disable_ngg, false, "Unconditionally disable NGG (gfx10+)")
#undef OPT_BOOL

View file

@ -486,6 +486,9 @@ static struct pipe_context *si_create_context(struct pipe_screen *screen,
if (!sctx->border_color_map)
goto fail;
if (sctx->chip_class >= GFX10)
sctx->ngg = !sscreen->options.disable_ngg;
/* Initialize context functions used by graphics and compute. */
if (sctx->chip_class >= GFX10)
sctx->emit_cache_flush = gfx10_emit_cache_flush;

View file

@ -1041,6 +1041,7 @@ struct si_context {
bool gs_tri_strip_adj_fix:1;
bool ls_vgpr_fix:1;
bool prim_discard_cs_instancing:1;
bool ngg:1;
int last_index_size;
int last_base_vertex;
int last_start_instance;

View file

@ -2588,6 +2588,27 @@ static void si_update_tess_uses_prim_id(struct si_context *sctx)
sctx->ps_shader.cso->info.uses_primid);
}
static bool si_update_ngg(struct si_context *sctx)
{
if (sctx->chip_class <= GFX9 ||
sctx->screen->options.disable_ngg)
return false;
bool new_ngg = true;
/* EN_MAX_VERT_OUT_PER_GS_INSTANCE does not work with tesselation. */
if (sctx->gs_shader.cso && sctx->tes_shader.cso &&
sctx->gs_shader.cso->gs_num_invocations * sctx->gs_shader.cso->gs_max_out_vertices > 256)
new_ngg = false;
if (new_ngg != sctx->ngg) {
sctx->ngg = new_ngg;
sctx->last_rast_prim = -1; /* reset this so that it gets updated */
return true;
}
return false;
}
static void si_bind_gs_shader(struct pipe_context *ctx, void *state)
{
struct si_context *sctx = (struct si_context *)ctx;
@ -2595,6 +2616,7 @@ static void si_bind_gs_shader(struct pipe_context *ctx, void *state)
struct si_shader *old_hw_vs_variant = si_get_vs_state(sctx);
struct si_shader_selector *sel = state;
bool enable_changed = !!sctx->gs_shader.cso != !!sel;
bool ngg_changed;
if (sctx->gs_shader.cso == sel)
return;
@ -2606,8 +2628,10 @@ static void si_bind_gs_shader(struct pipe_context *ctx, void *state)
si_update_common_shader_state(sctx);
sctx->last_rast_prim = -1; /* reset this so that it gets updated */
if (enable_changed) {
ngg_changed = si_update_ngg(sctx);
if (ngg_changed || enable_changed)
si_shader_change_notify(sctx);
if (enable_changed) {
if (sctx->ia_multi_vgt_param_key.u.uses_tess)
si_update_tess_uses_prim_id(sctx);
}
@ -2659,6 +2683,7 @@ static void si_bind_tes_shader(struct pipe_context *ctx, void *state)
sctx->last_rast_prim = -1; /* reset this so that it gets updated */
if (enable_changed) {
si_update_ngg(sctx);
si_shader_change_notify(sctx);
sctx->last_tes_sh_base = -1; /* invalidate derived tess state */
}