diff options
Diffstat (limited to 'hdl/core')
-rw-r--r-- | hdl/core/jump_ctl.py | 73 |
1 files changed, 73 insertions, 0 deletions
diff --git a/hdl/core/jump_ctl.py b/hdl/core/jump_ctl.py new file mode 100644 index 0000000..4dd037b --- /dev/null +++ b/hdl/core/jump_ctl.py @@ -0,0 +1,73 @@ +from amaranth import * +from amaranth.sim import Simulator, Settle, Delay +from enum import Enum, unique + +from hdl.utils import cmd, step, sim +from hdl.lib.in_out_buff import InOutBuff # used for timing analysis + +from hdl.core.alu import ALUFlags, ALU + +@unique +class JumpOpCodes(Enum): + j_eq = 0 + j_ne = 1 + j_lt_u = 2 + j_lte_u = 3 + j_lt_s = 4 + j_lte_s = 5 + +class HDL(Elaboratable): + def __init__(self, **kargs): + + self.alu_flags = Signal(ALU().alu_flags.width, reset_less=True) + self.jump_op = Signal(3, reset_less=True) + + self.jump = Signal(reset_less=True) # true if jump condition is met + + ports_in = [self.alu_flags, self.jump_op] + ports_out = [self.jump] + self.ports = {'in': ports_in, 'out': ports_out} + + self.sim = kargs["sim"] if "sim" in kargs else False + + def elaborate(self, platform=None): + m = Module() + + # dummy sync for simulation only needed if there is no other sequential logic + if self.sim == True: + dummy = Signal() + m.d.sync += dummy.eq(~dummy) + + with m.Switch(self.jump_op): + with m.Case(JumpOpCodes.j_eq.value): + m.d.comb += self.jump.eq(self.alu_flags[ALUFlags.zero]) + with m.Case(JumpOpCodes.j_ne.value): + m.d.comb += self.jump.eq(~self.alu_flags[ALUFlags.zero]) + with m.Case(JumpOpCodes.j_lt_u.value): + m.d.comb += self.jump.eq(self.alu_flags[ALUFlags.negative] & ~self.alu_flags[ALUFlags.zero]) + with m.Case(JumpOpCodes.j_lte_u.value): + m.d.comb += self.jump.eq(self.alu_flags[ALUFlags.negative] | self.alu_flags[ALUFlags.zero]) + with m.Case(JumpOpCodes.j_lt_s.value): + pass + with m.Case(JumpOpCodes.j_lte_s.value): + pass + with m.Case(): + m.d.comb += self.jump.eq(0) + + return m + + +# test addition +def test_hdl(): + dut = HDL(sim=True) + def proc(): + yield from step #step clock + yield Settle() #needed if for combinatorial logic + yield dut.something #read value + sim(dut, proc) + + + +if __name__ == '__main__': + hdl = InOutBuff(HDL()) + cmd(hdl) |