mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2026-05-08 09:08:10 +02:00
pan/va: fix FAU validation
Validation was checking that if an instruction was accessing FAU RAM, only one 64-bit slot was accessed, and if it was accessing a FAU special value, only one was accessed, however it was not checking if both RAM and special were used, which is only allowed in messaging instructions except ATEST and BLEND. Fixes Piglit: spec/ati_fragment_shader/ati_fragment_shader-render-ops/mov c0.r Reviewed-by: Alejandro Piñeiro <apinheiro@igalia.com> Reviewed-by: Mary Guillemard <mary.guillemard@collabora.com> Reviewed-by: Lars-Ivar Hesselberg Simonsen <lars-ivar.simonsen@arm.com> Fixes:fd1906afea("pan/va: Add FAU validation") Cc: mesa-stable Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/33608> (cherry picked from commite504825813)
This commit is contained in:
parent
7b38cf8b5e
commit
5e76850ce3
2 changed files with 42 additions and 18 deletions
|
|
@ -904,7 +904,7 @@
|
|||
"description": "pan/va: fix FAU validation",
|
||||
"nominated": true,
|
||||
"nomination_type": 2,
|
||||
"resolution": 0,
|
||||
"resolution": 1,
|
||||
"main_sha": null,
|
||||
"because_sha": "fd1906afea59073780939810e0e46094264677d3",
|
||||
"notes": null
|
||||
|
|
|
|||
|
|
@ -60,18 +60,16 @@ fau_state_buffer(struct fau_state *fau, bi_index idx)
|
|||
return false;
|
||||
}
|
||||
|
||||
/* Instructions executed in the execution engine may only encode one FAU index.
|
||||
* Instructions executed by the message unit may encode two FAU indices,
|
||||
* except for ATEST and BLEND which may sometimes run in the execution engine.
|
||||
*/
|
||||
static bool
|
||||
fau_state_uniform(struct fau_state *fau, bi_index idx)
|
||||
can_use_two_fau_indices(enum bi_opcode op)
|
||||
{
|
||||
/* Each slot is 64-bits. The low/high half is encoded as the offset of the
|
||||
* bi_index, which we want to ignore.
|
||||
*/
|
||||
unsigned slot = (idx.value & 63);
|
||||
|
||||
if (fau->uniform_slot < 0)
|
||||
fau->uniform_slot = slot;
|
||||
|
||||
return fau->uniform_slot == slot;
|
||||
return bi_opcode_props[op].message != BIFROST_MESSAGE_NONE &&
|
||||
op != BI_OPCODE_ATEST &&
|
||||
op != BI_OPCODE_BLEND;
|
||||
}
|
||||
|
||||
static bool
|
||||
|
|
@ -81,7 +79,32 @@ fau_is_special(enum bir_fau fau)
|
|||
}
|
||||
|
||||
static bool
|
||||
fau_state_special(struct fau_state *fau, bi_index idx)
|
||||
fau_state_uniform(struct fau_state *fau, bi_index idx, enum bi_opcode op)
|
||||
{
|
||||
/* Each slot is 64-bits. The low/high half is encoded as the offset of the
|
||||
* bi_index, which we want to ignore.
|
||||
*/
|
||||
unsigned slot = (idx.value & 63);
|
||||
|
||||
if (fau->uniform_slot < 0)
|
||||
fau->uniform_slot = slot;
|
||||
|
||||
if (fau->uniform_slot != slot)
|
||||
return false;
|
||||
|
||||
if (!can_use_two_fau_indices(op)) {
|
||||
for (unsigned i = 0; i < ARRAY_SIZE(fau->buffer); ++i) {
|
||||
bi_index buf = fau->buffer[i];
|
||||
if (!bi_is_null(buf) && fau_is_special(buf.value))
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool
|
||||
fau_state_special(struct fau_state *fau, bi_index idx, enum bi_opcode op)
|
||||
{
|
||||
for (unsigned i = 0; i < ARRAY_SIZE(fau->buffer); ++i) {
|
||||
bi_index buf = fau->buffer[i];
|
||||
|
|
@ -91,11 +114,12 @@ fau_state_special(struct fau_state *fau, bi_index idx)
|
|||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
return fau->uniform_slot == -1 || can_use_two_fau_indices(op);
|
||||
}
|
||||
|
||||
static bool
|
||||
valid_src(struct fau_state *fau, unsigned fau_page, bi_index src)
|
||||
valid_src(struct fau_state *fau, unsigned fau_page, bi_index src,
|
||||
enum bi_opcode op)
|
||||
{
|
||||
if (src.type != BI_INDEX_FAU)
|
||||
return true;
|
||||
|
|
@ -104,9 +128,9 @@ valid_src(struct fau_state *fau, unsigned fau_page, bi_index src)
|
|||
valid &= fau_state_buffer(fau, src);
|
||||
|
||||
if (src.value & BIR_FAU_UNIFORM)
|
||||
valid &= fau_state_uniform(fau, src);
|
||||
valid &= fau_state_uniform(fau, src, op);
|
||||
else if (fau_is_special(src.value))
|
||||
valid &= fau_state_special(fau, src);
|
||||
valid &= fau_state_special(fau, src, op);
|
||||
|
||||
return valid;
|
||||
}
|
||||
|
|
@ -119,7 +143,7 @@ va_validate_fau(bi_instr *I)
|
|||
unsigned fau_page = va_select_fau_page(I);
|
||||
|
||||
bi_foreach_src(I, s) {
|
||||
valid &= valid_src(&fau, fau_page, I->src[s]);
|
||||
valid &= valid_src(&fau, fau_page, I->src[s], I->op);
|
||||
}
|
||||
|
||||
return valid;
|
||||
|
|
@ -135,7 +159,7 @@ va_repair_fau(bi_builder *b, bi_instr *I)
|
|||
struct fau_state push = fau;
|
||||
bi_index src = I->src[s];
|
||||
|
||||
if (!valid_src(&fau, fau_page, src)) {
|
||||
if (!valid_src(&fau, fau_page, src, I->op)) {
|
||||
bi_replace_src(I, s, bi_mov_i32(b, bi_strip_index(src)));
|
||||
|
||||
/* Rollback update. Since the replacement move doesn't affect FAU
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue