asmicon: refresher (untested)
authorSebastien Bourdeauducq <sebastien@milkymist.org>
Thu, 15 Mar 2012 19:29:26 +0000 (20:29 +0100)
committerSebastien Bourdeauducq <sebastien@milkymist.org>
Thu, 15 Mar 2012 19:29:26 +0000 (20:29 +0100)
milkymist/asmicon/__init__.py
milkymist/asmicon/multiplexer.py
milkymist/asmicon/refresher.py
top.py

index 2a783207457e49ebbb44632a90a5bd11a0613b02..e107255c6b5b5e8eb66ca7af8c15c289991a667e 100644 (file)
@@ -6,21 +6,23 @@ from milkymist.asmicon.bankmachine import *
 from milkymist.asmicon.multiplexer import *
 
 class PhySettings:
-       def __init__(self, dfi_a, dfi_ba, dfi_d, nphases, rdphase, wrphase):
+       def __init__(self, dfi_a, dfi_d, nphases, rdphase, wrphase):
+               # NB: dfi_ba is obtained from GeomSettings.bank_a
                self.dfi_a = dfi_a
-               self.dfi_ba = dfi_ba
                self.dfi_d = dfi_d
                self.nphases = nphases
                self.rdphase = rdphase
                self.wrphase = wrphase
 
 class GeomSettings:
-       def __init__(self, row_a, col_a):
+       def __init__(self, bank_a, row_a, col_a):
+               self.bank_a = bank_a
                self.row_a = row_a
                self.col_a = col_a
 
 class TimingSettings:
-       def __init__(self, tREFI, tRFC):
+       def __init__(self, tRP, tREFI, tRFC):
+               self.tRP = tRP
                self.tREFI = tREFI
                self.tRFC = tRFC
 
@@ -32,12 +34,12 @@ class ASMIcon:
                self.finalized = False
                
                self.dfi = dfi.Interface(self.phy_settings.dfi_a,
-                       self.phy_settings.dfi_ba,
+                       self.geom_settings.bank_a,
                        self.phy_settings.dfi_d,
                        self.phy_settings.nphases)
                burst_length = self.phy_settings.nphases*2
                self.address_align = log2_int(burst_length)
-               aw = self.phy_settings.dfi_ba + self.geom_settings.row_a + self.geom_settings.col_a - self.address_align
+               aw = self.geom_settings.bank_a + self.geom_settings.row_a + self.geom_settings.col_a - self.address_align
                dw = self.phy_settings.dfi_d*self.phy_settings.nphases
                self.hub = asmibus.Hub(aw, dw, time)
        
@@ -47,8 +49,9 @@ class ASMIcon:
                self.finalized = True
                self.hub.finalize()
                slots = self.hub.get_slots()
-               self.refresher = Refresher(self.timing_settings)
-               self.bank_machines = [BankMachine(self.geom_settings, self.timing_settings, self.address_align, i, slots) for i in range(2**self.phy_settings.dfi_ba)]
+               self.refresher = Refresher(self.phy_settings.dfi_a, self.geom_settings.bank_a,
+                       self.timing_settings.tRP, self.timing_settings.tREFI, self.timing_settings.tRFC)
+               self.bank_machines = [BankMachine(self.geom_settings, self.timing_settings, self.address_align, i, slots) for i in range(2**self.geom_settings.bank_a)]
                self.multiplexer = Multiplexer(self.phy_settings, self.geom_settings, self.timing_settings,
                        self.bank_machines, self.refresher,
                        self.dfi, self.hub)
index 286ee78c5588530cb690c4b5982a11f9914e52ca..3e8ebf7770c7aa6c30ffba552e4e57d64fed32fe 100644 (file)
@@ -1,5 +1,22 @@
 from migen.fhdl.structure import *
 
+class CommandRequest:
+       def __init__(self, dfi_a, dfi_ba):
+               self.a = Signal(BV(dfi_a))
+               self.ba = Signal(BV(dfi_ba))
+               self.cas_n = Signal(reset=1)
+               self.ras_n = Signal(reset=1)
+               self.we_n = Signal(reset=1)
+
+class CommandRequestRW(CommandRequest):
+       def __init__(self, dfi_a, dfi_ba, tagbits):
+               CommandRequest.__init__(self, dfi_a, dfi_ba)
+               self.stb = Signal()
+               self.ack = Signal()
+               self.is_read = Signal()
+               self.is_write = Signal()
+               self.tag = Signal(BV(tagbits))
+
 class Multiplexer:
        def __init__(self, phy_settings, geom_settings, timing_settings, bank_machines, refresher, dfi, hub):
                pass
