sigh read and write xer detection, fix spr and trap compunit tests
authorLuke Kenneth Casson Leighton <lkcl@lkcl.net>
Sun, 5 Jul 2020 14:16:13 +0000 (15:16 +0100)
committerLuke Kenneth Casson Leighton <lkcl@lkcl.net>
Sun, 5 Jul 2020 14:16:13 +0000 (15:16 +0100)
src/soc/decoder/decode2execute1.py
src/soc/decoder/power_decoder2.py
src/soc/decoder/power_regspec_map.py
src/soc/fu/compunits/test/test_compunit.py
src/soc/fu/compunits/test/test_spr_compunit.py
src/soc/fu/compunits/test/test_trap_compunit.py
src/soc/fu/test/common.py

index 75e29e1ba9532463b47eaa302546aa19f4927ac6..df98c0f4aa0ac7a49648fdcd17626dc1a565eaf9 100644 (file)
@@ -58,6 +58,8 @@ class Decode2ToExecute1Type(RecordObject):
         self.lk = Signal(reset_less=True)
         self.rc = Data(1, "rc")
         self.oe = Data(1, "oe")
+        self.xer_in = Signal(reset_less=True)   # xer might be read
+        self.xer_out = Signal(reset_less=True)  # xer might be written
         self.invert_a = Signal(reset_less=True)
         self.zero_a = Signal(reset_less=True)
         self.invert_out = Signal(reset_less=True)
index 5fd010584d7c296b3ae85401e532ccd9e68a35ba..125fef6767cd5acc421d5a1483c244f36a265b3c 100644 (file)
@@ -642,6 +642,14 @@ class PowerDecode2(Elaboratable):
         comb += e.input_cr.eq(op.cr_in)   # condition reg comes in
         comb += e.output_cr.eq(op.cr_out) # condition reg goes in
 
+        # sigh this is exactly the sort of thing for which the
+        # decoder is designed to not need.  MTSPR, MFSPR and others need
+        # access to the XER bits.  however setting e.oe is not appropriate
+        with m.If(op.internal_op == InternalOp.OP_MFSPR):
+            comb += e.xer_in.eq(1)
+        with m.If(op.internal_op == InternalOp.OP_MTSPR):
+            comb += e.xer_out.eq(1)
+
         # set the trapaddr to 0x700 for a td/tw/tdi/twi operation
         with m.If(op.internal_op == InternalOp.OP_TRAP):
             comb += e.trapaddr.eq(0x70)    # addr=0x700 (strip first nibble)
index 6f461c963408bee852bd6abd3ddf23a5cf634360..51a101de6109e42f6142199788eb24333fe87619 100644 (file)
@@ -68,11 +68,11 @@ def regspec_decode_read(e, regfile, name):
         CA = 1<<XERRegs.CA
         OV = 1<<XERRegs.OV
         if name == 'xer_so':
-            return e.oe.oe[0] & e.oe.oe_ok, SO
+            return (e.oe.oe[0] & e.oe.oe_ok) | e.xer_in, SO
         if name == 'xer_ov':
-            return e.oe.oe[0] & e.oe.oe_ok, OV
+            return (e.oe.oe[0] & e.oe.oe_ok) | e.xer_in, OV
         if name == 'xer_ca':
-            return (e.input_carry == CryIn.CA.value), CA
+            return (e.input_carry == CryIn.CA.value) | e.xer_in, CA
 
     if regfile == 'FAST':
         # FAST register numbering is *unary* encoded
@@ -126,11 +126,11 @@ def regspec_decode_write(e, regfile, name):
         CA = 1<<XERRegs.CA
         OV = 1<<XERRegs.OV
         if name == 'xer_so':
-            return None, SO # hmmm
+            return e.xer_out, SO # hmmm
         if name == 'xer_ov':
-            return None, OV # hmmm
+            return e.xer_out, OV # hmmm
         if name == 'xer_ca':
-            return None, CA # hmmm
+            return e.xer_out, CA # hmmm
 
     if regfile == 'FAST':
         # FAST register numbering is *unary* encoded
index 2cae1bebfc4b19faaeda04a5eb910d67f8e3ad93..79e3c13f95628c93febfe2bacbaf012a5ee7021b 100644 (file)
@@ -61,6 +61,7 @@ def get_cu_output(cu, idx, code):
 
 
 def set_cu_inputs(cu, inp):
+    print ("set_cu_inputs", inp)
     for idx, data in inp.items():
         yield from set_cu_input(cu, idx, data)
 
