r600/sb: handle lds special dest registers.
[mesa.git] / src / gallium / drivers / r600 / eg_asm.c
index 6840cf6f18a32dfe391909b5e6f0a850f83ddc27..f8651bdff58e936864a0f655e3b15150fcbb066d 100644 (file)
@@ -71,9 +71,13 @@ int eg_bytecode_cf_build(struct r600_bytecode *bc, struct r600_bytecode_cf *cf)
                } else if (cfop->flags & CF_CLAUSE) {
                        /* CF_TEX/VTX (CF_ALU already handled above) */
                        bc->bytecode[id++] = S_SQ_CF_WORD0_ADDR(cf->addr >> 1);
-                       bc->bytecode[id++] = S_SQ_CF_WORD1_CF_INST(opcode) |
+                       bc->bytecode[id] = S_SQ_CF_WORD1_CF_INST(opcode) |
                                        S_SQ_CF_WORD1_BARRIER(1) |
+                                       S_SQ_CF_WORD1_VALID_PIXEL_MODE(cf->vpm) |
                                        S_SQ_CF_WORD1_COUNT((cf->ndw / 4) - 1);
+                       if (bc->chip_class == EVERGREEN) /* no EOP on cayman */
+                               bc->bytecode[id] |= S_SQ_CF_ALLOC_EXPORT_WORD1_END_OF_PROGRAM(cf->end_of_program);
+                       id++;
                } else if (cfop->flags & CF_EXP) {
                        /* EXPORT instructions */
                        bc->bytecode[id++] = S_SQ_CF_ALLOC_EXPORT_WORD0_RW_GPR(cf->output.gpr) |
@@ -88,11 +92,31 @@ int eg_bytecode_cf_build(struct r600_bytecode *bc, struct r600_bytecode_cf *cf)
                                        S_SQ_CF_ALLOC_EXPORT_WORD1_SWIZ_SEL_Z(cf->output.swizzle_z) |
                                        S_SQ_CF_ALLOC_EXPORT_WORD1_SWIZ_SEL_W(cf->output.swizzle_w) |
                                        S_SQ_CF_ALLOC_EXPORT_WORD1_BARRIER(cf->barrier) |
+                                       S_SQ_CF_ALLOC_EXPORT_WORD1_MARK(cf->mark) |
                                        S_SQ_CF_ALLOC_EXPORT_WORD1_CF_INST(opcode);
 
                        if (bc->chip_class == EVERGREEN) /* no EOP on cayman */
                                bc->bytecode[id] |= S_SQ_CF_ALLOC_EXPORT_WORD1_END_OF_PROGRAM(cf->end_of_program);
                        id++;
+               } else if (cfop->flags & CF_RAT) {
+                       bc->bytecode[id++] = S_SQ_CF_ALLOC_EXPORT_WORD0_RAT_RAT_ID(cf->rat.id) |
+                                       S_SQ_CF_ALLOC_EXPORT_WORD0_RAT_RAT_INST(cf->rat.inst) |
+                                       S_SQ_CF_ALLOC_EXPORT_WORD0_RAT_RAT_INDEX_MODE(cf->rat.index_mode) |
+                                       S_SQ_CF_ALLOC_EXPORT_WORD0_RW_GPR(cf->output.gpr) |
+                                       S_SQ_CF_ALLOC_EXPORT_WORD0_ELEM_SIZE(cf->output.elem_size) |
+                                       S_SQ_CF_ALLOC_EXPORT_WORD0_TYPE(cf->output.type) |
+                                       S_SQ_CF_ALLOC_EXPORT_WORD0_INDEX_GPR(cf->output.index_gpr);
+                       bc->bytecode[id] = S_SQ_CF_ALLOC_EXPORT_WORD1_BURST_COUNT(cf->output.burst_count - 1) |
+                                       S_SQ_CF_ALLOC_EXPORT_WORD1_BARRIER(cf->barrier) |
+                                       S_SQ_CF_ALLOC_EXPORT_WORD1_MARK(cf->mark) |
+                                       S_SQ_CF_ALLOC_EXPORT_WORD1_VALID_PIXEL_MODE(cf->vpm) |
+                                       S_SQ_CF_ALLOC_EXPORT_WORD1_CF_INST(opcode) |
+                                       S_SQ_CF_ALLOC_EXPORT_WORD1_BUF_COMP_MASK(cf->output.comp_mask) |
+                                       S_SQ_CF_ALLOC_EXPORT_WORD1_BUF_ARRAY_SIZE(cf->output.array_size);
+                       if (bc->chip_class == EVERGREEN) /* no EOP on cayman */
+                               bc->bytecode[id] |= S_SQ_CF_ALLOC_EXPORT_WORD1_END_OF_PROGRAM(cf->end_of_program);
+                       id++;
+
                } else if (cfop->flags & CF_MEM) {
                        /* MEM_STREAM, MEM_RING instructions */
                        bc->bytecode[id++] = S_SQ_CF_ALLOC_EXPORT_WORD0_RW_GPR(cf->output.gpr) |
@@ -102,6 +126,7 @@ int eg_bytecode_cf_build(struct r600_bytecode *bc, struct r600_bytecode_cf *cf)
                                        S_SQ_CF_ALLOC_EXPORT_WORD0_INDEX_GPR(cf->output.index_gpr);
                        bc->bytecode[id] = S_SQ_CF_ALLOC_EXPORT_WORD1_BURST_COUNT(cf->output.burst_count - 1) |
                                        S_SQ_CF_ALLOC_EXPORT_WORD1_BARRIER(cf->barrier) |
+                                       S_SQ_CF_ALLOC_EXPORT_WORD1_MARK(cf->mark) |
                                        S_SQ_CF_ALLOC_EXPORT_WORD1_CF_INST(opcode) |
                                        S_SQ_CF_ALLOC_EXPORT_WORD1_BUF_COMP_MASK(cf->output.comp_mask) |
                                        S_SQ_CF_ALLOC_EXPORT_WORD1_BUF_ARRAY_SIZE(cf->output.array_size);
@@ -111,12 +136,14 @@ int eg_bytecode_cf_build(struct r600_bytecode *bc, struct r600_bytecode_cf *cf)
                } else {
                        /* other instructions */
                        bc->bytecode[id++] = S_SQ_CF_WORD0_ADDR(cf->cf_addr >> 1);
-                       bc->bytecode[id++] =  S_SQ_CF_WORD1_CF_INST(opcode)|
+                       bc->bytecode[id] = S_SQ_CF_WORD1_CF_INST(opcode) |
                                        S_SQ_CF_WORD1_BARRIER(1) |
                                        S_SQ_CF_WORD1_COND(cf->cond) |
                                        S_SQ_CF_WORD1_POP_COUNT(cf->pop_count) |
-                                       S_SQ_CF_WORD1_COUNT(cf->count) |
-                                       S_SQ_CF_WORD1_END_OF_PROGRAM(cf->end_of_program);
+                                       S_SQ_CF_WORD1_COUNT(cf->count);
+                       if (bc->chip_class == EVERGREEN) /* no EOP on cayman */
+                               bc->bytecode[id] |= S_SQ_CF_ALLOC_EXPORT_WORD1_END_OF_PROGRAM(cf->end_of_program);
+                       id++;
                }
        }
        return 0;
@@ -198,9 +225,10 @@ int eg_bytecode_gds_build(struct r600_bytecode *bc, struct r600_bytecode_gds *gd
 {
        unsigned gds_op = (r600_isa_fetch_opcode(bc->isa->hw_class, gds->op) >> 8) & 0x3f;
        unsigned opcode;
-       if (gds->op == FETCH_OP_TF_WRITE)
+       if (gds->op == FETCH_OP_TF_WRITE) {
                opcode = 5;
-       else
+               gds_op = 0;
+       } else
                opcode = 4;
        bc->bytecode[id++] = S_SQ_MEM_GDS_WORD0_MEM_INST(2) |
                S_SQ_MEM_GDS_WORD0_MEM_OP(opcode) |