liteusb: continue refactoring (virtual UART and DMA working on minispartan6)

- rename ft2232h phy to ft245.
- make crc optional
- fix depacketizer
- refactor uart (it's now only a wrapper around standard UART)
- fix and update dma
This commit is contained in:
Florent Kermarrec 2015-05-01 16:11:15 +02:00
parent 8aa3fb3eb7
commit 603b4cdc8c
10 changed files with 141 additions and 159 deletions

View File

@ -3,6 +3,7 @@ from migen.genlib.fsm import *
from migen.actorlib.fifo import * from migen.actorlib.fifo import *
from migen.flow.actor import EndpointDescription from migen.flow.actor import EndpointDescription
from migen.actorlib.packet import * from migen.actorlib.packet import *
from migen.actorlib.structuring import Pipeline
packet_header_length = 9 packet_header_length = 9
@ -49,11 +50,12 @@ class LiteUSBMasterPort:
class LiteUSBSlavePort: class LiteUSBSlavePort:
def __init__(self, dw): def __init__(self, dw, tag):
self.sink = Sink(user_description(dw)) self.sink = Sink(user_description(dw))
self.source = Source(user_description(dw)) self.source = Source(user_description(dw))
self.tag = tag
class LiteUSBUserPort(LiteUSBSlavePort): class LiteUSBUserPort(LiteUSBSlavePort):
def __init__(self, dw): def __init__(self, dw, tag):
LiteUSBSlavePort.__init__(self, dw) LiteUSBSlavePort.__init__(self, dw, tag)

View File

@ -3,29 +3,29 @@ from misoclib.com.liteusb.core.packet import LiteUSBPacketizer, LiteUSBDepacketi
from misoclib.com.liteusb.core.crc import LiteUSBCRC32Inserter, LiteUSBCRC32Checker from misoclib.com.liteusb.core.crc import LiteUSBCRC32Inserter, LiteUSBCRC32Checker
from misoclib.com.liteusb.core.crossbar import LiteUSBCrossbar from misoclib.com.liteusb.core.crossbar import LiteUSBCrossbar
# XXX Header should be protected by CRC
class LiteUSBCore(Module): class LiteUSBCore(Module):
def __init__(self, phy): def __init__(self, phy, clk_freq, with_crc=True):
rx_pipeline = [phy]
tx_pipeline = [phy]
# depacketizer / packetizer # depacketizer / packetizer
self.submodules.depacketizer = LiteUSBDepacketizer() self.submodules.depacketizer = LiteUSBDepacketizer(clk_freq)
self.submodules.packetizer = LiteUSBPacketizer() self.submodules.packetizer = LiteUSBPacketizer()
self.comb += [ rx_pipeline += [self.depacketizer]
Record.connect(phy.source, self.depacketizer.sink), tx_pipeline += [self.packetizer]
Record.connect(self.packetizer.source, phy.sink)
]
# crc checker / inserter if with_crc:
self.submodules.crc_rx = LiteUSBCRC32Checker() # crc checker / inserter
self.submodules.crc_tx = LiteUSBCRC32Inserter() self.submodules.crc_rx = LiteUSBCRC32Checker()
self.comb += [ self.submodules.crc_tx = LiteUSBCRC32Inserter()
Record.connect(self.depacketizer.source, self.crc_rx.sink), rx_pipeline += [self.crc_rx]
Record.connect(self.crc_tx.source, self.packetizer.sink) tx_pipeline += [self.crc_tx]
]
# crossbar # crossbar
self.submodules.crossbar = LiteUSBCrossbar() self.submodules.crossbar = LiteUSBCrossbar()
self.comb += [ rx_pipeline += [self.crossbar.master]
Record.connect(self.crossbar.master.source, self.crc_tx.sink), tx_pipeline += [self.crossbar.master]
Record.connect(self.crc_rx.source, self.crossbar.master.sink)
] # graph
self.submodules.rx_pipeline = Pipeline(*rx_pipeline)
self.submodules.tx_pipeline = Pipeline(*reversed(tx_pipeline))

View File

@ -9,7 +9,7 @@ class LiteUSBCrossbar(Module):
self.dispatch_param = "dst" self.dispatch_param = "dst"
def get_port(self, dst): def get_port(self, dst):
port = LiteUSBUserPort(8) port = LiteUSBUserPort(8, dst)
if dst in self.users.keys(): if dst in self.users.keys():
raise ValueError("Destination {0:#x} already assigned".format(dst)) raise ValueError("Destination {0:#x} already assigned".format(dst))
self.users[dst] = port self.users[dst] = port

View File

@ -66,7 +66,7 @@ class LiteUSBPacketizer(Module):
class LiteUSBDepacketizer(Module): class LiteUSBDepacketizer(Module):
def __init__(self, timeout=10): def __init__(self, clk_freq, timeout=10):
self.sink = sink = Sink(phy_description(8)) self.sink = sink = Sink(phy_description(8))
self.source = source = Source(user_description(8)) self.source = source = Source(user_description(8))
@ -116,9 +116,9 @@ class LiteUSBDepacketizer(Module):
header_pack.source.ack.eq(1), header_pack.source.ack.eq(1),
) )
self.submodules.timeout = Timeout(60000000*timeout) #XXX use clk_freq self.submodules.timeout = Timeout(clk_freq*timeout)
self.comb += [ self.comb += [
self.timeout.reset.eq(fsm.ongoing("WAIT_SOP")), self.timeout.reset.eq(fsm.ongoing("IDLE")),
self.timeout.ce.eq(1) self.timeout.ce.eq(1)
] ]

