From ded51fd39ec7d2604e51f4013c8a0d92b3c122ac Mon Sep 17 00:00:00 2001 From: Danylo Piliaiev Date: Mon, 15 Nov 2021 17:14:37 +0200 Subject: [PATCH] ir3: Use getfiberid for SubgroupInvocationID on gen4 Since it requires (ss) categorize it as is_sfu() and not is_mem(). Signed-off-by: Danylo Piliaiev Part-of: --- src/freedreno/common/freedreno_dev_info.h | 2 ++ src/freedreno/common/freedreno_devices.py | 1 + src/freedreno/ir3/ir3.h | 4 ++-- src/freedreno/ir3/ir3_compiler.c | 3 +++ src/freedreno/ir3/ir3_compiler.h | 6 ++++++ src/freedreno/ir3/ir3_compiler_nir.c | 6 ++++++ src/freedreno/ir3/ir3_validate.c | 5 +++++ 7 files changed, 25 insertions(+), 2 deletions(-) diff --git a/src/freedreno/common/freedreno_dev_info.h b/src/freedreno/common/freedreno_dev_info.h index 0ba952815e1..14149325637 100644 --- a/src/freedreno/common/freedreno_dev_info.h +++ b/src/freedreno/common/freedreno_dev_info.h @@ -128,6 +128,8 @@ struct fd_dev_info { bool has_lpac; + bool has_getfiberid; + struct { uint32_t RB_UNKNOWN_8E04_blit; uint32_t PC_POWER_CNTL; diff --git a/src/freedreno/common/freedreno_devices.py b/src/freedreno/common/freedreno_devices.py index d787a688d47..5dac42c518c 100644 --- a/src/freedreno/common/freedreno_devices.py +++ b/src/freedreno/common/freedreno_devices.py @@ -265,6 +265,7 @@ a6xx_gen4 = dict( has_8bpp_ubwc = False, has_lpac = True, has_shading_rate = True, + has_getfiberid = True, magic = dict( TPL1_DBG_ECO_CNTL = 0x5008000, ), diff --git a/src/freedreno/ir3/ir3.h b/src/freedreno/ir3/ir3.h index 4e081977295..042715b319c 100644 --- a/src/freedreno/ir3/ir3.h +++ b/src/freedreno/ir3/ir3.h @@ -888,7 +888,7 @@ is_alu(struct ir3_instruction *instr) static inline bool is_sfu(struct ir3_instruction *instr) { - return (opc_cat(instr->opc) == 4); + return (opc_cat(instr->opc) == 4) || instr->opc == OPC_GETFIBERID; } static inline bool @@ -906,7 +906,7 @@ is_tex_or_prefetch(struct ir3_instruction *instr) static inline bool is_mem(struct ir3_instruction *instr) { - return (opc_cat(instr->opc) == 6); + return (opc_cat(instr->opc) == 6) && instr->opc != OPC_GETFIBERID; } static inline bool diff --git a/src/freedreno/ir3/ir3_compiler.c b/src/freedreno/ir3/ir3_compiler.c index bc51e383e62..26b120a87c0 100644 --- a/src/freedreno/ir3/ir3_compiler.c +++ b/src/freedreno/ir3/ir3_compiler.c @@ -129,6 +129,9 @@ ir3_compiler_create(struct fd_device *dev, const struct fd_dev_id *dev_id, compiler->storage_16bit = fd_dev_info(compiler->dev_id)->a6xx.storage_16bit; + + compiler->has_getfiberid = + fd_dev_info(compiler->dev_id)->a6xx.has_getfiberid; } else { compiler->max_const_pipeline = 512; compiler->max_const_geom = 512; diff --git a/src/freedreno/ir3/ir3_compiler.h b/src/freedreno/ir3/ir3_compiler.h index 00715396495..9b2edd3b944 100644 --- a/src/freedreno/ir3/ir3_compiler.h +++ b/src/freedreno/ir3/ir3_compiler.h @@ -160,6 +160,12 @@ struct ir3_compiler { /* True if 16-bit descriptors are used for both 16-bit and 32-bit access. */ bool storage_16bit; + /* True if getfiberid, getlast.w8, brcst.active, and quad_shuffle + * instructions are supported which are necessary to support + * subgroup quad and arithmetic operations. + */ + bool has_getfiberid; + /* Type to use for 1b nir bools: */ type_t bool_type; }; diff --git a/src/freedreno/ir3/ir3_compiler_nir.c b/src/freedreno/ir3/ir3_compiler_nir.c index bb4b6276e5d..b6ba7b90d5d 100644 --- a/src/freedreno/ir3/ir3_compiler_nir.c +++ b/src/freedreno/ir3/ir3_compiler_nir.c @@ -2110,6 +2110,12 @@ emit_intrinsic(struct ir3_context *ctx, nir_intrinsic_instr *intr) case nir_intrinsic_load_work_dim: dst[0] = create_driver_param(ctx, IR3_DP_WORK_DIM); break; + case nir_intrinsic_load_subgroup_invocation: + assert(ctx->compiler->has_getfiberid); + dst[0] = ir3_GETFIBERID(b); + dst[0]->cat6.type = TYPE_U32; + __ssa_dst(dst[0]); + break; case nir_intrinsic_discard_if: case nir_intrinsic_discard: case nir_intrinsic_demote: diff --git a/src/freedreno/ir3/ir3_validate.c b/src/freedreno/ir3/ir3_validate.c index f56e3c0ad9f..f10116a8032 100644 --- a/src/freedreno/ir3/ir3_validate.c +++ b/src/freedreno/ir3/ir3_validate.c @@ -333,6 +333,11 @@ validate_instr(struct ir3_validate_ctx *ctx, struct ir3_instruction *instr) validate_assert(ctx, !(instr->srcs[2]->flags & IR3_REG_HALF)); } break; + case OPC_GETFIBERID: + case OPC_GETSPID: + case OPC_GETWID: + validate_reg_size(ctx, instr->dsts[0], instr->cat6.type); + break; default: validate_reg_size(ctx, instr->dsts[0], instr->cat6.type); validate_assert(ctx, !(instr->srcs[0]->flags & IR3_REG_HALF));