From a59050080232f30b72d8c656d39287530fdff04c Mon Sep 17 00:00:00 2001 From: Kenneth Graunke Date: Wed, 13 May 2026 22:17:34 -0700 Subject: [PATCH] jay: Add a GPR_FROM_UGPRS opcode Part-of: --- src/intel/compiler/jay/jay_builder_opcodes.h.py | 2 +- src/intel/compiler/jay/jay_ir.h | 3 +++ src/intel/compiler/jay/jay_opcodes.py | 10 ++++++++++ src/intel/compiler/jay/jay_to_binary.c | 6 ++++++ src/intel/compiler/jay/jay_validate.c | 12 ++++++++++++ 5 files changed, 32 insertions(+), 1 deletion(-) diff --git a/src/intel/compiler/jay/jay_builder_opcodes.h.py b/src/intel/compiler/jay/jay_builder_opcodes.h.py index 735a653f08e..35113aa9bcf 100644 --- a/src/intel/compiler/jay/jay_builder_opcodes.h.py +++ b/src/intel/compiler/jay/jay_builder_opcodes.h.py @@ -58,7 +58,7 @@ TEMPLATE = """ multi_type = len(op.types) > 1 info_size = f'sizeof(jay_{op.name}_info)' if op.extra_struct else '0' operands = ["dst"] + [f"src{i}" for i in range(num_srcs)] - if num_srcs > 0: + if num_srcs > 0 and op.name != 'gpr_from_ugprs': uniform = " && " .join([f"jay_is_uniform(src{i})" for i in range(num_srcs)]) reg_file = f"({uniform}) ? UGPR : GPR" else: diff --git a/src/intel/compiler/jay/jay_ir.h b/src/intel/compiler/jay/jay_ir.h index b952a49df28..f7a564f4444 100644 --- a/src/intel/compiler/jay/jay_ir.h +++ b/src/intel/compiler/jay/jay_ir.h @@ -691,6 +691,9 @@ jay_src_type(const jay_inst *I, unsigned s) if (I->op == JAY_OPCODE_CVT) return jay_cvt_src_type(I); + if (I->op == JAY_OPCODE_GPR_FROM_UGPRS) + return jay_gpr_from_ugprs_src_type(I); + /* 16-bit operand */ if (I->op == JAY_OPCODE_MUL_32X16 && s == 1) return jay_type_resize(I->type, jay_type_size_bits(I->type) / 2); diff --git a/src/intel/compiler/jay/jay_opcodes.py b/src/intel/compiler/jay/jay_opcodes.py index 82a9368850d..10c0d243b72 100644 --- a/src/intel/compiler/jay/jay_opcodes.py +++ b/src/intel/compiler/jay/jay_opcodes.py @@ -161,6 +161,16 @@ op('deswizzle_even', 1, 'f32', 0, ['bool src_hi']) op('lane_id_8', 0, 'u16') op('lane_id_expand', 1, 'u16', 0, ['unsigned width']) +# Fill a scalar GPR from a contiguous UGPR[16] range containing words or bytes. +# src_type can be either U8 or U16 (only). For U8, stride can be 1 or 2, and +# index can be either 0 or 1. For U16, both stride and index must be 0. +op('gpr_from_ugprs', 1, 'u32', 0, [ + 'enum jay_type src_type', + 'uint8_t stride', + 'uint8_t index', + 'uint8_t pad', +]) + # Sample ID calculation op('extract_byte_per_8lanes', 2, 'u32') op('shr_odd_subspans_by_4', 1, 'u16') diff --git a/src/intel/compiler/jay/jay_to_binary.c b/src/intel/compiler/jay/jay_to_binary.c index 7ebfd7575a8..ef04593eb0d 100644 --- a/src/intel/compiler/jay/jay_to_binary.c +++ b/src/intel/compiler/jay/jay_to_binary.c @@ -484,6 +484,12 @@ emit(struct brw_codegen *p, brw_imm_uw(jay_lane_id_expand_width(I))); break; + case JAY_OPCODE_GPR_FROM_UGPRS: + brw_MOV(p, dst, + byte_offset(stride(SRC(0), jay_gpr_from_ugprs_stride(I), 1, 0), + jay_gpr_from_ugprs_index(I))); + break; + case JAY_OPCODE_EXTRACT_BYTE_PER_8LANES: brw_MOV(p, dst, stride(retype(SRC(simd_offs), BRW_TYPE_UB), 1, 8, 0)); break; diff --git a/src/intel/compiler/jay/jay_validate.c b/src/intel/compiler/jay/jay_validate.c index 4bb254627e1..1faeeb7fad1 100644 --- a/src/intel/compiler/jay/jay_validate.c +++ b/src/intel/compiler/jay/jay_validate.c @@ -85,6 +85,10 @@ get_src_words(struct validate_state *validate, jay_inst *I, unsigned s) return 4; } + if (I->op == JAY_OPCODE_GPR_FROM_UGPRS) { + return jay_ugpr_per_grf(validate->func->shader); + } + bool vectorized = I->dst.file == UGPR && jay_num_values(I->dst) > jay_type_vector_length(I->type) && I->op != JAY_OPCODE_SEND && @@ -252,6 +256,14 @@ validate_inst(struct validate_state *validate, jay_inst *I) CHECK(jay_is_flag(I->src[2]) && "SEL src[2] (selector) must be a flag"); } else if (I->op == JAY_OPCODE_SYNC) { CHECK(validate->post_ra && "SYNC does not exist while scheduling"); + } else if (I->op == JAY_OPCODE_GPR_FROM_UGPRS) { + enum jay_type src_type = jay_gpr_from_ugprs_src_type(I); + CHECK(I->dst.file == GPR); + CHECK(I->src[0].file == UGPR); + CHECK(jay_num_values(I->src[0]) == 16); + CHECK(src_type == JAY_TYPE_U8 || src_type == JAY_TYPE_U16); + CHECK(jay_gpr_from_ugprs_stride(I) <= 16 / jay_type_size_bits(src_type)); + CHECK(jay_gpr_from_ugprs_index(I) < 16 / jay_type_size_bits(src_type)); } }