View File

@ -16,7 +16,7 @@ class LiteUSBDMAWriter(Module, AutoCSR):
# Pack data # Pack data
pack_factor = lasmim.dw//8 pack_factor = lasmim.dw//8
pack = structuring.Pack(phy_layout, pack_factor, reverse=True) pack = structuring.Pack(phy_description(8), pack_factor, reverse=True)
cast = structuring.Cast(pack.source.payload.layout, lasmim.dw) cast = structuring.Cast(pack.source.payload.layout, lasmim.dw)
# DMA # DMA
@ -61,12 +61,12 @@ class LiteUSBDMAReader(Module, AutoCSR):
pack_factor = lasmim.dw//8 pack_factor = lasmim.dw//8
packed_dat = structuring.pack_layout(8, pack_factor) packed_dat = structuring.pack_layout(8, pack_factor)
cast = structuring.Cast(lasmim.dw, packed_dat) cast = structuring.Cast(lasmim.dw, packed_dat)
unpack = structuring.Unpack(pack_factor, phy_layout, reverse=True) unpack = structuring.Unpack(pack_factor, phy_description(8), reverse=True)
# Graph # Graph
cnt = Signal(32) cnt = Signal(32)
self.sync += \ self.sync += \
If(self.dma.generator._r_shoot.re, If(self.dma.generator._shoot.re,
cnt.eq(0) cnt.eq(0)
).Elif(source.stb & source.ack, ).Elif(source.stb & source.ack,
cnt.eq(cnt + 1) cnt.eq(cnt + 1)
@ -92,12 +92,11 @@ class LiteUSBDMAReader(Module, AutoCSR):
class LiteUSBDMA(Module, AutoCSR): class LiteUSBDMA(Module, AutoCSR):
def __init__(self, lasmim_dma_wr, lasmim_dma_rd, tag): def __init__(self, port, lasmim_dma_wr, lasmim_dma_rd):
self.tag = tag
self.submodules.writer = LiteUSBDMAWriter(lasmim_dma_wr) self.submodules.writer = LiteUSBDMAWriter(lasmim_dma_wr)
self.submodules.reader = LiteUSBDMAReader(lasmim_dma_rd, self.tag) self.submodules.reader = LiteUSBDMAReader(lasmim_dma_rd, port.tag)
self.submodules.ev = SharedIRQ(self.writer.ev, self.reader.ev) self.submodules.ev = SharedIRQ(self.writer.ev, self.reader.ev)
self.comb += [
self.sink = self.writer.sink Record.connect(port.source, self.writer.sink),
self.source = self.reader.source Record.connect(self.reader.source, port.sink),
]

View File

@ -1,59 +1,35 @@
from migen.fhdl.std import * from migen.fhdl.std import *
from migen.bank.description import *
from migen.bank.eventmanager import *
from migen.actorlib.fifo import SyncFIFO
from misoclib.com.liteusb.common import * from misoclib.com.liteusb.common import *
from misoclib.com.uart import UART
class LiteUSBUARTPHY:
def __init__(self):
self.sink = Sink([("data", 8)])
self.source = Source([("data", 8)])
class LiteUSBUART(Module, AutoCSR): class LiteUSBUART(UART):
def __init__(self, tag, fifo_depth=64): def __init__(self, port,
self.tag = tag tx_fifo_depth=16,
rx_fifo_depth=16):
self._rxtx = CSR(8) phy = LiteUSBUARTPHY()
UART.__init__(self, phy, tx_fifo_depth, rx_fifo_depth)
self.submodules.ev = EventManager()
self.ev.tx = EventSourcePulse()
self.ev.rx = EventSourceLevel()
self.ev.finalize()
self.source = source = Source(user_description(8))
self.sink = sink = Sink(user_description(8))
# # #
# TX # TX
tx_start = self._rxtx.re
tx_done = self.ev.tx.trigger
self.sync += \
If(tx_start,
source.stb.eq(1),
source.data.eq(self._rxtx.r),
).Elif(tx_done,
source.stb.eq(0)
)
self.comb += [ self.comb += [
source.sop.eq(1), port.sink.stb.eq(phy.sink.stb),
source.eop.eq(1), port.sink.sop.eq(1),
source.length.eq(1), port.sink.eop.eq(1),
source.dst.eq(self.tag), port.sink.length.eq(1),
tx_done.eq(source.stb & source.ack), port.sink.dst.eq(port.tag),
port.sink.data.eq(phy.sink.data),
phy.sink.ack.eq(port.sink.ack)
] ]
# RX # RX
rx_available = self.ev.rx.trigger
rx_fifo = SyncFIFO(8, fifo_depth)
self.submodules += rx_fifo
self.comb += [ self.comb += [
Record.connect(sink, rx_fifo.sink), phy.source.stb.eq(port.source.stb),
phy.source.data.eq(port.source.data),
rx_fifo.we.eq(sink.stb), port.source.ack.eq(phy.source.ack)
sink.ack.eq(sink.stb & rx_fifo.writable),
rx_fifo.din.eq(sink.data),
rx_available.eq(rx_fifo.stb),
rx_fifo.ack.eq(self.ev.rx.clear),
self._rxtx.w.eq(rx_fifo.dout)
] ]

View File

@ -1,3 +1,5 @@
import math
from migen.fhdl.std import * from migen.fhdl.std import *
from migen.flow.actor import * from migen.flow.actor import *
from migen.actorlib.fifo import SyncFIFO, AsyncFIFO from migen.actorlib.fifo import SyncFIFO, AsyncFIFO
@ -24,39 +26,31 @@ def anti_starvation(module, timeout):
return en, max_time return en, max_time
class FT2232HPHYSynchronous(Module): class FT245PHYSynchronous(Module):
def __init__(self, pads, def __init__(self, pads, clk_freq,
fifo_depth=32, fifo_depth=32,
read_time=16, read_time=128,
write_time=16): write_time=128):
dw = flen(pads.data) dw = flen(pads.data)
# # read fifo (FTDI --> SoC)
# Read / Write Fifos
#
# Read Fifo (Ftdi --> SoC)
read_fifo = RenameClockDomains(AsyncFIFO(phy_description(8), fifo_depth), read_fifo = RenameClockDomains(AsyncFIFO(phy_description(8), fifo_depth),
{"write": "ftdi", "read": "sys"}) {"write": "ftdi", "read": "sys"})
read_buffer = RenameClockDomains(SyncFIFO(phy_description(8), 4), read_buffer = RenameClockDomains(SyncFIFO(phy_description(8), 4),
{"sys": "ftdi"}) {"sys": "ftdi"})
self.comb += read_buffer.source.connect(read_fifo.sink) self.comb += read_buffer.source.connect(read_fifo.sink)
# Write Fifo (SoC --> Ftdi) # write fifo (SoC --> FTDI)
write_fifo = RenameClockDomains(AsyncFIFO(phy_description(8), fifo_depth), write_fifo = RenameClockDomains(AsyncFIFO(phy_description(8), fifo_depth),
{"write": "sys", "read": "ftdi"}) {"write": "sys", "read": "ftdi"})
self.submodules += read_fifo, read_buffer, write_fifo self.submodules += read_fifo, read_buffer, write_fifo
# # sink / source interfaces
# Sink / Source interfaces
#
self.sink = write_fifo.sink self.sink = write_fifo.sink
self.source = read_fifo.source self.source = read_fifo.source
# # read / write arbitration
# Read / Write Arbitration
#
wants_write = Signal() wants_write = Signal()
wants_read = Signal() wants_read = Signal()
@ -102,14 +96,13 @@ class FT2232HPHYSynchronous(Module):
NextState("READ") NextState("READ")
) )
# # databus tristate
# Read / Write Actions
#
data_w = Signal(dw) data_w = Signal(dw)
data_r = Signal(dw) data_r = Signal(dw)
data_oe = Signal() data_oe = Signal()
self.specials += Tristate(pads.data, data_w, data_oe, data_r)
# read / write actions
pads.oe_n.reset = 1 pads.oe_n.reset = 1
pads.rd_n.reset = 1 pads.rd_n.reset = 1
pads.wr_n.reset = 1 pads.wr_n.reset = 1
@ -145,43 +138,35 @@ class FT2232HPHYSynchronous(Module):
) )
] ]
#
# Databus Tristate
#
self.specials += Tristate(pads.data, data_w, data_oe, data_r)
self.debug = Signal(8) class FT245PHYAsynchronous(Module):
self.comb += self.debug.eq(data_r)
class FT2232HPHYAsynchronous(Module):
def __init__(self, pads, clk_freq, def __init__(self, pads, clk_freq,
fifo_depth=32, fifo_depth=32,
read_time=16, read_time=128,
write_time=16): write_time=128):
dw = flen(pads.data) dw = flen(pads.data)
self.clk_freq = clk_freq
# # timings
# Read / Write Fifos tRD = self.ns(30) # RD# active pulse width (t4)
# tRDDataSetup = self.ns(14) # RD# to DATA (t3)
tWRDataSetup = self.ns(5) # DATA to WR# active setup time (t8)
tWR = self.ns(30) # WR# active pulse width (t10)
tMultiReg = 2
# Read Fifo (Ftdi --> SoC) # read fifo (FTDI --> SoC)
read_fifo = SyncFIFO(phy_description(8), fifo_depth) read_fifo = SyncFIFO(phy_description(8), fifo_depth)
# Write Fifo (SoC --> Ftdi) # write fifo (SoC --> FTDI)
write_fifo = SyncFIFO(phy_description(8), fifo_depth) write_fifo = SyncFIFO(phy_description(8), fifo_depth)
self.submodules += read_fifo, write_fifo self.submodules += read_fifo, write_fifo
# # sink / source interfaces
# Sink / Source interfaces
#
self.sink = write_fifo.sink self.sink = write_fifo.sink
self.source = read_fifo.source self.source = read_fifo.source
# # read / write arbitration
# Read / Write Arbitration
#
wants_write = Signal() wants_write = Signal()
wants_read = Signal() wants_read = Signal()
@ -233,9 +218,7 @@ class FT2232HPHYAsynchronous(Module):
NextState("READ") NextState("READ")
) )
# # databus tristate
# Databus Tristate
#
data_w = Signal(dw) data_w = Signal(dw)
data_r_async = Signal(dw) data_r_async = Signal(dw)
data_r = Signal(dw) data_r = Signal(dw)
@ -245,10 +228,8 @@ class FT2232HPHYAsynchronous(Module):
MultiReg(data_r_async, data_r) MultiReg(data_r_async, data_r)
] ]
#
# Read / Write Actions # read actions
#
pads.wr_n.reset = 1
pads.rd_n.reset = 1 pads.rd_n.reset = 1
read_fsm = FSM(reset_state="IDLE") read_fsm = FSM(reset_state="IDLE")
@ -267,7 +248,7 @@ class FT2232HPHYAsynchronous(Module):
read_fsm.act("PULSE_RD_N", read_fsm.act("PULSE_RD_N",
pads.rd_n.eq(0), pads.rd_n.eq(0),
read_counter.ce.eq(1), read_counter.ce.eq(1),
If(read_counter.value == 15, # XXX Compute exact value If(read_counter.value == max((tRD-1), (tRDDataSetup + tMultiReg -1)),
NextState("ACQUIRE_DATA") NextState("ACQUIRE_DATA")
) )
) )
@ -282,6 +263,9 @@ class FT2232HPHYAsynchronous(Module):
) )
) )
# write actions
pads.wr_n.reset = 1
write_fsm = FSM(reset_state="IDLE") write_fsm = FSM(reset_state="IDLE")
write_counter = Counter(8) write_counter = Counter(8)
self.submodules += write_fsm, write_counter self.submodules += write_fsm, write_counter
@ -299,7 +283,7 @@ class FT2232HPHYAsynchronous(Module):
data_oe.eq(1), data_oe.eq(1),
data_w.eq(write_fifo.source.data), data_w.eq(write_fifo.source.data),
write_counter.ce.eq(1), write_counter.ce.eq(1),
If(write_counter.value == 5, # XXX Compute exact value If(write_counter.value == (tWRDataSetup-1),
write_counter.reset.eq(1), write_counter.reset.eq(1),
NextState("PULSE_WR_N") NextState("PULSE_WR_N")
) )
@ -309,7 +293,7 @@ class FT2232HPHYAsynchronous(Module):
data_w.eq(write_fifo.source.data), data_w.eq(write_fifo.source.data),
pads.wr_n.eq(0), pads.wr_n.eq(0),
write_counter.ce.eq(1), write_counter.ce.eq(1),
If(write_counter.value == 15, # XXX Compute exact value If(write_counter.value == (tWR-1),
NextState("WAIT_TXE_N") NextState("WAIT_TXE_N")
) )
) )
@ -319,3 +303,17 @@ class FT2232HPHYAsynchronous(Module):
NextState("IDLE") NextState("IDLE")
) )
) )
def ns(self, t, margin=True):
clk_period_ns = 1000000000/self.clk_freq
if margin:
t += clk_period_ns/2
return math.ceil(t/clk_period_ns)
def FT245PHY(pads, *args, **kwargs):
# autodetect PHY
if hasattr(pads, "oe_n"):
return FT245PHYSynchronous(pads, *args, **kwargs)
else:
return FT245PHYAsynchronous(pads, *args, **kwargs)