@@ -224,6 +225,7 @@ class TestRunner(FHDLTestCase):
 
                     # set operand and get inputs
                     yield from set_operand(cu, pdecode2, sim)
+                    yield Settle()
                     iname = yield from self.iodef.get_cu_inputs(pdecode2, sim)
                     inp = get_inp_indexed(cu, iname)
 
index 5fa58b9e26e57d7875c89d6ee542c62d3bd3ad90..8cd528de623419c96ef407e4f76154402641c009 100644 (file)
@@ -1,7 +1,7 @@
 import unittest
 from soc.decoder.power_enums import (XER_bits, Function)
 
-from soc.fu.alu.test.test_pipe_caller import get_cu_inputs
+from soc.fu.spr.test.test_pipe_caller import get_cu_inputs
 from soc.fu.spr.test.test_pipe_caller import SPRTestCase # creates the tests
 
 from soc.fu.test.common import ALUHelpers
index a77c9d1db505266989ca7580d60ea776c06bad5c..9d13e21dc055cd23831b4008b52cf92e38979b06 100644 (file)
@@ -1,7 +1,7 @@
 import unittest
 from soc.decoder.power_enums import (XER_bits, Function)
 
-from soc.fu.alu.test.test_pipe_caller import get_cu_inputs
+from soc.fu.trap.test.test_pipe_caller import get_cu_inputs
 from soc.fu.trap.test.test_pipe_caller import TrapTestCase # creates the tests
 
 from soc.fu.test.common import ALUHelpers
index 519e1108ceef89f10a68d6aaa9b78db960fe68ea..a5c7f816eca27da691a67071b6eef71409fe8584 100644 (file)
@@ -94,7 +94,8 @@ class ALUHelpers:
 
     def get_rd_sim_xer_ca(res, sim, dec2):
         cry_in = yield dec2.e.input_carry
-        if cry_in == CryIn.CA.value:
+        xer_in = yield dec2.e.xer_in
+        if xer_in or cry_in == CryIn.CA.value:
             expected_carry = 1 if sim.spr['XER'][XER_bits['CA']] else 0
             expected_carry32 = 1 if sim.spr['XER'][XER_bits['CA32']] else 0
             res['xer_ca'] = expected_carry | (expected_carry32 << 1)
@@ -231,18 +232,21 @@ class ALUHelpers:
     def get_xer_so(res, alu, dec2):
         oe = yield dec2.e.oe.oe
         oe_ok = yield dec2.e.oe.ok
-        if oe and oe_ok:
+        xer_in = yield dec2.e.xer_in
+        if xer_in or (oe and oe_ok):
             res['xer_so'] = yield alu.n.data_o.xer_so.data[0]
 
     def get_xer_ov(res, alu, dec2):
         oe = yield dec2.e.oe.oe
         oe_ok = yield dec2.e.oe.ok
-        if oe and oe_ok:
+        xer_in = yield dec2.e.xer_in
+        if xer_in or (oe and oe_ok):
             res['xer_ov'] = yield alu.n.data_o.xer_ov.data
 
     def get_xer_ca(res, alu, dec2):
         cry_out = yield dec2.e.output_carry
-        if cry_out:
+        xer_in = yield dec2.e.xer_in
+        if xer_in or (cry_out):
             res['xer_ca'] = yield alu.n.data_o.xer_ca.data
 
     def get_sim_int_o(res, sim, dec2):
@@ -296,7 +300,9 @@ class ALUHelpers:
     def get_sim_xer_ov(res, sim, dec2):
         oe = yield dec2.e.oe.oe
         oe_ok = yield dec2.e.oe.ok
-        if oe and oe_ok:
+        xer_in = yield dec2.e.xer_in
+        print ("get_sim_xer_ov", xer_in)
+        if xer_in or (oe and oe_ok):
             expected_ov = 1 if sim.spr['XER'][XER_bits['OV']] else 0
             expected_ov32 = 1 if sim.spr['XER'][XER_bits['OV32']] else 0
             res['xer_ov'] = expected_ov | (expected_ov32 << 1)
@@ -304,7 +310,8 @@ class ALUHelpers:
     def get_sim_xer_so(res, sim, dec2):
         oe = yield dec2.e.oe.oe
         oe_ok = yield dec2.e.oe.ok
-        if oe and oe_ok:
+        xer_in = yield dec2.e.xer_in
+        if xer_in or (oe and oe_ok):
             res['xer_so'] = 1 if sim.spr['XER'][XER_bits['SO']] else 0
 
     def check_slow_spr1(dut, res, sim_o, msg):