From b291032987a6f4f408170cba867869fa3a6929ae Mon Sep 17 00:00:00 2001 From: Florent Kermarrec Date: Tue, 11 Jul 2023 16:40:15 +0200 Subject: [PATCH] frontend/dma/LiteDRAMDMAReader: Simplify FIFO reservation and add last generation support. With this, last is now asserted on the last cycle of the DMA transfer, making behavior similar to WishboneDMAReader. This is useful to create packets from DRAM data. --- litedram/frontend/dma.py | 37 +++++++++++++++++-------------------- 1 file changed, 17 insertions(+), 20 deletions(-) diff --git a/litedram/frontend/dma.py b/litedram/frontend/dma.py index 300ad42..3f31455 100644 --- a/litedram/frontend/dma.py +++ b/litedram/frontend/dma.py @@ -70,9 +70,12 @@ class LiteDRAMDMAReader(Module, AutoCSR): else: raise NotImplementedError + # Reservation FIFO ------------------------------------------------------------------------- + + res_fifo = stream.SyncFIFO([("dummy", 1)], fifo_depth) + self.submodules += res_fifo + # Request issuance ------------------------------------------------------------------------- - request_enable = Signal() - request_issued = Signal() if is_native: self.comb += cmd.we.eq(0) @@ -80,24 +83,14 @@ class LiteDRAMDMAReader(Module, AutoCSR): self.comb += cmd.size.eq(int(log2(port.data_width//8))) self.comb += [ cmd.addr.eq(sink.address), - cmd.valid.eq(enable & sink.valid & request_enable), - sink.ready.eq(enable & cmd.ready & request_enable), - request_issued.eq(cmd.valid & cmd.ready) + cmd.last.eq(sink.last), + cmd.valid.eq(enable & sink.valid & res_fifo.sink.ready), + sink.ready.eq(enable & cmd.ready & res_fifo.sink.ready), ] - - # FIFO reservation level counter ----------------------------------------------------------- - # - Incremented when data is planned to be queued. - # - Decremented when data is dequeued. - data_dequeued = Signal() - self.rsv_level = rsv_level = Signal(max=fifo_depth+1) - self.sync += [ - If(request_issued, - If(~data_dequeued, rsv_level.eq(self.rsv_level + 1)) - ).Elif(data_dequeued, - rsv_level.eq(rsv_level - 1) - ) + self.comb += [ + res_fifo.sink.valid.eq(cmd.valid & cmd.ready), + res_fifo.sink.last.eq(cmd.last), ] - self.comb += request_enable.eq(rsv_level != fifo_depth) # FIFO ------------------------------------------------------------------------------------- fifo = stream.SyncFIFO([("data", port.data_width)], fifo_depth, fifo_buffered) @@ -105,10 +98,14 @@ class LiteDRAMDMAReader(Module, AutoCSR): self.comb += [ rdata.connect(fifo.sink, omit={"id", "resp", "dest", "user"}), - fifo.source.connect(source, omit={"ready"}), + fifo.source.connect(source, omit={"valid", "ready", "last"}), + If(res_fifo.source.valid, + source.valid.eq(fifo.source.valid), + source.last.eq(res_fifo.source.last), + ), fifo.source.ready.eq(source.ready | ~enable), # Flush FIFO/Reservation counter when disabled. - data_dequeued.eq(fifo.source.valid & fifo.source.ready) ] + self.comb += res_fifo.source.ready.eq(fifo.source.valid & fifo.source.ready) if with_csr: self.add_csr()