View File

@ -3,11 +3,11 @@ PYTHON = python3
CMD = PYTHONPATH=$(MSCDIR) $(PYTHON) CMD = PYTHONPATH=$(MSCDIR) $(PYTHON)
ft2232h_sync_tb: ft245_sync_tb:
$(CMD) ft2232h_sync_tb.py $(CMD) ft245_sync_tb.py
ft2232h_async_tb: ft245_async_tb:
$(CMD) ft2232h_async_tb.py $(CMD) ft245_async_tb.py
core_tb: core_tb:
$(CMD) core_tb.py $(CMD) core_tb.py

View File

@ -5,18 +5,22 @@ from migen.fhdl.specials import *
from migen.sim.generic import run_simulation from migen.sim.generic import run_simulation
from misoclib.com.liteusb.common import * from misoclib.com.liteusb.common import *
from misoclib.com.liteusb.phy.ft2232h import FT2232HPHYAsynchronous from misoclib.com.liteusb.phy.ft245 import FT245PHYAsynchronous
from misoclib.com.liteusb.test.common import * from misoclib.com.liteusb.test.common import *
# XXX for now use it from liteeth to avoid duplication # XXX for now use it from liteeth to avoid duplication
from misoclib.com.liteeth.test.common import * from misoclib.com.liteeth.test.common import *
class FT2232HAsynchronousModel(Module, RandRun): class FT245AsynchronousModel(Module):
def __init__(self, rd_data): def __init__(self, clk_freq, rd_data):
RandRun.__init__(self, 10) self.clk_freq = clk_freq
self.rd_data = [0] + rd_data self.rd_data = [0] + rd_data
self.rd_idx = 0 self.rd_idx = 0
# timings
self.tRDInactive = self.ns(49) # RXF# inactive after RD# cycle
self.tWRInactive = self.ns(49) # TXE# inactive after WR# cycle
# pads # pads
self.data = Signal(8) self.data = Signal(8)
self.rxf_n = Signal(reset=1) self.rxf_n = Signal(reset=1)
@ -48,11 +52,10 @@ class FT2232HAsynchronousModel(Module, RandRun):
else: else:
if (not selfp.wr_n and self.last_wr_n) and not selfp.txe_n: if (not selfp.wr_n and self.last_wr_n) and not selfp.txe_n:
self.wr_data.append(selfp.data_w) self.wr_data.append(selfp.data_w)
self.wr_delay = 20 # XXX FIXME self.wr_delay = self.tWRInactive
self.last_wr_n = selfp.wr_n self.last_wr_n = selfp.wr_n
if self.run: selfp.txe_n = 0
selfp.txe_n = 0
def rd_sim(self, selfp): def rd_sim(self, selfp):
if self.rd_delay: if self.rd_delay:
@ -60,12 +63,9 @@ class FT2232HAsynchronousModel(Module, RandRun):
self.rd_delay = self.rd_delay - 1 self.rd_delay = self.rd_delay - 1
else: else:
rxf_n = selfp.rxf_n rxf_n = selfp.rxf_n
if self.run: if self.rd_idx < len(self.rd_data)-1:
if self.rd_idx < len(self.rd_data)-1: self.rd_done = selfp.rxf_n
self.rd_done = selfp.rxf_n selfp.rxf_n = 0
selfp.rxf_n = 0
else:
selfp.rxf_n = self.rd_done
else: else:
selfp.rxf_n = self.rd_done selfp.rxf_n = self.rd_done
@ -75,12 +75,11 @@ class FT2232HAsynchronousModel(Module, RandRun):
selfp.data_r = self.rd_data[self.rd_idx] selfp.data_r = self.rd_data[self.rd_idx]
self.rd_done = 1 self.rd_done = 1
if selfp.rd_n and not self.last_rd_n: if selfp.rd_n and not self.last_rd_n:
self.rd_delay = 4 # XXX FIXME self.rd_delay = self.tRDInactive
self.last_rd_n = selfp.rd_n self.last_rd_n = selfp.rd_n
def do_simulation(self, selfp): def do_simulation(self, selfp):
RandRun.do_simulation(self, selfp)
if self.init: if self.init:
selfp.rxf_n = 0 selfp.rxf_n = 0
self.wr_data = [] self.wr_data = []
@ -88,13 +87,21 @@ class FT2232HAsynchronousModel(Module, RandRun):
self.wr_sim(selfp) self.wr_sim(selfp)
self.rd_sim(selfp) self.rd_sim(selfp)
def ns(self, t, margin=True):
clk_period_ns = 1000000000/self.clk_freq
if margin:
t += clk_period_ns/2
return math.ceil(t/clk_period_ns)
test_packet = [i%256 for i in range(128)] test_packet = [i%256 for i in range(128)]
class TB(Module): class TB(Module):
def __init__(self): def __init__(self):
self.submodules.model = FT2232HAsynchronousModel(test_packet) clk_freq = 50*1000000
self.submodules.phy = FT2232HPHYAsynchronous(self.model, 50000000) self.submodules.model = FT245AsynchronousModel(clk_freq, test_packet)
self.submodules.phy = FT245PHYAsynchronous(self.model, clk_freq)
self.submodules.streamer = PacketStreamer(phy_description(8)) self.submodules.streamer = PacketStreamer(phy_description(8))
self.submodules.streamer_randomizer = AckRandomizer(phy_description(8), level=10) self.submodules.streamer_randomizer = AckRandomizer(phy_description(8), level=10)

