From: Luke Kenneth Casson Leighton Date: Tue, 7 Apr 2020 16:49:46 +0000 (+0100) Subject: add in special regs to be passed out of function (as return results) X-Git-Tag: div_pipeline~1435^2~43 X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=bd55a5c2096d9fdf57703f736b533d625f3591d2;p=soc.git add in special regs to be passed out of function (as return results) --- diff --git a/src/soc/decoder/isa/caller.py b/src/soc/decoder/isa/caller.py index 050e1c85..e3c2ec05 100644 --- a/src/soc/decoder/isa/caller.py +++ b/src/soc/decoder/isa/caller.py @@ -189,10 +189,11 @@ class ISACaller: info = self.instrs[name] yield from self.prep_namespace(info.form, info.op_fields) - input_names = create_args(info.read_regs | info.uninit_regs | - info.special_regs) + # preserve order of register names + input_names = create_args(list(info.read_regs) + list(info.uninit_regs)) print(input_names) + # main registers (RT, RA ...) inputs = [] for name in input_names: regnum = yield getattr(self.decoder, name) @@ -200,18 +201,30 @@ class ISACaller: self.namespace[regname] = regnum print('reading reg %d' % regnum) inputs.append(self.gpr(regnum)) + + # "special" registers + for special in info.special_regs: + inputs.append(self.namespace[special]) + print(inputs) results = info.func(self, *inputs) print(results) + # any modified return results? if info.write_regs: output_names = create_args(info.write_regs) for name, output in zip(output_names, results): - regnum = yield getattr(self.decoder, name) - print('writing reg %d' % regnum) - if output.bits > 64: - output = SelectableInt(output.value, 64) - self.gpr[regnum] = output + if name in info.special_regs: + print('writing special %s' % name, output) + self.namespace[name].eq(output) + else: + regnum = yield getattr(self.decoder, name) + print('writing reg %d' % regnum) + if output.bits > 64: + output = SelectableInt(output.value, 64) + self.gpr[regnum] = output + + # update program counter self.pc.update(self.namespace) diff --git a/src/soc/decoder/isa/test_caller.py b/src/soc/decoder/isa/test_caller.py index 2d2f5bdc..558172bb 100644 --- a/src/soc/decoder/isa/test_caller.py +++ b/src/soc/decoder/isa/test_caller.py @@ -96,7 +96,9 @@ class DecoderTestCase(FHDLTestCase): with Program(lst) as program: sim = self.run_tst_program(program) print ("cr", sim.cr) - self.assertEqual(sim.cr, SelectableInt(0xffffffff, 32)) + self.assertEqual(sim.cr, SelectableInt(0xf, 32)) + print ("cr0", sim.crl[0]) + self.assertTrue(SelectableInt(0xf, 4) == sim.crl[0]) def run_tst_program(self, prog, initial_regs=[0] * 32): simulator = self.run_tst(prog, initial_regs) diff --git a/src/soc/decoder/pseudo/parser.py b/src/soc/decoder/pseudo/parser.py index e413f4d6..b5803d88 100644 --- a/src/soc/decoder/pseudo/parser.py +++ b/src/soc/decoder/pseudo/parser.py @@ -608,6 +608,7 @@ class PowerParser: self.op_fields.add(name) if name in ['CR', 'LR', 'CTR', 'TAR', 'FPSCR']: self.special_regs.add(name) + self.write_regs.add(name) # and add to list to write p[0] = ast.Name(id=name, ctx=ast.Load()) def p_atom_number(self, p): diff --git a/src/soc/decoder/pseudo/pywriter.py b/src/soc/decoder/pseudo/pywriter.py index 6be4ff53..7a1c3f5e 100644 --- a/src/soc/decoder/pseudo/pywriter.py +++ b/src/soc/decoder/pseudo/pywriter.py @@ -55,6 +55,7 @@ class PyISAWriter(ISA): pycode, rused = convert_to_python(pcode, d.form) # create list of arguments to call regs = list(rused['read_regs']) + list(rused['uninit_regs']) + regs += list(rused['special_regs']) args = ', '.join(create_args(regs, 'self')) # create list of arguments to return retargs = ', '.join(create_args(rused['write_regs'])) diff --git a/src/soc/decoder/selectable_int.py b/src/soc/decoder/selectable_int.py index 392e3335..78cccc29 100644 --- a/src/soc/decoder/selectable_int.py +++ b/src/soc/decoder/selectable_int.py @@ -22,6 +22,10 @@ class FieldSelectableInt: br = _br self.br = br # map of indices. + def eq(self, b): + self.si = copy(b.si) + self.br = copy(b.br) + def _op(self, op, b): vi = self.get_range() vi = op(vi, b) @@ -100,6 +104,10 @@ class SelectableInt: self.value = value & mask self.bits = bits + def eq(self, b): + self.value = b.value + self.bits = b.bits + def __add__(self, b): if isinstance(b, int): b = SelectableInt(b, self.bits) @@ -207,6 +215,8 @@ class SelectableInt: self.value = (self.value & ~mask) | (value & mask) def __ge__(self, other): + if isinstance(other, FieldSelectableInt): + other = other.get_range() if isinstance(other, SelectableInt): other = check_extsign(self, other) assert other.bits == self.bits @@ -216,6 +226,8 @@ class SelectableInt: assert False def __le__(self, other): + if isinstance(other, FieldSelectableInt): + other = other.get_range() if isinstance(other, SelectableInt): other = check_extsign(self, other) assert other.bits == self.bits @@ -225,6 +237,8 @@ class SelectableInt: assert False def __gt__(self, other): + if isinstance(other, FieldSelectableInt): + other = other.get_range() if isinstance(other, SelectableInt): other = check_extsign(self, other) assert other.bits == self.bits @@ -234,6 +248,8 @@ class SelectableInt: assert False def __lt__(self, other): + if isinstance(other, FieldSelectableInt): + other = other.get_range() if isinstance(other, SelectableInt): other = check_extsign(self, other) assert other.bits == self.bits @@ -243,6 +259,9 @@ class SelectableInt: assert False def __eq__(self, other): + print ("__eq__", self, other) + if isinstance(other, FieldSelectableInt): + other = other.get_range() if isinstance(other, SelectableInt): other = check_extsign(self, other) assert other.bits == self.bits