1c8a0095967e51f4e9dda213617d4413b67c4cb9
[ieee754fpu.git] / src / scoreboard / dependence_cell.py
1 from nmigen.compat.sim import run_simulation
2 from nmigen.cli import verilog, rtlil
3 from nmigen import Module, Signal, Elaboratable
4 from nmutil.latch import SRLatch
5
6 class DependenceCell(Elaboratable):
7 """ implements 11.4.7 mitch alsup dependence cell, p27
8 """
9 def __init__(self):
10 # inputs
11 self.dest_i = Signal(reset_less=True) # Dest in (top)
12 self.src1_i = Signal(reset_less=True) # oper1 in (top)
13 self.src2_i = Signal(reset_less=True) # oper2 in (top)
14 self.issue_i = Signal(reset_less=True) # Issue in (top)
15
16 self.go_write_i = Signal(reset_less=True) # Go Write in (left)
17 self.go_read_i = Signal(reset_less=True) # Go Read in (left)
18
19 # for Register File Select Lines (vertical)
20 self.dest_rsel_o = Signal(reset_less=True) # dest reg sel (bottom)
21 self.src1_rsel_o = Signal(reset_less=True) # src1 reg sel (bottom)
22 self.src2_rsel_o = Signal(reset_less=True) # src2 reg sel (bottom)
23
24 # for Function Unit "forward progress" (horizontal)
25 self.dest_fwd_o = Signal(reset_less=True) # dest FU fw (right)
26 self.src1_fwd_o = Signal(reset_less=True) # src1 FU fw (right)
27 self.src2_fwd_o = Signal(reset_less=True) # src2 FU fw (right)
28
29 def elaborate(self, platform):
30 m = Module()
31 m.submodules.dest_l = dest_l = SRLatch()
32 m.submodules.src1_l = src1_l = SRLatch()
33 m.submodules.src2_l = src2_l = SRLatch()
34
35 # destination latch: reset on go_write HI, set on dest and issue
36 m.d.sync += dest_l.s.eq(self.issue_i & self.dest_i)
37 m.d.sync += dest_l.r.eq(self.go_write_i)
38
39 # src1 latch: reset on go_read HI, set on src1_i and issue
40 m.d.sync += src1_l.s.eq(self.issue_i & self.src1_i)
41 m.d.sync += src1_l.r.eq(self.go_read_i)
42
43 # src2 latch: reset on go_read HI, set on op2_i and issue
44 m.d.sync += src2_l.s.eq(self.issue_i & self.src2_i)
45 m.d.sync += src2_l.r.eq(self.go_read_i)
46
47 # FU "Forward Progress" (read out horizontally)
48 m.d.comb += self.dest_fwd_o.eq(dest_l.qn & self.dest_i)
49 m.d.comb += self.src1_fwd_o.eq(src1_l.qn & self.src1_i)
50 m.d.comb += self.src2_fwd_o.eq(src2_l.qn & self.src2_i)
51
52 # Register File Select (read out vertically)
53 m.d.comb += self.dest_rsel_o.eq(dest_l.qn & self.go_write_i)
54 m.d.comb += self.src1_rsel_o.eq(src1_l.qn & self.go_read_i)
55 m.d.comb += self.src2_rsel_o.eq(src2_l.qn & self.go_read_i)
56
57 return m
58
59 def __iter__(self):
60 yield self.dest_i
61 yield self.src1_i
62 yield self.src2_i
63 yield self.issue_i
64 yield self.go_write_i
65 yield self.go_read_i
66 yield self.dest_rsel_o
67 yield self.src1_rsel_o
68 yield self.src2_rsel_o
69 yield self.dest_fwd_o
70 yield self.src1_fwd_o
71 yield self.src2_fwd_o
72
73 def ports(self):
74 return list(self)
75
76 def dcell_sim(dut):
77 yield dut.dest_i.eq(1)
78 yield dut.issue_i.eq(1)
79 yield
80 yield dut.issue_i.eq(0)
81 yield
82 yield dut.src1_i.eq(1)
83 yield dut.issue_i.eq(1)
84 yield
85 yield dut.issue_i.eq(0)
86 yield
87 yield dut.go_read_i.eq(1)
88 yield
89 yield dut.go_read_i.eq(0)
90 yield
91 yield dut.go_write_i.eq(1)
92 yield
93 yield dut.go_write_i.eq(0)
94 yield
95
96 def test_dcell():
97 dut = DependenceCell()
98 vl = rtlil.convert(dut, ports=dut.ports())
99 with open("test_dcell.il", "w") as f:
100 f.write(vl)
101
102 run_simulation(dut, dcell_sim(dut), vcd_name='test_dcell.vcd')
103
104 if __name__ == '__main__':
105 test_dcell()