View File

@ -5,13 +5,13 @@ from migen.fhdl.specials import *
from migen.sim.generic import run_simulation from migen.sim.generic import run_simulation
from misoclib.com.liteusb.common import * from misoclib.com.liteusb.common import *
from misoclib.com.liteusb.phy.ft2232h import FT2232HPHYSynchronous from misoclib.com.liteusb.phy.ft245 import FT245PHYSynchronous
from misoclib.com.liteusb.test.common import * from misoclib.com.liteusb.test.common import *
# XXX for now use it from liteeth to avoid duplication # XXX for now use it from liteeth to avoid duplication
from misoclib.com.liteeth.test.common import * from misoclib.com.liteeth.test.common import *
class FT2232HSynchronousModel(Module, RandRun): class FT245SynchronousModel(Module, RandRun):
def __init__(self, rd_data): def __init__(self, rd_data):
RandRun.__init__(self, 10) RandRun.__init__(self, 10)
self.rd_data = [0] + rd_data self.rd_data = [0] + rd_data
@ -82,8 +82,8 @@ test_packet = [i%256 for i in range(512)]
class TB(Module): class TB(Module):
def __init__(self): def __init__(self):
self.submodules.model = FT2232HSynchronousModel(test_packet) self.submodules.model = FT245SynchronousModel(test_packet)
self.submodules.phy = FT2232HPHYSynchronous(self.model) self.submodules.phy = FT245PHYSynchronous(self.model)
self.submodules.streamer = PacketStreamer(phy_description(8)) self.submodules.streamer = PacketStreamer(phy_description(8))
self.submodules.streamer_randomizer = AckRandomizer(phy_description(8), level=10) self.submodules.streamer_randomizer = AckRandomizer(phy_description(8), level=10)