From: Alyssa Rosenzweig Date: Tue, 11 Jun 2019 14:41:09 +0000 (-0700) Subject: panfrost/midgard: Decode LOD/bias registers X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=d7ad29ce25428be563a0d6204c419cc39b112d07;p=mesa.git panfrost/midgard: Decode LOD/bias registers For constant LODs/biases, we can use an immediate embedded in the texture (already decoded); for non-constant, we have to use a register squeezed into the usual immediate field, which is decoded here. Signed-off-by: Alyssa Rosenzweig --- diff --git a/src/gallium/drivers/panfrost/midgard/disassemble.c b/src/gallium/drivers/panfrost/midgard/disassemble.c index f1139f40b27..501846fab1c 100644 --- a/src/gallium/drivers/panfrost/midgard/disassemble.c +++ b/src/gallium/drivers/panfrost/midgard/disassemble.c @@ -1175,9 +1175,27 @@ print_texture_word(uint32_t *word, unsigned tabs) printf(", "); } + char lod_operand = texture_op_takes_bias(texture->op) ? '+' : '='; + if (texture->lod_register) { - /* TODO: Decode */ - printf("lod/bias/grad reg 0x%X (%X), ", texture->bias, texture->bias_int); + midgard_tex_register_select sel; + uint8_t raw = texture->bias; + memcpy(&sel, &raw, sizeof(raw)); + + unsigned c = (sel.component_hi << 1) | sel.component_lo; + + printf("lod %c ", lod_operand); + print_texture_reg(sel.full, sel.select, sel.upper); + printf(".%c, ", components[c]); + + if (!sel.component_hi) + printf(" /* gradient? */"); + + if (texture->bias_int) + printf(" /* bias_int = 0x%X */", texture->bias_int); + + if (sel.zero) + printf(" /* sel.zero = 0x%X */", sel.zero); } else if (texture->op == TEXTURE_OP_TEXEL_FETCH) { /* For texel fetch, the int LOD is in the fractional place and * there is no fraction / possibility of bias. We *always* have diff --git a/src/gallium/drivers/panfrost/midgard/midgard.h b/src/gallium/drivers/panfrost/midgard/midgard.h index 532734820e9..79933973b25 100644 --- a/src/gallium/drivers/panfrost/midgard/midgard.h +++ b/src/gallium/drivers/panfrost/midgard/midgard.h @@ -489,6 +489,37 @@ __attribute__((__packed__)) } midgard_load_store; +/* 8-bit register selector used in texture ops to select a bias/LOD/gradient + * register, shoved into the `bias` field */ + +typedef struct +__attribute__((__packed__)) +{ + /* Combines with component_hi to form 2-bit component select out of + * xyzw, as the component for bias/LOD and the starting component of a + * gradient vector */ + + unsigned component_lo : 1; + + /* Register select between r28/r29 */ + unsigned select : 1; + + /* For a half-register, selects the upper half */ + unsigned upper : 1; + + /* Specifies a full-register, clear for a half-register. Mutually + * exclusive with upper. */ + unsigned full : 1; + + /* Higher half of component_lo. Always seen to be set for LOD/bias + * and clear for processed gradients, but I'm not sure if that's a + * hardware requirement. */ + unsigned component_hi : 1; + + /* Padding to make this 8-bit */ + unsigned zero : 3; +} midgard_tex_register_select; + /* Texture pipeline results are in r28-r29 */ #define REG_TEX_BASE 28 @@ -572,10 +603,14 @@ __attribute__((__packed__)) signed offset_y : 4; signed offset_z : 4; - /* Texture bias or LOD, depending on whether it is executed in a - * fragment/vertex shader respectively. Compute as int(2^8 * biasf). + /* In immediate bias mode, for a normal texture op, this is + * texture bias, computed as int(2^8 * frac(biasf)), with + * bias_int = floor(bias). For a textureLod, it's that, but + * s/bias/lod. For a texel fetch, this is the LOD as-is. * - * For texel fetch, this is the LOD as is. */ + * In register mode, this is a midgard_tex_register_select + * structure and bias_int is zero */ + unsigned bias : 8; unsigned bias_int : 8;