drtio: clock domains

This commit is contained in:
Sebastien Bourdeauducq 2016-10-14 00:34:59 +08:00
parent 018f6d1b52
commit c548a65ec3
2 changed files with 38 additions and 12 deletions

View File

@ -1,16 +1,31 @@
from types import SimpleNamespace
from migen import * from migen import *
from artiq.gateware.drtio import link_layer, rt_packets, iot from artiq.gateware.drtio import link_layer, rt_packets, iot
class DRTIOSatellite(Module): class DRTIOSatellite(Module):
def __init__(self, transceiver, channels, fine_ts_width=3, full_ts_width=63): def __init__(self, transceiver, rx_synchronizer, channels, fine_ts_width=3, full_ts_width=63):
self.submodules.link_layer = link_layer.LinkLayer( self.submodules.link_layer = link_layer.LinkLayer(
transceiver.encoder, transceiver.decoders) transceiver.encoder, transceiver.decoders)
self.submodules.rt_packets = rt_packets.RTPacketSatellite( link_layer_sync = SimpleNamespace(
self.link_layer) tx_aux_frame=self.link_layer.tx.aux_frame,
self.submodules.iot = iot.IOT( tx_aux_data=self.link_layer.tx_aux_data,
self.rt_packets, channels, fine_ts_width, full_ts_width) tx_aux_ack=self.link_layer.tx_aux_ack,
tx_rt_frame=self.link_layer.tx_rt_frame,
tx_rt_data=self.link_layer.tx_rt_data,
rx_aux_stb=rx_synchronizer.sync(self.link_layer.rx_aux_stb),
rx_aux_frame=rx_synchronizer.sync(self.link_layer.rx_aux_frame),
rx_aux_data=rx_synchronizer.sync(self.link_layer.rx_aux_data),
rx_rt_frame=rx_synchronizer.sync(self.link_layer.rx_rt_frame),
rx_rt_data=rx_synchronizer.sync(self.link_layer.rx_rt_data)
)
self.submodules.rt_packets = ClockDomainsRenamer("rtio")(
rt_packets.RTPacketSatellite(link_layer_sync))
self.submodules.iot = ClockDomainsRenamer("rtio")(
iot.IOT(self.rt_packets, channels, fine_ts_width, full_ts_width))
class DRTIOMaster(Module): class DRTIOMaster(Module):

View File

@ -3,6 +3,7 @@ from operator import xor, or_
from migen import * from migen import *
from migen.genlib.fsm import * from migen.genlib.fsm import *
from migen.genlib.cdc import MultiReg
class Scrambler(Module): class Scrambler(Module):
@ -210,24 +211,26 @@ class LinkLayerRX(Module):
class LinkLayer(Module): class LinkLayer(Module):
def __init__(self, encoder, decoders): def __init__(self, encoder, decoders):
# control signals, in rtio clock domain
self.reset = Signal() self.reset = Signal()
self.ready = Signal() self.ready = Signal()
# pulsed to reset receiver, rx_ready must immediately go low # pulsed to reset receiver, rx_ready must immediately go low
self.rx_reset = Signal() self.rx_reset = Signal()
# receiver locked including comma alignment # receiver locked including comma alignment
self.rx_ready = Signal() self.rx_ready = Signal()
tx = LinkLayerTX(encoder) tx = ClockDomainsRenamer("rtio")(LinkLayerTX(encoder))
rx = LinkLayerRX(decoders) rx = ClockDomainsRenamer("rtio_rx")(LinkLayerRX(decoders))
self.submodules += tx, rx self.submodules += tx, rx
# in rtio clock domain
self.tx_aux_frame = tx.aux_frame self.tx_aux_frame = tx.aux_frame
self.tx_aux_data = tx.aux_data self.tx_aux_data = tx.aux_data
self.tx_aux_ack = tx.aux_ack self.tx_aux_ack = tx.aux_ack
self.tx_rt_frame = tx.rt_frame self.tx_rt_frame = tx.rt_frame
self.tx_rt_data = tx.rt_data self.tx_rt_data = tx.rt_data
# in rtio_rx clock domain
self.rx_aux_stb = rx.aux_stb self.rx_aux_stb = rx.aux_stb
self.rx_aux_frame = rx.aux_frame self.rx_aux_frame = rx.aux_frame
self.rx_aux_data = rx.aux_data self.rx_aux_data = rx.aux_data
@ -236,11 +239,19 @@ class LinkLayer(Module):
# # # # # #
fsm = ResetInserter()(FSM(reset_state="RESET_RX")) fsm = ClockDomainsRenamer("rtio")(
ResetInserter()(FSM(reset_state="RESET_RX")))
self.submodules += fsm self.submodules += fsm
self.comb += fsm.reset.eq(self.reset) self.comb += fsm.reset.eq(self.reset)
rx_remote_rx_ready = Signal()
rx_link_init = Signal()
self.specials += [
MultiReg(rx.remote_rx_ready, rx_remote_rx_ready, "rtio"),
MultiReg(rx.link_init, rx_link_init, "rtio")
]
fsm.act("RESET_RX", fsm.act("RESET_RX",
tx.link_init.eq(1), tx.link_init.eq(1),
self.rx_reset.eq(1), self.rx_reset.eq(1),
@ -255,14 +266,14 @@ class LinkLayer(Module):
fsm.act("WAIT_REMOTE_RX_READY", fsm.act("WAIT_REMOTE_RX_READY",
tx.link_init.eq(1), tx.link_init.eq(1),
tx.signal_rx_ready.eq(1), tx.signal_rx_ready.eq(1),
If(rx.remote_rx_ready, If(rx_remote_rx_ready,
NextState("WAIT_REMOTE_LINK_UP") NextState("WAIT_REMOTE_LINK_UP")
) )
) )
fsm.act("WAIT_REMOTE_LINK_UP", fsm.act("WAIT_REMOTE_LINK_UP",
If(~rx.link_init, NextState("READY")) If(~rx_link_init, NextState("READY"))
) )
fsm.act("READY", fsm.act("READY",
If(rx.link_init, NextState("RESET_RX")), If(rx_link_init, NextState("RESET_RX")),
self.ready.eq(1) self.ready.eq(1)
) )