diff --git a/src/gateware/cxp_upconn.py b/src/gateware/cxp_upconn.py index f36fff9..bff8d54 100644 --- a/src/gateware/cxp_upconn.py +++ b/src/gateware/cxp_upconn.py @@ -1,8 +1,7 @@ from migen import * from migen.genlib.resetsync import AsyncResetSynchronizer -from migen.genlib.cdc import MultiReg -from misoc.cores.code_8b10b import SingleEncoder, Decoder +from misoc.cores.code_8b10b import SingleEncoder from misoc.interconnect.csr import * from misoc.interconnect import stream @@ -10,9 +9,10 @@ class CXP_UpConn(Module, AutoCSR): def __init__(self, pads, tx_fifo_depth=32): self.clock_domains.cd_cxp_upconn = ClockDomain() self.clk_reset = CSRStorage(reset=1) - self.bitrate2x_enable = CSRStorage() + self.tx_fifos = [] + # # # pll_locked = Signal() @@ -48,73 +48,30 @@ class CXP_UpConn(Module, AutoCSR): AsyncResetSynchronizer(self.cd_cxp_upconn, ~pll_locked | self.clk_reset.storage) ] - self.symbol0 = CSR(9) - self.symbol1 = CSR(9) + self.submodules.phy = UpConnTXPHY(pads) nfifos = 2 - self.data = [ Signal(8) for _ in range(nfifos)] - self.k_symbol = [ Signal() for _ in range(nfifos)] - self.stb = [ Signal() for _ in range(nfifos)] - - - self.fifo_full = CSRStatus(nfifos) - - - self.tx_fifos = [] - self.tx_encoders = [] - - cdr = ClockDomainsRenamer({"write": "sys", "read": "cxp_upconn"}) - - # Priority Queue + # FIFOs with transmission priority # 0: Trigger packet # 1: IO acknowledgment for trigger packet # 2: All other packets for i in range(nfifos): + cdr = ClockDomainsRenamer({"write": "sys", "read": "cxp_upconn"}) fifo = cdr(stream.AsyncFIFO([("data", 9)], tx_fifo_depth)) - # fifo = stream.SyncFIFO([("data", 9)], tx_fifo_depth) self.tx_fifos.append(fifo) setattr(self.submodules, "tx_fifo" + str(i), fifo) - self.sync += [ - fifo.sink.stb.eq(self.stb[i]), - fifo.sink.data.eq(Cat(self.data[i], self.k_symbol[i])), - self.fifo_full.status[i].eq(~fifo.sink.ack), - ] - - self.sync += [ - self.stb[0].eq(self.symbol0.re), - self.data[0].eq(self.symbol0.r[:8]), - self.k_symbol[0].eq(self.symbol0.r[8]), - self.stb[1].eq(self.symbol1.re), - self.data[1].eq(self.symbol1.r[:8]), - self.k_symbol[1].eq(self.symbol1.r[8]), - ] - self.tx_fifo0_source_data = CSRStatus(9) - self.tx_fifo1_source_data = CSRStatus(9) - self.tx_fifo0_stb = CSRStatus() - self.tx_fifo1_stb = CSRStatus() - - self.submodules.tx = UpConn_TX(pads) - - self.comb += [ - self.tx_fifo0_source_data.status.eq(self.tx_fifos[0].source.data), - self.tx_fifo1_source_data.status.eq(self.tx_fifos[1].source.data), - self.tx_fifo0_stb.status.eq(self.tx_fifos[0].source.stb), - self.tx_fifo1_stb.status.eq(self.tx_fifos[1].source.stb), - ] self.sync.cxp_upconn +=[ - self.tx.data_stb.eq(self.tx_fifos[0].source.stb | self.tx_fifos[1].source.stb), + self.phy.sink.stb.eq(self.tx_fifos[0].source.stb | self.tx_fifos[1].source.stb), self.tx_fifos[0].source.ack.eq(0), self.tx_fifos[1].source.ack.eq(0), - If(self.tx.data_ack, + If(self.phy.sink.ack, If(self.tx_fifos[0].source.stb, - self.tx.encoder.d.eq(self.tx_fifos[0].source.data[:8]), - self.tx.encoder.k.eq(self.tx_fifos[0].source.data[8]), + self.phy.sink.data.eq(self.tx_fifos[0].source.data), self.tx_fifos[0].source.ack.eq(1), ).Elif(self.tx_fifos[1].source.stb, - self.tx.encoder.d.eq(self.tx_fifos[1].source.data[:8]), - self.tx.encoder.k.eq(self.tx_fifos[1].source.data[8]), + self.phy.sink.data.eq(self.tx_fifos[1].source.data), self.tx_fifos[1].source.ack.eq(1), ), ), @@ -122,41 +79,52 @@ class CXP_UpConn(Module, AutoCSR): # DEBUG: remove pads self.specials += Instance("OBUF", i_I=self.cd_cxp_upconn.clk, o_O=pads.n_rx) + self.symbol0 = CSR(9) + self.symbol1 = CSR(9) -class UpConn_TX(Module, AutoCSR): + self.sync += [ + self.tx_fifos[0].sink.stb.eq(self.symbol0.re), + self.tx_fifos[0].sink.data.eq(self.symbol0.r), + self.tx_fifos[1].sink.stb.eq(self.symbol1.re), + self.tx_fifos[1].sink.data.eq(self.symbol1.r), + # self.fifo_full[i].eq(~fifo.sink.ack), + ] + +class UpConnTXPHY(Module, AutoCSR): def __init__(self, pads): - self.data_ack = Signal() - self.data_stb = Signal() - self.data_out = CSRStatus(10) + self.sink = stream.Endpoint([("data", 9)]) # # # self.submodules.encoder = ClockDomainsRenamer("cxp_upconn")(SingleEncoder(True)) + self.comb += [ + self.encoder.d.eq(self.sink.data[:8]), + self.encoder.k.eq(self.sink.data[8]) + ] + o = Signal() tx_busy = Signal() tx_bitcount = Signal(max=10) tx_reg = Signal(10) + self.specials += Instance("OBUF", i_I=o, o_O=pads.p_tx) self.sync.cxp_upconn +=[ - self.data_ack.eq(0), + self.sink.ack.eq(0), If(tx_busy, o.eq(tx_reg[0]), tx_reg.eq(Cat(tx_reg[1:], 0)) ), If(tx_bitcount != 9, tx_bitcount.eq(tx_bitcount + 1), - ).Elif(self.data_stb, + ).Elif(self.sink.stb, tx_busy.eq(1), tx_bitcount.eq(0), tx_reg.eq(self.encoder.output), - self.data_out.status.eq(self.encoder.output), self.encoder.disp_in.eq(self.encoder.disp_out), - self.data_ack.eq(1), + self.sink.ack.eq(1), ).Else( tx_busy.eq(0), o.eq(0) ) ] - - self.specials += Instance("OBUF", i_I=o, o_O=pads.p_tx)