ir3: add support for the ldg.k a1.x addressing mode

We assumed a1.x addressing doesn't work. However, it turns out it
actually does work but instead of taking the offset's hight bits from
a1.x and adding an immediate to the low bits, the full offset is stored
in a1.x and the offset is ignored.

Signed-off-by: Job Noorman <jnoorman@igalia.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/40947>
This commit is contained in:
Job Noorman 2026-04-14 14:41:20 +02:00 committed by Marge Bot
parent bf167ca73b
commit e6529b54c0
3 changed files with 11 additions and 19 deletions

View file

@ -1244,16 +1244,17 @@ emit_intrinsic_copy_global_to_uniform(struct ir3_context *ctx,
unsigned size = nir_intrinsic_range(intr);
unsigned dst = nir_intrinsic_range_base(intr);
unsigned addr_offset = nir_intrinsic_base(intr);
unsigned dst_lo = dst & 0xff;
unsigned dst_hi = dst >> 8;
struct ir3_instruction *a1 = NULL;
if (dst_hi)
a1 = ir3_create_addr1(&ctx->build, dst_hi << 8);
unsigned dst_imm = dst;
if (dst > 256) {
a1 = ir3_create_addr1(&ctx->build, dst);
dst_imm = 0;
}
struct ir3_instruction *addr =
ir3_collect(b, ir3_get_src_shared(ctx, &intr->src[0], true)[0]);
struct ir3_instruction *ldg = ir3_LDG_K(b, create_immed(b, dst_lo), 0, addr, 0,
struct ir3_instruction *ldg = ir3_LDG_K(b, create_immed(b, dst_imm), 0, addr, 0,
create_immed(b, addr_offset), 0,
create_immed(b, size), 0);
ldg->barrier_class = ldg->barrier_conflict = IR3_BARRIER_CONST_W;

View file

@ -408,20 +408,8 @@ copy_global_to_uniform(nir_shader *nir, struct ir3_ubo_analysis_state *state)
unsigned size = (range->end - range->start);
for (unsigned offset = 0; offset < size; offset += 16) {
unsigned const_offset = range->offset / 4 + offset / 4;
if (const_offset < 256) {
nir_copy_global_to_uniform_ir3(b, base,
.base = start + offset,
.range_base = const_offset,
.range = 1);
} else {
/* It seems that the a1.x format doesn't work, so we need to
* decompose the ldg.k into ldg + stc.
*/
nir_def *load =
nir_load_global_ir3(b, 4, 32, base,
nir_imm_int(b, (start + offset) / 4));
nir_store_const_ir3(b, load, .base = const_offset);
}
nir_copy_global_to_uniform_ir3(b, base, .base = start + offset,
.range_base = const_offset, .range = 1);
}
}

View file

@ -220,6 +220,9 @@ TODO rename UAV src to "UAV" so disasm_field_cb can find it easily?
<bitset name="ldg.k" extends="#instruction-cat6-a3xx">
<doc>
LoaD Global Constants
DST: offset into the const file as an immediate or value in a1.x.
The a1.x+offset form is not supported (i.e., the offset is ignored).
</doc>
<gen min="600"/>