scrambling: cleanup/fix Descrambler synchronization

This commit is contained in:
Florent Kermarrec 2019-11-13 09:53:32 +01:00
parent f49ce9bbdf
commit 8955d24c7a
2 changed files with 36 additions and 17 deletions

View File

@ -5,7 +5,7 @@ import unittest
from migen import * from migen import *
from usb3_pipe.scrambling import Scrambler from usb3_pipe.scrambling import Scrambler, Descrambler
scrambler_ref = [ scrambler_ref = [
0x8dbf6dbe, 0xe6a740be, 0xb2e2d32c, 0x2a770207, 0x8dbf6dbe, 0xe6a740be, 0xb2e2d32c, 0x2a770207,
@ -26,7 +26,7 @@ scrambler_ref = [
0xd514af76, 0xb660ac4f, 0xb762d679, 0x2ae5e743 0xd514af76, 0xb660ac4f, 0xb762d679, 0x2ae5e743
] ]
class TestScrambler(unittest.TestCase): class TestScrambling(unittest.TestCase):
def test_scrambler_data(self): def test_scrambler_data(self):
def generator(dut): def generator(dut):
yield dut.source.ready.eq(1) yield dut.source.ready.eq(1)
@ -55,3 +55,28 @@ class TestScrambler(unittest.TestCase):
dut = Scrambler() dut = Scrambler()
run_simulation(dut, generator(dut)) run_simulation(dut, generator(dut))
def test_descrambler_data(self):
def generator(dut):
for i in range(16):
yield dut.sink.valid.eq(1)
yield dut.sink.data.eq(0)
yield
for i in range(16):
yield dut.sink.valid.eq(1)
yield dut.sink.data.eq(scrambler_ref[i])
yield
yield dut.sink.valid.eq(0)
for i in range(64):
yield
def checker(dut):
yield dut.source.ready.eq(1)
while (yield dut.source.valid) == 0:
yield
for i in range(16):
self.assertEqual((yield dut.source.data), 0)
yield
dut = Descrambler()
run_simulation(dut, [generator(dut), checker(dut)], vcd_name="toto.vcd")

View File

@ -77,7 +77,6 @@ class ScramblerUnit(Module):
class Scrambler(Module): class Scrambler(Module):
def __init__(self): def __init__(self):
self.enable = Signal(reset=1)
self.sink = sink = stream.Endpoint([("data", 32), ("ctrl", 4)]) self.sink = sink = stream.Endpoint([("data", 32), ("ctrl", 4)])
self.source = source = stream.Endpoint([("data", 32), ("ctrl", 4)]) self.source = source = stream.Endpoint([("data", 32), ("ctrl", 4)])
@ -89,21 +88,17 @@ class Scrambler(Module):
self.comb += sink.connect(source) self.comb += sink.connect(source)
for i in range(4): for i in range(4):
self.comb += [ self.comb += [
If(self.enable, If(sink.ctrl[i], # K codes shall not be scrambled.
If(sink.ctrl[i], # K codes shall not be scrambled. source.data[8*i:8*(i+1)].eq(sink.data[8*i:8*(i+1)])
source.data[8*i:8*(i+1)].eq(sink.data[8*i:8*(i+1)]) ).Else(
).Else( source.data[8*i:8*(i+1)].eq(sink.data[8*i:8*(i+1)] ^ scrambler.value[8*i:8*(i+1)])
source.data[8*i:8*(i+1)].eq(sink.data[8*i:8*(i+1)] ^ scrambler.value[8*i:8*(i+1)])
)
) )
] ]
# Descrambler (Scrambler + Auto-Synchronization) --------------------------------------------------- # Descrambler (Scrambler + Auto-Synchronization) ---------------------------------------------------
class Descrambler(Module): class Descrambler(Module):
def __init__(self): def __init__(self):
self.enable = Signal(reset=1)
self.sink = sink = stream.Endpoint([("data", 32), ("ctrl", 4)]) self.sink = sink = stream.Endpoint([("data", 32), ("ctrl", 4)])
self.source = source = stream.Endpoint([("data", 32), ("ctrl", 4)]) self.source = source = stream.Endpoint([("data", 32), ("ctrl", 4)])
@ -112,13 +107,12 @@ class Descrambler(Module):
scrambler = Scrambler() scrambler = Scrambler()
self.submodules += scrambler self.submodules += scrambler
sync = Signal() synchro = Signal()
synced = Signal() synchronized = Signal()
self.comb += sync.eq(sink.data == scrambler.source.data) self.comb += synchro.eq(sink.valid & sink.ready & (scrambler.source.data == 0x00000000))
self.sync += If(sync, synced.eq(1)) self.sync += If(synchro, synchronized.eq(1))
self.comb += [ self.comb += [
sink.ready.eq(1),
sink.connect(scrambler.sink), sink.connect(scrambler.sink),
scrambler.sink.valid.eq(sink.valid & (sync | synced)), scrambler.sink.valid.eq(sink.valid & (synchro | synchronized)),
scrambler.source.connect(source) scrambler.source.connect(source)
] ]