index 3971f7ef9671b574521f94f6defc298e29870070..7e086f527e3c04cee817c781cfe8fef1d49796ff 100644 (file)
@@ -1,8 +1,74 @@
 from migen.fhdl.structure import *
+from migen.corelogic.misc import timeline
+from migen.corelogic.fsm import FSM
+
+from milkymist.asmicon.multiplexer import *
 
 class Refresher:
-       def __init__(self, timing_settings):
-               pass
+       def __init__(self, dfi_a, dfi_ba, tRP, tREFI, tRFC):
+               self.tRP = tRP
+               self.tREFI = tREFI
+               self.tRFC = tRFC
+               
+               self.req = Signal()
+               self.ack = Signal()
+               self.cmd_request = CommandRequest(dfi_a, dfi_ba)
        
        def get_fragment(self):
-               return Fragment()
+               comb = []
+               sync = []
+               
+               # Refresh sequence generator:
+               # PRECHARGE ALL --(tRP)--> AUTO REFRESH --(tRFC)--> done
+               seq_start = Signal()
+               seq_done = Signal()
+               sync += [
+                       self.cmd_request.a.eq(2**10),
+                       self.cmd_request.ba.eq(0),
+                       self.cmd_request.cas_n.eq(1),
+                       self.cmd_request.ras_n.eq(1),
+                       self.cmd_request.we_n.eq(1)
+               ]
+               sync += timeline(seq_start, [
+                       (0, [
+                               self.cmd_request.ras_n.eq(0),
+                               self.cmd_request.we_n.eq(0)
+                       ]),
+                       (self.tRP, [
+                               self.cmd_request.cas_n.eq(0),
+                               self.cmd_request.ras_n.eq(0)
+                       ]),
+                       (self.tRP+self.tRFC, [
+                               seq_done.eq(1)
+                       ])
+               ])
+               
+               # Periodic refresh counter
+               counter = Signal(BV(bits_for(self.tREFI - 1)))
+               start = Signal()
+               sync += [
+                       start.eq(0),
+                       If(counter == 0,
+                               start.eq(1),
+                               counter.eq(self.tREFI - 1)
+                       ).Else(
+                               counter.eq(counter - 1)
+                       )
+               ]
+               
+               # Control FSM
+               fsm = FSM("IDLE", "WAIT_GRANT", "WAIT_SEQ")
+               fsm.act(fsm.IDLE, If(start, fsm.next_state(fsm.WAIT_GRANT)))
+               fsm.act(fsm.WAIT_GRANT,
+                       self.req.eq(1),
+                       If(self.ack,
+                               seq_start.eq(1),
+                               fsm.next_state(fsm.WAIT_SEQ)
+                       )
+               )
+               fsm.act(fsm.WAIT_SEQ,
+                       self.req.eq(1),
+                       If(seq_done, fsm.next_state(fsm.IDLE))
+               )
+               
+               return Fragment(comb, sync) + fsm.get_fragment()
diff --git a/top.py b/top.py
index 551edc53de5b79bbcc275864b0808b44f88cf1a2..6c938cc2b8fc8c7e9a6b9006d4378f159d9206ce 100644 (file)
--- a/top.py
+++ b/top.py
@@ -21,17 +21,18 @@ def ns(t, margin=False):
 
 sdram_phy = asmicon.PhySettings(
        dfi_a=13,
-       dfi_ba=2,
        dfi_d=64, 
        nphases=2,
        rdphase=0,
        wrphase=1
 )
 sdram_geom = asmicon.GeomSettings(
+       bank_a=2,
        row_a=13,
        col_a=10
 )
 sdram_timing = asmicon.TimingSettings(
+       tRP=ns(15),
        tREFI=ns(7800),
        tRFC=ns(70)
 )
@@ -58,8 +59,8 @@ def get():
        #
        # DFI
        #
-       ddrphy0 = s6ddrphy.S6DDRPHY(sdram_phy.dfi_a, sdram_phy.dfi_ba, sdram_phy.dfi_d)
-       dfii0 = dfii.DFIInjector(1, sdram_phy.dfi_a, sdram_phy.dfi_ba, sdram_phy.dfi_d, sdram_phy.nphases)
+       ddrphy0 = s6ddrphy.S6DDRPHY(sdram_phy.dfi_a, sdram_geom.bank_a, sdram_phy.dfi_d)
+       dfii0 = dfii.DFIInjector(1, sdram_phy.dfi_a, sdram_geom.bank_a, sdram_phy.dfi_d, sdram_phy.nphases)
        dficon0 = dfi.Interconnect(dfii0.master, ddrphy0.dfi)
        dficon1 = dfi.Interconnect(asmicon0.dfi, dfii0.slave)