iris: implement required PSS sync for Wa_18019816803

According to WA description, we need to track DS write state
and emit a PSS_STALL_SYNC whenever that state changes.

Signed-off-by: Tapani Pälli <tapani.palli@intel.com>
Reviewed-by: Lionel Landwerlin <lionel.g.landwerlin@intel.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/18411>
This commit is contained in:
Tapani Pälli 2022-04-05 09:57:46 +03:00 committed by Marge Bot
parent 92941ee84b
commit 0cb88ddca2
3 changed files with 71 additions and 0 deletions

View file

@ -301,6 +301,16 @@ iris_blorp_exec_render(struct blorp_batch *blorp_batch,
PIPE_CONTROL_STALL_AT_SCOREBOARD);
#endif
/* Check if blorp ds state matches ours. */
if (intel_needs_workaround(batch->screen->devinfo, 18019816803)) {
const bool blorp_ds_state =
params->depth.enabled || params->stencil.enabled;
if (ice->state.ds_write_state != blorp_ds_state) {
blorp_batch->flags |= BLORP_BATCH_NEED_PSS_STALL_SYNC;
ice->state.ds_write_state = blorp_ds_state;
}
}
if (params->depth.enabled &&
!(blorp_batch->flags & BLORP_BATCH_NO_EMIT_DEPTH_STENCIL))
genX(emit_depth_state_workarounds)(ice, batch, &params->depth.surf);

View file

@ -118,6 +118,7 @@ enum {
#define IRIS_DIRTY_RENDER_MISC_BUFFER_FLUSHES (1ull << 33)
#define IRIS_DIRTY_COMPUTE_MISC_BUFFER_FLUSHES (1ull << 34)
#define IRIS_DIRTY_VFG (1ull << 35)
#define IRIS_DIRTY_DS_WRITE_ENABLE (1ull << 36)
#define IRIS_ALL_DIRTY_FOR_COMPUTE (IRIS_DIRTY_COMPUTE_RESOLVES_AND_FLUSHES | \
IRIS_DIRTY_COMPUTE_MISC_BUFFER_FLUSHES)
@ -821,6 +822,9 @@ struct iris_context {
/** Are stencil writes enabled? (Stencil buffer may or may not exist.) */
bool stencil_writes_enabled;
/** Current/upcoming ds_write_state for Wa_18019816803. */
bool ds_write_state;
/** Do we have integer RT in current framebuffer state? */
bool has_integer_rt;

View file

@ -1682,6 +1682,9 @@ struct iris_depth_stencil_alpha_state {
/** Outbound to Gfx8-9 PMA stall equations */
bool depth_test_enabled;
/** Tracking state of DS writes for Wa_18019816803. */
bool ds_write_state;
};
/**
@ -1699,6 +1702,46 @@ iris_create_zsa_state(struct pipe_context *ctx,
bool two_sided_stencil = state->stencil[1].enabled;
bool depth_write_enabled = false;
bool stencil_write_enabled = false;
/* Depth writes enabled? */
if (state->depth_writemask &&
((!state->depth_enabled) ||
((state->depth_func != PIPE_FUNC_NEVER) &&
(state->depth_func != PIPE_FUNC_EQUAL))))
depth_write_enabled = true;
bool stencil_all_keep =
state->stencil[0].fail_op == PIPE_STENCIL_OP_KEEP &&
state->stencil[0].zfail_op == PIPE_STENCIL_OP_KEEP &&
state->stencil[0].zpass_op == PIPE_STENCIL_OP_KEEP &&
(!two_sided_stencil ||
(state->stencil[1].fail_op == PIPE_STENCIL_OP_KEEP &&
state->stencil[1].zfail_op == PIPE_STENCIL_OP_KEEP &&
state->stencil[1].zpass_op == PIPE_STENCIL_OP_KEEP));
bool stencil_mask_zero =
state->stencil[0].writemask == 0 ||
(!two_sided_stencil || state->stencil[1].writemask == 0);
bool stencil_func_never =
state->stencil[0].func == PIPE_FUNC_NEVER &&
state->stencil[0].fail_op == PIPE_STENCIL_OP_KEEP &&
(!two_sided_stencil ||
(state->stencil[1].func == PIPE_FUNC_NEVER &&
state->stencil[1].fail_op == PIPE_STENCIL_OP_KEEP));
/* Stencil writes enabled? */
if (state->stencil[0].writemask != 0 ||
((two_sided_stencil && state->stencil[1].writemask != 0) &&
(!stencil_all_keep &&
!stencil_mask_zero &&
!stencil_func_never)))
stencil_write_enabled = true;
cso->ds_write_state = depth_write_enabled || stencil_write_enabled;
cso->alpha_enabled = state->alpha_enabled;
cso->alpha_func = state->alpha_func;
cso->alpha_ref_value = state->alpha_ref_value;
@ -1781,6 +1824,12 @@ iris_bind_zsa_state(struct pipe_context *ctx, void *state)
ice->state.depth_writes_enabled = new_cso->depth_writes_enabled;
ice->state.stencil_writes_enabled = new_cso->stencil_writes_enabled;
/* State ds_write_enable changed, need to flag dirty DS. */
if (!old_cso || (ice->state.ds_write_state != new_cso->ds_write_state)) {
ice->state.dirty |= IRIS_DIRTY_DS_WRITE_ENABLE;
ice->state.ds_write_state = new_cso->ds_write_state;
}
#if GFX_VER >= 12
if (cso_changed(depth_bounds))
ice->state.dirty |= IRIS_DIRTY_DEPTH_BOUNDS;
@ -7085,6 +7134,14 @@ iris_upload_dirty_render_state(struct iris_context *ice,
iris_batch_emit(batch, cso->wmds, sizeof(cso->wmds));
#endif
/* Depth or stencil write changed in cso. */
if (intel_needs_workaround(batch->screen->devinfo, 18019816803) &&
(dirty & IRIS_DIRTY_DS_WRITE_ENABLE)) {
iris_emit_pipe_control_flush(
batch, "workaround: PSS stall after DS write enable change",
PIPE_CONTROL_PSS_STALL_SYNC);
}
#if GFX_VER >= 12
iris_batch_emit(batch, cso->depth_bounds, sizeof(cso->depth_bounds));
#endif