From 2ab4e48f9457159087c851f2230c1e642ea65802 Mon Sep 17 00:00:00 2001 From: Eric Anholt Date: Wed, 20 Aug 2014 14:20:17 -0700 Subject: [PATCH] vc4: Fix totally broken assertions about inter-instruction reg conflicts. The spec citation talked about A and B, and I proceeded to pay no attention to whether the waddrs were for A or B. As a result, this pair of instructions would claim to conflict: mov ra4, ra4 ; nop nop, r0, r0 mov.ns ra4, rb4 ; nop nop, r0, r0 --- src/gallium/drivers/vc4/vc4_qpu_validate.c | 21 ++++++++++++++++++--- 1 file changed, 18 insertions(+), 3 deletions(-) diff --git a/src/gallium/drivers/vc4/vc4_qpu_validate.c b/src/gallium/drivers/vc4/vc4_qpu_validate.c index b9f28528c39..d0437332334 100644 --- a/src/gallium/drivers/vc4/vc4_qpu_validate.c +++ b/src/gallium/drivers/vc4/vc4_qpu_validate.c @@ -69,6 +69,12 @@ reads_a_reg(uint64_t inst, uint32_t r) return _reads_reg(inst, r, false, true); } +static bool +reads_b_reg(uint64_t inst, uint32_t r) +{ + return _reads_reg(inst, r, true, false); +} + static bool writes_sfu(uint64_t inst) { @@ -167,10 +173,19 @@ vc4_qpu_validate(uint64_t *insts, uint32_t num_inst) for (int i = 0; i < num_inst - 1; i++) { uint64_t inst = insts[i]; uint32_t add_waddr = QPU_GET_FIELD(inst, QPU_WADDR_ADD); - uint32_t mul_waddr = QPU_GET_FIELD(inst, QPU_WADDR_ADD); + uint32_t mul_waddr = QPU_GET_FIELD(inst, QPU_WADDR_MUL); + uint32_t waddr_a, waddr_b; + + if (inst & QPU_WS) { + waddr_b = add_waddr; + waddr_a = mul_waddr; + } else { + waddr_a = add_waddr; + waddr_b = mul_waddr; + } - assert(add_waddr >= 32 || !reads_reg(insts[i + 1], add_waddr)); - assert(mul_waddr >= 32 || !reads_reg(insts[i + 1], mul_waddr)); + assert(waddr_a >= 32 || !reads_a_reg(insts[i + 1], waddr_a)); + assert(waddr_b >= 32 || !reads_b_reg(insts[i + 1], waddr_b)); } /* "After an SFU lookup instruction, accumulator r4 must not be read -- 2.30.2