From 55508bbe66cdae22cc8ae74f27829fba13f393c7 Mon Sep 17 00:00:00 2001 From: Jason Ekstrand Date: Fri, 4 Sep 2020 12:09:11 -0500 Subject: [PATCH] intel/compiler: Generalize shader relocations a bit This commit adds a delta to be added to the relocated value as well as the possibility of multiple types of relocations. Reviewed-by: Lionel Landwerlin Part-of: --- src/intel/compiler/brw_compiler.c | 11 +++++++++-- src/intel/compiler/brw_compiler.h | 17 ++++++++++++++--- src/intel/compiler/brw_eu.h | 3 +++ src/intel/compiler/brw_eu_emit.c | 31 +++++++++++++++++++++---------- 4 files changed, 47 insertions(+), 15 deletions(-) diff --git a/src/intel/compiler/brw_compiler.c b/src/intel/compiler/brw_compiler.c index 5ec16f958cf..6816424b88c 100644 --- a/src/intel/compiler/brw_compiler.c +++ b/src/intel/compiler/brw_compiler.c @@ -284,10 +284,17 @@ brw_write_shader_relocs(const struct intel_device_info *devinfo, { for (unsigned i = 0; i < prog_data->num_relocs; i++) { assert(prog_data->relocs[i].offset % 8 == 0); - brw_inst *inst = (brw_inst *)(program + prog_data->relocs[i].offset); + void *dst = program + prog_data->relocs[i].offset; for (unsigned j = 0; j < num_values; j++) { if (prog_data->relocs[i].id == values[j].id) { - brw_update_reloc_imm(devinfo, inst, values[j].value); + uint32_t value = values[j].value + prog_data->relocs[i].delta; + switch (prog_data->relocs[i].type) { + case BRW_SHADER_RELOC_TYPE_MOV_IMM: + brw_update_reloc_imm(devinfo, dst, value); + break; + default: + unreachable("Invalid relocation type"); + } break; } } diff --git a/src/intel/compiler/brw_compiler.h b/src/intel/compiler/brw_compiler.h index 65a0b57af8b..1a01f49c20d 100644 --- a/src/intel/compiler/brw_compiler.h +++ b/src/intel/compiler/brw_compiler.h @@ -680,6 +680,11 @@ enum brw_shader_reloc_id { BRW_SHADER_RELOC_CONST_DATA_ADDR_HIGH, }; +enum brw_shader_reloc_type { + /** A MOV instruction with an immediate source */ + BRW_SHADER_RELOC_TYPE_MOV_IMM, +}; + /** Represents a code relocation * * Relocatable constants are immediates in the code which we want to be able @@ -689,12 +694,18 @@ struct brw_shader_reloc { /** The 32-bit ID of the relocatable constant */ uint32_t id; - /** The offset in the shader to the relocatable instruction + /** Type of this relocation */ + enum brw_shader_reloc_type type; + + /** The offset in the shader to the relocated value * - * This is the offset to the instruction rather than the immediate value - * itself. This allows us to do some sanity checking while we relocate. + * For MOV_IMM relocs, this is an offset to the MOV instruction. This + * allows us to do some sanity checking while we update the value. */ uint32_t offset; + + /** Value to be added to the relocated value before it is written */ + uint32_t delta; }; /** A value to write to a relocation */ diff --git a/src/intel/compiler/brw_eu.h b/src/intel/compiler/brw_eu.h index 4e2814e162e..82b06a55e23 100644 --- a/src/intel/compiler/brw_eu.h +++ b/src/intel/compiler/brw_eu.h @@ -200,6 +200,9 @@ void brw_realign(struct brw_codegen *p, unsigned align); int brw_append_data(struct brw_codegen *p, void *data, unsigned size, unsigned align); brw_inst *brw_next_insn(struct brw_codegen *p, unsigned opcode); +void brw_add_reloc(struct brw_codegen *p, uint32_t id, + enum brw_shader_reloc_type type, + uint32_t offset, uint32_t delta); void brw_set_dest(struct brw_codegen *p, brw_inst *insn, struct brw_reg dest); void brw_set_src0(struct brw_codegen *p, brw_inst *insn, struct brw_reg reg); diff --git a/src/intel/compiler/brw_eu_emit.c b/src/intel/compiler/brw_eu_emit.c index b8187e02463..ba73c0049ef 100644 --- a/src/intel/compiler/brw_eu_emit.c +++ b/src/intel/compiler/brw_eu_emit.c @@ -706,6 +706,25 @@ brw_next_insn(struct brw_codegen *p, unsigned opcode) return insn; } +void +brw_add_reloc(struct brw_codegen *p, uint32_t id, + enum brw_shader_reloc_type type, + uint32_t offset, uint32_t delta) +{ + if (p->num_relocs + 1 > p->reloc_array_size) { + p->reloc_array_size = MAX2(16, p->reloc_array_size * 2); + p->relocs = reralloc(p->mem_ctx, p->relocs, + struct brw_shader_reloc, p->reloc_array_size); + } + + p->relocs[p->num_relocs++] = (struct brw_shader_reloc) { + .id = id, + .type = type, + .offset = offset, + .delta = delta, + }; +} + static brw_inst * brw_alu1(struct brw_codegen *p, unsigned opcode, struct brw_reg dest, struct brw_reg src) @@ -3690,16 +3709,8 @@ brw_MOV_reloc_imm(struct brw_codegen *p, assert(type_sz(src_type) == 4); assert(type_sz(dst.type) == 4); - if (p->num_relocs + 1 > p->reloc_array_size) { - p->reloc_array_size = MAX2(16, p->reloc_array_size * 2); - p->relocs = reralloc(p->mem_ctx, p->relocs, - struct brw_shader_reloc, p->reloc_array_size); - } - - p->relocs[p->num_relocs++] = (struct brw_shader_reloc) { - .id = id, - .offset = p->next_insn_offset, - }; + brw_add_reloc(p, id, BRW_SHADER_RELOC_TYPE_MOV_IMM, + p->next_insn_offset, 0); brw_MOV(p, dst, retype(brw_imm_ud(DEFAULT_PATCH_IMM), src_type)); }