From 88bc5baa00c632c2411304b2c7e5cc49f882c30e Mon Sep 17 00:00:00 2001 From: Eric Anholt Date: Fri, 1 Aug 2014 12:50:53 -0700 Subject: vc4: Add support for swizzles of 32 bit float vertex attributes. Some tests start working (useprogram-flushverts, for example) due to getitng the right vertices now. Some that used to pass start failing with memory overflow during binning, which is weird (glsl-fs-texture2drect). And a couple stop rendering correctly (glsl-fs-bug25902). v2: Move the attribute format setup in the key from after search time to before the search. v3: Fix reading of attributes other than position (I forgot to respect attr and stored everything in inputs 0-3, i.e. position). --- src/gallium/drivers/vc4/vc4_program.c | 88 +++++++++++++++++++++++++++++------ 1 file changed, 73 insertions(+), 15 deletions(-) (limited to 'src/gallium/drivers/vc4/vc4_program.c') diff --git a/src/gallium/drivers/vc4/vc4_program.c b/src/gallium/drivers/vc4/vc4_program.c index 8c0b241d7ef..5d640f45321 100644 --- a/src/gallium/drivers/vc4/vc4_program.c +++ b/src/gallium/drivers/vc4/vc4_program.c @@ -369,6 +369,64 @@ tgsi_to_qir_abs(struct tgsi_to_qir *trans, return qir_FMAXABS(c, arg, arg); } +static void +emit_vertex_input(struct tgsi_to_qir *trans, int attr) +{ + enum pipe_format format = trans->vs_key->attr_formats[attr]; + struct qcompile *c = trans->c; + struct qreg vpm_reads[4]; + + /* Right now, we're setting the VPM offsets to be 16 bytes wide every + * time, so we always read 4 32-bit VPM entries. + */ + for (int i = 0; i < 4; i++) { + vpm_reads[i] = qir_get_temp(c); + qir_emit(c, qir_inst(QOP_VPM_READ, + vpm_reads[i], + c->undef, + c->undef)); + c->num_inputs++; + } + + bool format_warned = false; + const struct util_format_description *desc = + util_format_description(format); + + for (int i = 0; i < 4; i++) { + uint8_t swiz = desc->swizzle[i]; + + switch (swiz) { + case UTIL_FORMAT_SWIZZLE_NONE: + if (!format_warned) { + fprintf(stderr, + "vtx element %d NONE swizzle: %s\n", + attr, util_format_name(format)); + format_warned = true; + } + /* FALLTHROUGH */ + case UTIL_FORMAT_SWIZZLE_0: + trans->inputs[attr * 4 + i] = qir_uniform_ui(trans, 0); + break; + case UTIL_FORMAT_SWIZZLE_1: + trans->inputs[attr * 4 + i] = qir_uniform_ui(trans, + fui(1.0)); + break; + default: + if (!format_warned && + (desc->channel[swiz].type != UTIL_FORMAT_TYPE_FLOAT || + desc->channel[swiz].size != 32)) { + fprintf(stderr, + "vtx element %d unsupported type: %s\n", + attr, util_format_name(format)); + format_warned = true; + } + + trans->inputs[attr * 4 + i] = vpm_reads[swiz]; + break; + } + } +} + static void emit_tgsi_declaration(struct tgsi_to_qir *trans, struct tgsi_full_declaration *decl) @@ -377,28 +435,25 @@ emit_tgsi_declaration(struct tgsi_to_qir *trans, switch (decl->Declaration.File) { case TGSI_FILE_INPUT: - for (int i = decl->Range.First * 4; - i < (decl->Range.Last + 1) * 4; - i++) { - if (c->stage == QSTAGE_FRAG) { + if (c->stage == QSTAGE_FRAG) { + for (int i = decl->Range.First * 4; + i < (decl->Range.Last + 1) * 4; + i++) { struct qreg vary = { QFILE_VARY, i }; - trans->inputs[i] = qir_VARY_ADD_C(c, qir_MOV(c, vary)); - } else { - struct qreg dst = qir_get_temp(c); - /* XXX: attribute type/size/count */ - qir_emit(c, qir_inst(QOP_VPM_READ, - dst, - c->undef, - c->undef)); - trans->inputs[i] = dst; - } - c->num_inputs++; + c->num_inputs++; + } + } else { + for (int i = decl->Range.First; + i <= decl->Range.Last; + i++) { + emit_vertex_input(trans, i); + } } break; } @@ -793,6 +848,9 @@ vc4_update_compiled_vs(struct vc4_context *vc4) memset(key, 0, sizeof(*key)); key->base.shader_state = vc4->prog.bind_vs; + for (int i = 0; i < ARRAY_SIZE(key->attr_formats); i++) + key->attr_formats[i] = vc4->vtx->pipe[i].src_format; + vc4->prog.vs = util_hash_table_get(vc4->vs_cache, key); if (vc4->prog.vs) return; -- cgit v1.2.3