vc4: Add WIP support for varyings.
authorEric Anholt <eric@anholt.net>
Fri, 4 Jul 2014 16:38:44 +0000 (09:38 -0700)
committerEric Anholt <eric@anholt.net>
Sat, 9 Aug 2014 01:59:46 +0000 (18:59 -0700)
It doesn't do all the interpolation yet, but more tests can run now.

v2: Rebase on helpers.

src/gallium/drivers/vc4/vc4_context.h
src/gallium/drivers/vc4/vc4_draw.c
src/gallium/drivers/vc4/vc4_program.c
src/gallium/drivers/vc4/vc4_qir.c
src/gallium/drivers/vc4/vc4_qir.h
src/gallium/drivers/vc4/vc4_qpu_emit.c

index 8258d3046c0984cf4efd93d66ae40aaaf4c0fa49..f36b96b0c25ee2fa31d8442f89c779032a8a793b 100644 (file)
@@ -80,6 +80,7 @@ struct vc4_compiled_shader {
         struct vc4_shader_uniform_info uniforms[2];
 
         uint32_t coord_shader_offset;
+        uint8_t num_inputs;
 };
 
 struct vc4_program_stateobj {
index 10b5deb560e1a92a9c27b18a051ed615bb33adad..d315f40ed2040d3ac043de6e7252d3d1b29c6dcf 100644 (file)
@@ -177,7 +177,7 @@ vc4_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
         cl_start_shader_reloc(&vc4->shader_rec, 7);
         cl_u16(&vc4->shader_rec, VC4_SHADER_FLAG_ENABLE_CLIPPING);
         cl_u8(&vc4->shader_rec, 0); /* fs num uniforms (unused) */
-        cl_u8(&vc4->shader_rec, 0); /* fs num varyings */
+        cl_u8(&vc4->shader_rec, vc4->prog.fs->num_inputs);
         cl_reloc(vc4, &vc4->shader_rec, vc4->prog.fs->bo, 0);
         cl_reloc(vc4, &vc4->shader_rec, fs_ubo, fs_ubo_offset);
 
index 0b3cfb400af9edadc30a31065a498c2ac24e0a33..12d188185cd3e4613fce034176fe1ce573201d12 100644 (file)
@@ -53,6 +53,8 @@ struct tgsi_to_qir {
         uint32_t *uniform_data;
         enum quniform_contents *uniform_contents;
         uint32_t num_uniforms;
+        uint32_t num_inputs;
+        uint32_t num_outputs;
 };
 
 struct vc4_key {
@@ -184,6 +186,8 @@ update_dst(struct tgsi_to_qir *trans, struct tgsi_full_instruction *tgsi_inst,
                 break;
         case TGSI_FILE_OUTPUT:
                 trans->outputs[tgsi_dst->Index * 4 + i] = val;
+                trans->num_outputs = MAX2(trans->num_outputs,
+                                          tgsi_dst->Index * 4 + i + 1);
                 break;
         default:
                 fprintf(stderr, "unknown dst file %d\n", tgsi_dst->File);
@@ -265,6 +269,38 @@ tgsi_to_qir_abs(struct tgsi_to_qir *trans,
         return qir_FMAXABS(c, arg, arg);
 }
 
+static void
+emit_tgsi_declaration(struct tgsi_to_qir *trans,
+                      struct tgsi_full_declaration *decl)
+{
+        struct qcompile *c = trans->c;
+
+        switch (decl->Declaration.File) {
+        case TGSI_FILE_INPUT:
+                if (c->stage == QSTAGE_FRAG) {
+                        for (int index = decl->Range.First;
+                             index <= decl->Range.Last;
+                             index++) {
+                                for (int i = 0; i < 4; i++) {
+                                        struct qreg vary = {
+                                                QFILE_VARY,
+                                                index * 4 + i
+                                        };
+
+                                        /* XXX: multiply by W */
+                                        trans->inputs[index * 4 + i] =
+                                                qir_VARY_ADD_C(c,
+                                                               qir_MOV(c,
+                                                                       vary));
+
+                                        trans->num_inputs++;
+                                }
+                        }
+                }
+                break;
+        }
+}
+
 static void
 emit_tgsi_instruction(struct tgsi_to_qir *trans,
                       struct tgsi_full_instruction *tgsi_inst)
@@ -356,11 +392,6 @@ parse_tgsi_immediate(struct tgsi_to_qir *trans, struct tgsi_full_immediate *imm)
 static void
 emit_frag_init(struct tgsi_to_qir *trans)
 {
-        /* XXX: lols */
-        for (int i = 0; i < 4; i++) {
-                trans->inputs[i] = qir_uniform_ui(trans, fui(1.0));
-        }
-
 }
 
 static void
@@ -453,10 +484,15 @@ emit_1_wc_write(struct tgsi_to_qir *trans)
 static void
 emit_vert_end(struct tgsi_to_qir *trans)
 {
+        struct qcompile *c = trans->c;
+
         emit_scaled_viewport_write(trans);
         emit_zs_write(trans);
         emit_1_wc_write(trans);
-        /* XXX: write varyings */
+
+        for (int i = 4; i < trans->num_outputs; i++) {
+                qir_VPM_WRITE(c, trans->outputs[i]);
+        }
 }
 
 static void
@@ -523,6 +559,11 @@ vc4_shader_tgsi_to_qir(struct vc4_compiled_shader *shader, enum qstage stage,
                 tgsi_parse_token(&trans->parser);
 
                 switch (trans->parser.FullToken.Token.Type) {
+                case TGSI_TOKEN_TYPE_DECLARATION:
+                        emit_tgsi_declaration(trans,
+                                              &trans->parser.FullToken.FullDeclaration);
+                        break;
+
                 case TGSI_TOKEN_TYPE_INSTRUCTION:
                         emit_tgsi_instruction(trans,
                                               &trans->parser.FullToken.FullInstruction);
@@ -603,8 +644,8 @@ vc4_fs_compile(struct vc4_context *vc4, struct vc4_compiled_shader *shader,
 {
         struct tgsi_to_qir *trans = vc4_shader_tgsi_to_qir(shader, QSTAGE_FRAG,
                                                            &key->base);
+        shader->num_inputs = trans->num_inputs;
         copy_uniform_state_to_shader(shader, 0, trans);
-
         shader->bo = vc4_bo_alloc_mem(vc4->screen, trans->c->qpu_insts,
                                       trans->c->num_qpu_insts * sizeof(uint64_t),
                                       "fs_code");
index 4ee1f018fc547277dffa85637cf6b66429d7ae74..02342f212c317edcc0734f1bc1875f613a3520c4 100644 (file)
@@ -59,6 +59,7 @@ static const struct qir_op_info qir_op_info[] = {
         [QOP_VPM_WRITE] = { "vpm_write", 0, 1 },
         [QOP_VPM_READ] = { "vpm_read", 0, 1 },
         [QOP_TLB_COLOR_WRITE] = { "tlb_color", 0, 1 },
+        [QOP_VARY_ADD_C] = { "vary_add_c", 1, 1 },
 };
 
 static const char *
index 4263adcddd1fccfbeb0c16e72c222645dd140ae4..75b1933e6a616bba837957aa10d3909374c30a66 100644 (file)
@@ -68,6 +68,7 @@ enum qop {
         QOP_VPM_WRITE,
         QOP_VPM_READ,
         QOP_TLB_COLOR_WRITE,
+        QOP_VARY_ADD_C,
 };
 
 struct simple_node {
@@ -178,6 +179,7 @@ QIR_ALU1(RSQ)
 QIR_ALU1(EXP2)
 QIR_ALU1(LOG2)
 QIR_ALU2(PACK_SCALED)
+QIR_ALU1(VARY_ADD_C)
 
 static inline void
 qir_VPM_WRITE(struct qcompile *c, struct qreg a)
index 8cb5de15fff4a8fbae7e89afdcab3feb55c1adbc..f02fe822b07b7b8af8592b5bac34845bfa8f4c0a 100644 (file)
@@ -299,6 +299,12 @@ vc4_generate_code(struct qcompile *c)
                                                qpu_m_NOP());
                         break;
 
+                case QOP_VARY_ADD_C:
+                        insts[ni++] = qpu_inst(qpu_a_FADD(dst,
+                                                          src[0], qpu_r5()),
+                                               qpu_m_NOP());
+                        break;
+
                 case QOP_PACK_SCALED:
                         insts[ni++] = qpu_inst(qpu_a_MOV(dst, src[0]),
                                                qpu_m_NOP());