+++ /dev/null
-# This file is Copyright (c) 2016-2020 Florent Kermarrec <florent@enjoy-digital.fr>
-# License: BSD
-
-"""Wishbone frontend for LiteDRAM"""
-
-from math import log2
-
-from nmigen import *
-
-import gram.stream as stream
-
-
-# LiteDRAMWishbone2Native --------------------------------------------------------------------------
-
-class LiteDRAMWishbone2Native(Module):
- def __init__(self, wishbone, port, base_address=0x00000000):
- wishbone_data_width = len(wishbone.dat_w)
- # Round to lowest power 2
- port_data_width = 2**int(log2(len(port.wdata.data)))
- assert wishbone_data_width >= port_data_width
-
- # # #
-
- adr_offset = base_address >> log2_int(port.data_width//8)
-
- # Write Datapath ---------------------------------------------------------------------------
- wdata_converter = stream.StrideConverter(
- [("data", wishbone_data_width), ("we", wishbone_data_width//8)],
- [("data", port_data_width), ("we", port_data_width//8)],
- )
- self.submodules += wdata_converter
- self.comb += [
- wdata_converter.sink.valid.eq(
- wishbone.cyc & wishbone.stb & wishbone.we),
- wdata_converter.sink.data.eq(wishbone.dat_w),
- wdata_converter.sink.we.eq(wishbone.sel),
- wdata_converter.source.connect(port.wdata)
- ]
-
- # Read Datapath ----------------------------------------------------------------------------
- rdata_converter = stream.StrideConverter(
- [("data", port_data_width)],
- [("data", wishbone_data_width)],
- )
- self.submodules += rdata_converter
- self.comb += [
- port.rdata.connect(rdata_converter.sink),
- rdata_converter.source.ready.eq(1),
- wishbone.dat_r.eq(rdata_converter.source.data),
- ]
-
- # Control ----------------------------------------------------------------------------------
- ratio = wishbone_data_width//port_data_width
- count = Signal(max=max(ratio, 2))
- self.submodules.fsm = fsm = FSM(reset_state="CMD")
- fsm.act("CMD",
- port.cmd.valid.eq(wishbone.cyc & wishbone.stb),
- port.cmd.we.eq(wishbone.we),
- port.cmd.addr.eq(wishbone.adr*ratio + count - adr_offset),
- If(port.cmd.valid & port.cmd.ready,
- NextValue(count, count + 1),
- If(count == (ratio - 1),
- NextValue(count, 0),
- If(wishbone.we,
- NextState("WAIT-WRITE")
- ).Else(
- NextState("WAIT-READ")
- )
- )
- )
- )
- fsm.act("WAIT-WRITE",
- If(wdata_converter.sink.ready,
- wishbone.ack.eq(1),
- NextState("CMD")
- )
- )
- fsm.act("WAIT-READ",
- If(rdata_converter.source.valid,
- wishbone.ack.eq(1),
- NextState("CMD")
- )
- )
def __init__(self, core):
super().__init__()
- self._port = core.crossbar.get_port()
+ self._port = core.crossbar.get_port(data_width=32)
dram_size = core.size//4
dram_addr_width = log2_int(dram_size)
self.bus = wishbone.Interface(addr_width=dram_addr_width,
data_width=32, granularity=granularity)
- map = MemoryMap(addr_width=dram_addr_width, data_width=granularity)
- map.add_resource(self, size=dram_size)
+ map = MemoryMap(addr_width=dram_addr_width+log2_int(granularity)-1, data_width=granularity)
self.bus.memory_map = map
def elaborate(self, platform):
m = Module()
- ratio = wishbone_data_width//port_data_width
- count = Signal(max=max(ratio, 2))
+ # Write datapath
+ m.d.comb += [
+ self._port.wdata.valid.eq(wishbone.cyc & wishbone.stb & wishbone.we),
+ self._port.wdata.data.eq(wishbone.dat_w),
+ self._port.wdata.we.eq(wishbone.sel),
+ ]
+
+ # Read datapath
+ m.d.comb += [
+ self.bus.dat_r.eq(self._port.rdata.data),
+ self._port.rdata.data.ready.eq(1),
+ ]
+
with m.FSM():
with m.State("Send-Cmd"):
m.d.comb += [
port.cmd.valid.eq(self.bus.cyc & self.bus.stb),
port.cmd.we.eq(self.bus.we),
- port.cmd.addr.eq(self.bus.adr*ratio + count - adr_offset),
+ port.cmd.addr.eq(self.bus.adr),
]
with m.If(port.cmd.valid & port.cmd.ready):
+ with m.If(self.bus.we):
+ m.next = "Wait-Write"
+ with m.Else():
+ m.next = "Wait-Read"
+
+ with m.State("Wait-Read"):
+ with m.If(self._port.rdata.valid):
+ m.d.comb += self.bus.ack.eq(1)
+ m.next = "Send-Cmd"
- # with m.State("Write"):
- # ...
+ with m.State("Wait-Write"):
+ with m.If(self._port.wdata.ready):
+ m.d.comb += self.bus.ack.eq(1)
+ m.next = "Send-Cmd"
- # with m.State("Read"):
- # ...
return m