code clean up

This commit is contained in:
Florent Kermarrec 2015-02-09 09:26:56 +01:00
parent a8300a2e93
commit 996a56c335
7 changed files with 214 additions and 228 deletions

View File

@ -28,11 +28,9 @@ class LiteEthARPPacketizer(LiteEthPacketizer):
class LiteEthARPTX(Module): class LiteEthARPTX(Module):
def __init__(self, mac_address, ip_address): def __init__(self, mac_address, ip_address):
self.sink = sink = Sink(_arp_table_layout) self.sink = sink = Sink(_arp_table_layout)
self.source = Source(eth_mac_description(8)) self.source = source = Source(eth_mac_description(8))
### ###
packetizer = LiteEthARPPacketizer() self.submodules.packetizer = packetizer = LiteEthARPPacketizer()
self.submodules += packetizer
source = packetizer.sink
counter = Counter(max=max(arp_header_len, eth_min_len)) counter = Counter(max=max(arp_header_len, eth_min_len))
self.submodules += counter self.submodules += counter
@ -47,34 +45,35 @@ class LiteEthARPTX(Module):
) )
) )
self.comb += [ self.comb += [
source.sop.eq(counter.value == 0), packetizer.sink.sop.eq(counter.value == 0),
source.eop.eq(counter.value == max(arp_header_len, eth_min_len)-1), packetizer.sink.eop.eq(counter.value == max(arp_header_len, eth_min_len)-1),
source.hwtype.eq(arp_hwtype_ethernet), packetizer.sink.hwtype.eq(arp_hwtype_ethernet),
source.proto.eq(arp_proto_ip), packetizer.sink.proto.eq(arp_proto_ip),
source.hwsize.eq(6), packetizer.sink.hwsize.eq(6),
source.protosize.eq(4), packetizer.sink.protosize.eq(4),
source.sender_mac.eq(mac_address), packetizer.sink.sender_mac.eq(mac_address),
source.sender_ip.eq(ip_address), packetizer.sink.sender_ip.eq(ip_address),
If(sink.reply, If(sink.reply,
source.opcode.eq(arp_opcode_reply), packetizer.sink.opcode.eq(arp_opcode_reply),
source.target_mac.eq(sink.mac_address), packetizer.sink.target_mac.eq(sink.mac_address),
source.target_ip.eq(sink.ip_address) packetizer.sink.target_ip.eq(sink.ip_address)
).Elif(sink.request, ).Elif(sink.request,
source.opcode.eq(arp_opcode_request),
source.target_mac.eq(0xffffffffffff), packetizer.sink.opcode.eq(arp_opcode_request),
source.target_ip.eq(sink.ip_address) packetizer.sink.target_mac.eq(0xffffffffffff),
packetizer.sink.target_ip.eq(sink.ip_address)
) )
] ]
fsm.act("SEND", fsm.act("SEND",
source.stb.eq(1), packetizer.sink.stb.eq(1),
Record.connect(packetizer.source, self.source), Record.connect(packetizer.source, source),
self.source.target_mac.eq(source.target_mac), source.target_mac.eq(packetizer.sink.target_mac),
self.source.sender_mac.eq(mac_address), source.sender_mac.eq(mac_address),
self.source.ethernet_type.eq(ethernet_type_arp), source.ethernet_type.eq(ethernet_type_arp),
If(self.source.stb & self.source.ack, If(source.stb & source.ack,
sink.ack.eq(source.eop),
counter.ce.eq(1), counter.ce.eq(1),
If(self.source.eop, If(source.eop,
sink.ack.eq(1),
NextState("IDLE") NextState("IDLE")
) )
) )
@ -82,41 +81,39 @@ class LiteEthARPTX(Module):
class LiteEthARPRX(Module): class LiteEthARPRX(Module):
def __init__(self, mac_address, ip_address): def __init__(self, mac_address, ip_address):
self.sink = Sink(eth_mac_description(8)) self.sink = sink = Sink(eth_mac_description(8))
self.source = source = Source(_arp_table_layout) self.source = source = Source(_arp_table_layout)
### ###
depacketizer = LiteEthARPDepacketizer() self.submodules.depacketizer = depacketizer = LiteEthARPDepacketizer()
self.submodules += depacketizer self.comb += Record.connect(sink, depacketizer.sink)
self.comb += Record.connect(self.sink, depacketizer.sink)
sink = depacketizer.source
self.submodules.fsm = fsm = FSM(reset_state="IDLE") self.submodules.fsm = fsm = FSM(reset_state="IDLE")
fsm.act("IDLE", fsm.act("IDLE",
sink.ack.eq(1), depacketizer.source.ack.eq(1),
If(sink.stb & sink.sop, If(depacketizer.source.stb & depacketizer.source.sop,
sink.ack.eq(0), depacketizer.source.ack.eq(0),
NextState("CHECK") NextState("CHECK")
) )
) )
valid = Signal() valid = Signal()
self.comb += valid.eq( self.comb += valid.eq(
sink.stb & depacketizer.source.stb &
(sink.hwtype == arp_hwtype_ethernet) & (depacketizer.source.hwtype == arp_hwtype_ethernet) &
(sink.proto == arp_proto_ip) & (depacketizer.source.proto == arp_proto_ip) &
(sink.hwsize == 6) & (depacketizer.source.hwsize == 6) &
(sink.protosize == 4) & (depacketizer.source.protosize == 4) &
(sink.target_ip == ip_address) (depacketizer.source.target_ip == ip_address)
) )
reply = Signal() reply = Signal()
request = Signal() request = Signal()
self.comb += Case(sink.opcode, { self.comb += Case(depacketizer.source.opcode, {
arp_opcode_request : [request.eq(1)], arp_opcode_request : [request.eq(1)],
arp_opcode_reply : [reply.eq(1)], arp_opcode_reply : [reply.eq(1)],
"default" : [] "default" : []
}) })
self.comb += [ self.comb += [
source.ip_address.eq(sink.sender_ip), source.ip_address.eq(depacketizer.source.sender_ip),
source.mac_address.eq(sink.sender_mac) source.mac_address.eq(depacketizer.source.sender_mac)
] ]
fsm.act("CHECK", fsm.act("CHECK",
If(valid, If(valid,
@ -127,8 +124,8 @@ class LiteEthARPRX(Module):
NextState("TERMINATE") NextState("TERMINATE")
), ),
fsm.act("TERMINATE", fsm.act("TERMINATE",
sink.ack.eq(1), depacketizer.source.ack.eq(1),
If(sink.stb & sink.eop, If(depacketizer.source.stb & depacketizer.source.eop,
NextState("IDLE") NextState("IDLE")
) )
) )
@ -153,8 +150,8 @@ class LiteEthARPTable(Module):
request_ip_address.d.eq(request.ip_address) request_ip_address.d.eq(request.ip_address)
] ]
# Note: Only store 1 IP/MAC couple, can be improved with a real # Note: Store only 1 IP/MAC couple, can be improved with a real
# table in the future to improve performance when packet are # table in the future to improve performance when packets are
# targeting multiple destinations. # targeting multiple destinations.
update = Signal() update = Signal()
cached_valid = Signal() cached_valid = Signal()
@ -166,7 +163,7 @@ class LiteEthARPTable(Module):
self.submodules.fsm = fsm = FSM(reset_state="IDLE") self.submodules.fsm = fsm = FSM(reset_state="IDLE")
fsm.act("IDLE", fsm.act("IDLE",
# Note: for simplicicy, if APR table is busy response from arp_rx # Note: for simplicicy, if APR table is busy response from arp_rx
# is lost. This is compensated by the protocol (retry) # is lost. This is compensated by the protocol (retries)
If(sink.stb & sink.request, If(sink.stb & sink.request,
NextState("SEND_REPLY") NextState("SEND_REPLY")
).Elif(sink.stb & sink.reply & request_pending.q, ).Elif(sink.stb & sink.reply & request_pending.q,
@ -251,15 +248,15 @@ class LiteEthARPTable(Module):
class LiteEthARP(Module): class LiteEthARP(Module):
def __init__(self, mac, mac_address, ip_address, clk_freq): def __init__(self, mac, mac_address, ip_address, clk_freq):
self.submodules.tx = LiteEthARPTX(mac_address, ip_address) self.submodules.tx = tx = LiteEthARPTX(mac_address, ip_address)
self.submodules.rx = LiteEthARPRX(mac_address, ip_address) self.submodules.rx = rx = LiteEthARPRX(mac_address, ip_address)
self.submodules.table = LiteEthARPTable(clk_freq) self.submodules.table = table = LiteEthARPTable(clk_freq)
self.comb += [ self.comb += [
Record.connect(self.rx.source, self.table.sink), Record.connect(rx.source, table.sink),
Record.connect(self.table.source, self.tx.sink) Record.connect(table.source, tx.sink)
] ]
mac_port = mac.crossbar.get_port(ethernet_type_arp) mac_port = mac.crossbar.get_port(ethernet_type_arp)
self.comb += [ self.comb += [
Record.connect(self.tx.source, mac_port.sink), Record.connect(tx.source, mac_port.sink),
Record.connect(mac_port.source, self.rx.sink) Record.connect(mac_port.source, rx.sink)
] ]

View File

@ -20,64 +20,60 @@ class LiteEthICMPPacketizer(LiteEthPacketizer):
class LiteEthICMPTX(Module): class LiteEthICMPTX(Module):
def __init__(self, ip_address): def __init__(self, ip_address):
self.sink = Sink(eth_icmp_user_description(8)) self.sink = sink = Sink(eth_icmp_user_description(8))
self.source = Source(eth_ipv4_user_description(8)) self.source = source = Source(eth_ipv4_user_description(8))
### ###
packetizer = LiteEthICMPPacketizer() self.submodules.packetizer = packetizer = LiteEthICMPPacketizer()
self.submodules += packetizer
self.comb += [ self.comb += [
packetizer.sink.stb.eq(self.sink.stb), packetizer.sink.stb.eq(sink.stb),
packetizer.sink.sop.eq(self.sink.sop), packetizer.sink.sop.eq(sink.sop),
packetizer.sink.eop.eq(self.sink.eop), packetizer.sink.eop.eq(sink.eop),
self.sink.ack.eq(packetizer.sink.ack), sink.ack.eq(packetizer.sink.ack),
packetizer.sink.msgtype.eq(self.sink.msgtype), packetizer.sink.msgtype.eq(sink.msgtype),
packetizer.sink.code.eq(self.sink.code), packetizer.sink.code.eq(sink.code),
packetizer.sink.checksum.eq(self.sink.checksum), packetizer.sink.checksum.eq(sink.checksum),
packetizer.sink.quench.eq(self.sink.quench), packetizer.sink.quench.eq(sink.quench),
packetizer.sink.data.eq(self.sink.data) packetizer.sink.data.eq(sink.data)
] ]
sink = packetizer.source
self.submodules.fsm = fsm = FSM(reset_state="IDLE") self.submodules.fsm = fsm = FSM(reset_state="IDLE")
fsm.act("IDLE", fsm.act("IDLE",
sink.ack.eq(1), packetizer.source.ack.eq(1),
If(sink.stb & sink.sop, If(packetizer.source.stb & packetizer.source.sop,
sink.ack.eq(0), packetizer.source.ack.eq(0),
NextState("SEND") NextState("SEND")
) )
) )
fsm.act("SEND", fsm.act("SEND",
Record.connect(packetizer.source, self.source), Record.connect(packetizer.source, source),
self.source.length.eq(self.sink.length + icmp_header_len), source.length.eq(sink.length + icmp_header_len),
self.source.protocol.eq(icmp_protocol), source.protocol.eq(icmp_protocol),
self.source.ip_address.eq(self.sink.ip_address), source.ip_address.eq(sink.ip_address),
If(self.source.stb & self.source.eop & self.source.ack, If(source.stb & source.eop & source.ack,
NextState("IDLE") NextState("IDLE")
) )
) )
class LiteEthICMPRX(Module): class LiteEthICMPRX(Module):
def __init__(self, ip_address): def __init__(self, ip_address):
self.sink = Sink(eth_ipv4_user_description(8)) self.sink = sink = Sink(eth_ipv4_user_description(8))
self.source = source = Source(eth_icmp_user_description(8)) self.source = source = Source(eth_icmp_user_description(8))
### ###
depacketizer = LiteEthICMPDepacketizer() self.submodules.depacketizer = depacketizer = LiteEthICMPDepacketizer()
self.submodules += depacketizer self.comb += Record.connect(sink, depacketizer.sink)
self.comb += Record.connect(self.sink, depacketizer.sink)
sink = depacketizer.source
self.submodules.fsm = fsm = FSM(reset_state="IDLE") self.submodules.fsm = fsm = FSM(reset_state="IDLE")
fsm.act("IDLE", fsm.act("IDLE",
sink.ack.eq(1), depacketizer.source.ack.eq(1),
If(sink.stb & sink.sop, If(depacketizer.source.stb & depacketizer.source.sop,
sink.ack.eq(0), depacketizer.source.ack.eq(0),
NextState("CHECK") NextState("CHECK")
) )
) )
valid = Signal() valid = Signal()
self.comb += valid.eq( self.comb += valid.eq(
sink.stb & depacketizer.source.stb &
(self.sink.protocol == icmp_protocol) (sink.protocol == icmp_protocol)
) )
fsm.act("CHECK", fsm.act("CHECK",
If(valid, If(valid,
@ -87,55 +83,55 @@ class LiteEthICMPRX(Module):
) )
) )
self.comb += [ self.comb += [
source.sop.eq(sink.sop), source.sop.eq(depacketizer.source.sop),
source.eop.eq(sink.eop), source.eop.eq(depacketizer.source.eop),
source.msgtype.eq(sink.msgtype), source.msgtype.eq(depacketizer.source.msgtype),
source.code.eq(sink.code), source.code.eq(depacketizer.source.code),
source.checksum.eq(sink.checksum), source.checksum.eq(depacketizer.source.checksum),
source.quench.eq(sink.quench), source.quench.eq(depacketizer.source.quench),
source.ip_address.eq(self.sink.ip_address), source.ip_address.eq(sink.ip_address),
source.length.eq(self.sink.length - icmp_header_len), source.length.eq(sink.length - icmp_header_len),
source.data.eq(sink.data), source.data.eq(depacketizer.source.data),
source.error.eq(sink.error) source.error.eq(depacketizer.source.error)
] ]
fsm.act("PRESENT", fsm.act("PRESENT",
source.stb.eq(sink.stb), source.stb.eq(depacketizer.source.stb),
sink.ack.eq(source.ack), depacketizer.source.ack.eq(source.ack),
If(source.stb & source.eop & source.ack, If(source.stb & source.eop & source.ack,
NextState("IDLE") NextState("IDLE")
) )
) )
fsm.act("DROP", fsm.act("DROP",
sink.ack.eq(1), depacketizer.source.ack.eq(1),
If(sink.stb & sink.eop & sink.ack, If(depacketizer.source.stb & depacketizer.source.eop & depacketizer.source.ack,
NextState("IDLE") NextState("IDLE")
) )
) )
class LiteEthICMPEcho(Module): class LiteEthICMPEcho(Module):
def __init__(self): def __init__(self):
self.sink = Sink(eth_icmp_user_description(8)) self.sink = sink = Sink(eth_icmp_user_description(8))
self.source = Source(eth_icmp_user_description(8)) self.source = source = Source(eth_icmp_user_description(8))
### ###
self.submodules.fifo = SyncFIFO(eth_icmp_user_description(8), 512, buffered=True) self.submodules.fifo = fifo = SyncFIFO(eth_icmp_user_description(8), 512, buffered=True)
self.comb += [ self.comb += [
Record.connect(self.sink, self.fifo.sink), Record.connect(sink, fifo.sink),
Record.connect(self.fifo.source, self.source), Record.connect(fifo.source, source),
self.source.msgtype.eq(0x0), self.source.msgtype.eq(0x0),
self.source.checksum.eq(~((~self.fifo.source.checksum)-0x0800)) self.source.checksum.eq(~((~fifo.source.checksum)-0x0800))
] ]
class LiteEthICMP(Module): class LiteEthICMP(Module):
def __init__(self, ip, ip_address): def __init__(self, ip, ip_address):
self.submodules.tx = LiteEthICMPTX(ip_address) self.submodules.tx = tx = LiteEthICMPTX(ip_address)
self.submodules.rx = LiteEthICMPRX(ip_address) self.submodules.rx = rx = LiteEthICMPRX(ip_address)
self.submodules.echo = LiteEthICMPEcho() self.submodules.echo = echo = LiteEthICMPEcho()
self.comb += [ self.comb += [
Record.connect(self.rx.source, self.echo.sink), Record.connect(rx.source, echo.sink),
Record.connect(self.echo.source, self.tx.sink) Record.connect(echo.source, tx.sink)
] ]
ip_port = ip.crossbar.get_port(icmp_protocol) ip_port = ip.crossbar.get_port(icmp_protocol)
self.comb += [ self.comb += [
Record.connect(self.tx.source, ip_port.sink), Record.connect(tx.source, ip_port.sink),
Record.connect(ip_port.source, self.rx.sink) Record.connect(ip_port.source, rx.sink)
] ]

View File

@ -20,14 +20,14 @@ class LiteEthIPV4Packetizer(LiteEthPacketizer):
ipv4_header_len) ipv4_header_len)
class LiteEthIPV4Checksum(Module): class LiteEthIPV4Checksum(Module):
def __init__(self, skip_header=False): def __init__(self, skip_checksum=False):
self.header = Signal(ipv4_header_len*8) self.header = Signal(ipv4_header_len*8)
self.value = Signal(16) self.value = Signal(16)
###
s = Signal(17) s = Signal(17)
r = Signal(17) r = Signal(17)
for i in range(ipv4_header_len//2): for i in range(ipv4_header_len//2):
if skip_header and i == 5: if skip_checksum and (i == ipv4_header["checksum"].byte//2):
pass pass
else: else:
s_next = Signal(17) s_next = Signal(17)
@ -41,31 +41,28 @@ class LiteEthIPV4Checksum(Module):
class LiteEthIPTX(Module): class LiteEthIPTX(Module):
def __init__(self, mac_address, ip_address, arp_table): def __init__(self, mac_address, ip_address, arp_table):
self.sink = Sink(eth_ipv4_user_description(8)) self.sink = sink = Sink(eth_ipv4_user_description(8))
self.source = Source(eth_mac_description(8)) self.source = source = Source(eth_mac_description(8))
self.target_unreachable = Signal() self.target_unreachable = Signal()
### ###
packetizer = LiteEthIPV4Packetizer() self.submodules.packetizer = packetizer = LiteEthIPV4Packetizer()
self.submodules += packetizer
self.comb += [ self.comb += [
packetizer.sink.stb.eq(self.sink.stb), packetizer.sink.stb.eq(sink.stb),
packetizer.sink.sop.eq(self.sink.sop), packetizer.sink.sop.eq(sink.sop),
packetizer.sink.eop.eq(self.sink.eop), packetizer.sink.eop.eq(sink.eop),
self.sink.ack.eq(packetizer.sink.ack), sink.ack.eq(packetizer.sink.ack),
packetizer.sink.target_ip.eq(self.sink.ip_address), packetizer.sink.target_ip.eq(sink.ip_address),
packetizer.sink.protocol.eq(self.sink.protocol), packetizer.sink.protocol.eq(sink.protocol),
packetizer.sink.total_length.eq(self.sink.length + (0x5*4)), packetizer.sink.total_length.eq(sink.length + (0x5*4)),
packetizer.sink.version.eq(0x4), # ipv4 packetizer.sink.version.eq(0x4), # ipv4
packetizer.sink.ihl.eq(0x5), # 20 bytes packetizer.sink.ihl.eq(0x5), # 20 bytes
packetizer.sink.identification.eq(0), packetizer.sink.identification.eq(0),
packetizer.sink.ttl.eq(0x80), packetizer.sink.ttl.eq(0x80),
packetizer.sink.sender_ip.eq(ip_address), packetizer.sink.sender_ip.eq(ip_address),
packetizer.sink.data.eq(self.sink.data) packetizer.sink.data.eq(sink.data)
] ]
sink = packetizer.source
checksum = LiteEthIPV4Checksum(skip_header=True) self.submodules.checksum = checksum = LiteEthIPV4Checksum(skip_checksum=True)
self.submodules += checksum
self.comb += [ self.comb += [
checksum.header.eq(packetizer.header), checksum.header.eq(packetizer.header),
packetizer.sink.checksum.eq(checksum.value) packetizer.sink.checksum.eq(checksum.value)
@ -75,13 +72,13 @@ class LiteEthIPTX(Module):
self.submodules.fsm = fsm = FSM(reset_state="IDLE") self.submodules.fsm = fsm = FSM(reset_state="IDLE")
fsm.act("IDLE", fsm.act("IDLE",
sink.ack.eq(1), packetizer.source.ack.eq(1),
If(sink.stb & sink.sop, If(packetizer.source.stb & packetizer.source.sop,
sink.ack.eq(0), packetizer.source.ack.eq(0),
NextState("SEND_MAC_ADDRESS_REQUEST") NextState("SEND_MAC_ADDRESS_REQUEST")
) )
) )
self.comb += arp_table.request.ip_address.eq(self.sink.ip_address) self.comb += arp_table.request.ip_address.eq(sink.ip_address)
fsm.act("SEND_MAC_ADDRESS_REQUEST", fsm.act("SEND_MAC_ADDRESS_REQUEST",
arp_table.request.stb.eq(1), arp_table.request.stb.eq(1),
If(arp_table.request.stb & arp_table.request.ack, If(arp_table.request.stb & arp_table.request.ack,
@ -99,13 +96,16 @@ class LiteEthIPTX(Module):
) )
) )
) )
self.sync += If(arp_table.response.stb, target_mac.eq(arp_table.response.mac_address)) self.sync += \
If(arp_table.response.stb,
target_mac.eq(arp_table.response.mac_address)
)
fsm.act("SEND", fsm.act("SEND",
Record.connect(packetizer.source, self.source), Record.connect(packetizer.source, source),
self.source.ethernet_type.eq(ethernet_type_ip), source.ethernet_type.eq(ethernet_type_ip),
self.source.target_mac.eq(target_mac), source.target_mac.eq(target_mac),
self.source.sender_mac.eq(mac_address), source.sender_mac.eq(mac_address),
If(self.source.stb & self.source.eop & self.source.ack, If(source.stb & source.eop & source.ack,
NextState("IDLE") NextState("IDLE")
) )
) )
@ -118,32 +118,29 @@ class LiteEthIPTX(Module):
class LiteEthIPRX(Module): class LiteEthIPRX(Module):
def __init__(self, mac_address, ip_address): def __init__(self, mac_address, ip_address):
self.sink = Sink(eth_mac_description(8)) self.sink = sink = Sink(eth_mac_description(8))
self.source = source = Source(eth_ipv4_user_description(8)) self.source = source = Source(eth_ipv4_user_description(8))
### ###
depacketizer = LiteEthIPV4Depacketizer() self.submodules.depacketizer = depacketizer = LiteEthIPV4Depacketizer()
self.submodules += depacketizer self.comb += Record.connect(sink, depacketizer.sink)
self.comb += Record.connect(self.sink, depacketizer.sink)
sink = depacketizer.source
checksum = LiteEthIPV4Checksum(skip_header=False) self.submodules.checksum = checksum = LiteEthIPV4Checksum(skip_checksum=False)
self.submodules += checksum
self.comb += checksum.header.eq(depacketizer.header) self.comb += checksum.header.eq(depacketizer.header)
self.submodules.fsm = fsm = FSM(reset_state="IDLE") self.submodules.fsm = fsm = FSM(reset_state="IDLE")
fsm.act("IDLE", fsm.act("IDLE",
sink.ack.eq(1), depacketizer.source.ack.eq(1),
If(sink.stb & sink.sop, If(depacketizer.source.stb & depacketizer.source.sop,
sink.ack.eq(0), depacketizer.source.ack.eq(0),
NextState("CHECK") NextState("CHECK")
) )
) )
valid = Signal() valid = Signal()
self.comb += valid.eq( self.comb += valid.eq(
sink.stb & depacketizer.source.stb &
(sink.target_ip == ip_address) & (depacketizer.source.target_ip == ip_address) &
(sink.version == 0x4) & (depacketizer.source.version == 0x4) &
(sink.ihl == 0x5) & (depacketizer.source.ihl == 0x5) &
(checksum.value == 0) (checksum.value == 0)
) )
@ -155,39 +152,39 @@ class LiteEthIPRX(Module):
) )
) )
self.comb += [ self.comb += [
source.sop.eq(sink.sop), source.sop.eq(depacketizer.source.sop),
source.eop.eq(sink.eop), source.eop.eq(depacketizer.source.eop),
source.length.eq(sink.total_length - (0x5*4)), source.length.eq(depacketizer.source.total_length - (0x5*4)),
source.protocol.eq(sink.protocol), source.protocol.eq(depacketizer.source.protocol),
source.ip_address.eq(sink.sender_ip), source.ip_address.eq(depacketizer.source.sender_ip),
source.data.eq(sink.data), source.data.eq(depacketizer.source.data),
source.error.eq(sink.error) source.error.eq(depacketizer.source.error)
] ]
fsm.act("PRESENT", fsm.act("PRESENT",
source.stb.eq(sink.stb), source.stb.eq(depacketizer.source.stb),
sink.ack.eq(source.ack), depacketizer.source.ack.eq(source.ack),
If(source.stb & source.eop & source.ack, If(source.stb & source.eop & source.ack,
NextState("IDLE") NextState("IDLE")
) )
) )
fsm.act("DROP", fsm.act("DROP",
sink.ack.eq(1), depacketizer.source.ack.eq(1),
If(sink.stb & sink.eop & sink.ack, If(depacketizer.source.stb & depacketizer.source.eop & depacketizer.source.ack,
NextState("IDLE") NextState("IDLE")
) )
) )
class LiteEthIP(Module): class LiteEthIP(Module):
def __init__(self, mac, mac_address, ip_address, arp_table): def __init__(self, mac, mac_address, ip_address, arp_table):
self.submodules.tx = LiteEthIPTX(mac_address, ip_address, arp_table) self.submodules.tx = tx = LiteEthIPTX(mac_address, ip_address, arp_table)
self.submodules.rx = LiteEthIPRX(mac_address, ip_address) self.submodules.rx = rx = LiteEthIPRX(mac_address, ip_address)
mac_port = mac.crossbar.get_port(ethernet_type_ip) mac_port = mac.crossbar.get_port(ethernet_type_ip)
self.comb += [ self.comb += [
Record.connect(self.tx.source, mac_port.sink), Record.connect(tx.source, mac_port.sink),
Record.connect(mac_port.source, self.rx.sink) Record.connect(mac_port.source, rx.sink)
] ]
self.submodules.crossbar = LiteEthIPV4Crossbar() self.submodules.crossbar = crossbar = LiteEthIPV4Crossbar()
self.comb += [ self.comb += [
Record.connect(self.crossbar.master.source, self.tx.sink), Record.connect(crossbar.master.source, tx.sink),
Record.connect(self.rx.source, self.crossbar.master.sink) Record.connect(rx.source, crossbar.master.sink)
] ]

View File

@ -13,7 +13,7 @@ class LiteEthIPV4Crossbar(Module):
def get_port(self, protocol): def get_port(self, protocol):
port = LiteEthIPV4UserPort(8) port = LiteEthIPV4UserPort(8)
if protocol in self.users.keys(): if protocol in self.users.keys():
raise ValueError("Protocol {} already used".format(protocol)) raise ValueError("Protocol {0:#x} already assigned".format(protocol))
self.users[protocol] = port self.users[protocol] = port
return port return port

View File

@ -20,64 +20,60 @@ class LiteEthUDPPacketizer(LiteEthPacketizer):
class LiteEthUDPTX(Module): class LiteEthUDPTX(Module):
def __init__(self, ip_address): def __init__(self, ip_address):
self.sink = Sink(eth_udp_user_description(8)) self.sink = sink = Sink(eth_udp_user_description(8))
self.source = Source(eth_ipv4_user_description(8)) self.source = source = Source(eth_ipv4_user_description(8))
### ###
packetizer = LiteEthUDPPacketizer() self.submodules.packetizer = packetizer = LiteEthUDPPacketizer()
self.submodules += packetizer
self.comb += [ self.comb += [
packetizer.sink.stb.eq(self.sink.stb), packetizer.sink.stb.eq(sink.stb),
packetizer.sink.sop.eq(self.sink.sop), packetizer.sink.sop.eq(sink.sop),
packetizer.sink.eop.eq(self.sink.eop), packetizer.sink.eop.eq(sink.eop),
self.sink.ack.eq(packetizer.sink.ack), sink.ack.eq(packetizer.sink.ack),
packetizer.sink.src_port.eq(self.sink.src_port), packetizer.sink.src_port.eq(sink.src_port),
packetizer.sink.dst_port.eq(self.sink.dst_port), packetizer.sink.dst_port.eq(sink.dst_port),
packetizer.sink.length.eq(self.sink.length + udp_header_len), packetizer.sink.length.eq(sink.length + udp_header_len),
packetizer.sink.checksum.eq(0), packetizer.sink.checksum.eq(0), # Disabled (MAC CRC is enough)
packetizer.sink.data.eq(self.sink.data) packetizer.sink.data.eq(sink.data)
] ]
sink = packetizer.source
self.submodules.fsm = fsm = FSM(reset_state="IDLE") self.submodules.fsm = fsm = FSM(reset_state="IDLE")
fsm.act("IDLE", fsm.act("IDLE",
sink.ack.eq(1), packetizer.source.ack.eq(1),
If(sink.stb & sink.sop, If(packetizer.source.stb & packetizer.source.sop,
sink.ack.eq(0), packetizer.source.ack.eq(0),
NextState("SEND") NextState("SEND")
) )
) )
fsm.act("SEND", fsm.act("SEND",
Record.connect(packetizer.source, self.source), Record.connect(packetizer.source, source),
self.source.length.eq(packetizer.sink.length), source.length.eq(packetizer.sink.length),
self.source.protocol.eq(udp_protocol), source.protocol.eq(udp_protocol),
self.source.ip_address.eq(self.sink.ip_address), source.ip_address.eq(sink.ip_address),
If(self.source.stb & self.source.eop & self.source.ack, If(source.stb & source.eop & source.ack,
NextState("IDLE") NextState("IDLE")
) )
) )
class LiteEthUDPRX(Module): class LiteEthUDPRX(Module):
def __init__(self, ip_address): def __init__(self, ip_address):
self.sink = Sink(eth_ipv4_user_description(8)) self.sink = sink = Sink(eth_ipv4_user_description(8))
self.source = source = Source(eth_udp_user_description(8)) self.source = source = Source(eth_udp_user_description(8))
### ###
depacketizer = LiteEthUDPDepacketizer() self.submodules.depacketizer = depacketizer = LiteEthUDPDepacketizer()
self.submodules += depacketizer self.comb += Record.connect(sink, depacketizer.sink)
self.comb += Record.connect(self.sink, depacketizer.sink)
sink = depacketizer.source
self.submodules.fsm = fsm = FSM(reset_state="IDLE") self.submodules.fsm = fsm = FSM(reset_state="IDLE")
fsm.act("IDLE", fsm.act("IDLE",
sink.ack.eq(1), depacketizer.source.ack.eq(1),
If(sink.stb & sink.sop, If(depacketizer.source.stb & depacketizer.source.sop,
sink.ack.eq(0), depacketizer.source.ack.eq(0),
NextState("CHECK") NextState("CHECK")
) )
) )
valid = Signal() valid = Signal()
self.comb += valid.eq( self.comb += valid.eq(
sink.stb & depacketizer.source.stb &
(self.sink.protocol == udp_protocol) (sink.protocol == udp_protocol)
) )
fsm.act("CHECK", fsm.act("CHECK",
@ -88,43 +84,43 @@ class LiteEthUDPRX(Module):
) )
) )
self.comb += [ self.comb += [
source.sop.eq(sink.sop), source.sop.eq(depacketizer.source.sop),
source.eop.eq(sink.eop), source.eop.eq(depacketizer.source.eop),
source.src_port.eq(sink.src_port), source.src_port.eq(depacketizer.source.src_port),
source.dst_port.eq(sink.dst_port), source.dst_port.eq(depacketizer.source.dst_port),
source.ip_address.eq(self.sink.ip_address), source.ip_address.eq(sink.ip_address),
source.length.eq(sink.length - udp_header_len), source.length.eq(depacketizer.source.length - udp_header_len),
source.data.eq(sink.data), source.data.eq(depacketizer.source.data),
source.error.eq(sink.error) source.error.eq(depacketizer.source.error)
] ]
fsm.act("PRESENT", fsm.act("PRESENT",
source.stb.eq(sink.stb), source.stb.eq(depacketizer.source.stb),
sink.ack.eq(source.ack), depacketizer.source.ack.eq(source.ack),
If(source.stb & source.eop & source.ack, If(source.stb & source.eop & source.ack,
NextState("IDLE") NextState("IDLE")
) )
) )
fsm.act("DROP", fsm.act("DROP",
sink.ack.eq(1), depacketizer.source.ack.eq(1),
If(sink.stb & sink.eop & sink.ack, If(depacketizer.source.stb & depacketizer.source.eop & depacketizer.source.ack,
NextState("IDLE") NextState("IDLE")
) )
) )
class LiteEthUDP(Module): class LiteEthUDP(Module):
def __init__(self, ip, ip_address, with_loopback): def __init__(self, ip, ip_address, with_loopback):
self.submodules.tx = LiteEthUDPTX(ip_address) self.submodules.tx = tx = LiteEthUDPTX(ip_address)
self.submodules.rx = LiteEthUDPRX(ip_address) self.submodules.rx = rx = LiteEthUDPRX(ip_address)
ip_port = ip.crossbar.get_port(udp_protocol) ip_port = ip.crossbar.get_port(udp_protocol)
self.comb += [ self.comb += [
Record.connect(self.tx.source, ip_port.sink), Record.connect(tx.source, ip_port.sink),
Record.connect(ip_port.source, self.rx.sink) Record.connect(ip_port.source, rx.sink)
] ]
if with_loopback: if with_loopback:
self.submodules.fifo = SyncFIFO(eth_udp_user_description(8), 2048, buffered=True) self.submodules.fifo = fifo = SyncFIFO(eth_udp_user_description(8), 2048, buffered=True)
self.comb += [ self.comb += [
Record.connect(self.rx.source, self.fifo.sink), Record.connect(rx.source, fifo.sink),
Record.connect(self.fifo.source, self.tx.sink) Record.connect(fifo.source, tx.sink)
] ]
else: else:
self.sink, self.source = self.tx.sink, self.rx.source self.sink, self.source = self.tx.sink, self.rx.source

View File

@ -13,7 +13,7 @@ class LiteEthMACCrossbar(Module):
def get_port(self, ethernet_type): def get_port(self, ethernet_type):
port = LiteEthMACUserPort(8) port = LiteEthMACUserPort(8)
if ethernet_type in self.users.keys(): if ethernet_type in self.users.keys():
raise ValueError("Ethernet type {} already used".format(ethernet_type)) raise ValueError("Ethernet type {0:#x} already assigned".format(ethernet_type))
self.users[ethernet_type] = port self.users[ethernet_type] = port
return port return port

View File

@ -3,7 +3,7 @@ from config import *
wb.open() wb.open()
regs = wb.regs regs = wb.regs
### ###
regs.ethphy_crg_reset.write(1) regs.phy_crg_reset.write(1)
print("sysid : 0x%04x" %regs.identifier_sysid.read()) print("sysid : 0x%04x" %regs.identifier_sysid.read())
print("revision : 0x%04x" %regs.identifier_revision.read()) print("revision : 0x%04x" %regs.identifier_revision.read())
print("frequency : %d MHz" %(regs.identifier_frequency.read()/1000000)) print("frequency : %d MHz" %(regs.identifier_frequency.read()/1000000))