mirror of
https://github.com/enjoy-digital/litex.git
synced 2025-01-04 09:52:26 -05:00
global: pep8 (E302)
This commit is contained in:
parent
17e5249be0
commit
1051878f4c
113 changed files with 454 additions and 0 deletions
|
@ -1,6 +1,7 @@
|
||||||
from migen.fhdl.std import *
|
from migen.fhdl.std import *
|
||||||
from migen.fhdl import verilog
|
from migen.fhdl import verilog
|
||||||
|
|
||||||
|
|
||||||
class Example(Module):
|
class Example(Module):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
dx = 2
|
dx = 2
|
||||||
|
|
|
@ -2,6 +2,7 @@ from migen.fhdl.std import *
|
||||||
from migen.genlib.complex import *
|
from migen.genlib.complex import *
|
||||||
from migen.fhdl import verilog
|
from migen.fhdl import verilog
|
||||||
|
|
||||||
|
|
||||||
class Example(Module):
|
class Example(Module):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
w = Complex(32, 42)
|
w = Complex(32, 42)
|
||||||
|
|
|
@ -2,6 +2,7 @@ from migen.fhdl.std import *
|
||||||
from migen.fhdl import verilog
|
from migen.fhdl import verilog
|
||||||
from migen.genlib.fsm import FSM, NextState, NextValue
|
from migen.genlib.fsm import FSM, NextState, NextValue
|
||||||
|
|
||||||
|
|
||||||
class Example(Module):
|
class Example(Module):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.s = Signal()
|
self.s = Signal()
|
||||||
|
|
|
@ -4,6 +4,7 @@ from migen.fhdl.std import *
|
||||||
from migen.genlib.cdc import GrayCounter
|
from migen.genlib.cdc import GrayCounter
|
||||||
from migen.sim.generic import run_simulation
|
from migen.sim.generic import run_simulation
|
||||||
|
|
||||||
|
|
||||||
class TB(Module):
|
class TB(Module):
|
||||||
def __init__(self, width=3):
|
def __init__(self, width=3):
|
||||||
self.width = width
|
self.width = width
|
||||||
|
|
|
@ -2,11 +2,13 @@ from migen.fhdl.std import *
|
||||||
from migen.fhdl import verilog
|
from migen.fhdl import verilog
|
||||||
from migen.genlib.divider import Divider
|
from migen.genlib.divider import Divider
|
||||||
|
|
||||||
|
|
||||||
class CDM(Module):
|
class CDM(Module):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.submodules.divider = Divider(5)
|
self.submodules.divider = Divider(5)
|
||||||
self.clock_domains.cd_sys = ClockDomain(reset_less=True)
|
self.clock_domains.cd_sys = ClockDomain(reset_less=True)
|
||||||
|
|
||||||
|
|
||||||
class MultiMod(Module):
|
class MultiMod(Module):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.submodules.foo = CDM()
|
self.submodules.foo = CDM()
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from migen.fhdl.std import *
|
from migen.fhdl.std import *
|
||||||
from migen.fhdl import verilog
|
from migen.fhdl import verilog
|
||||||
|
|
||||||
|
|
||||||
class Example(Module):
|
class Example(Module):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.specials.mem = Memory(32, 100, init=[5, 18, 32])
|
self.specials.mem = Memory(32, 100, init=[5, 18, 32])
|
||||||
|
|
|
@ -2,24 +2,29 @@ from migen.fhdl.std import *
|
||||||
from migen.fhdl import verilog
|
from migen.fhdl import verilog
|
||||||
from migen.genlib.misc import optree
|
from migen.genlib.misc import optree
|
||||||
|
|
||||||
|
|
||||||
def gen_list(n):
|
def gen_list(n):
|
||||||
s = [Signal() for i in range(n)]
|
s = [Signal() for i in range(n)]
|
||||||
return s
|
return s
|
||||||
|
|
||||||
|
|
||||||
def gen_2list(n):
|
def gen_2list(n):
|
||||||
s = [Signal(2) for i in range(n)]
|
s = [Signal(2) for i in range(n)]
|
||||||
return s
|
return s
|
||||||
|
|
||||||
|
|
||||||
class Foo:
|
class Foo:
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
la = gen_list(3)
|
la = gen_list(3)
|
||||||
lb = gen_2list(2)
|
lb = gen_2list(2)
|
||||||
self.sigs = la + lb
|
self.sigs = la + lb
|
||||||
|
|
||||||
|
|
||||||
class Bar:
|
class Bar:
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.sigs = gen_list(2)
|
self.sigs = gen_list(2)
|
||||||
|
|
||||||
|
|
||||||
class Example(Module):
|
class Example(Module):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
a = [Bar() for x in range(3)]
|
a = [Bar() for x in range(3)]
|
||||||
|
|
|
@ -3,12 +3,14 @@ from migen.fhdl.specials import SynthesisDirective
|
||||||
from migen.fhdl import verilog
|
from migen.fhdl import verilog
|
||||||
from migen.genlib.cdc import *
|
from migen.genlib.cdc import *
|
||||||
|
|
||||||
|
|
||||||
class XilinxMultiRegImpl(MultiRegImpl):
|
class XilinxMultiRegImpl(MultiRegImpl):
|
||||||
def __init__(self, *args, **kwargs):
|
def __init__(self, *args, **kwargs):
|
||||||
MultiRegImpl.__init__(self, *args, **kwargs)
|
MultiRegImpl.__init__(self, *args, **kwargs)
|
||||||
self.specials += set(SynthesisDirective("attribute shreg_extract of {r} is no", r=r)
|
self.specials += set(SynthesisDirective("attribute shreg_extract of {r} is no", r=r)
|
||||||
for r in self.regs)
|
for r in self.regs)
|
||||||
|
|
||||||
|
|
||||||
class XilinxMultiReg:
|
class XilinxMultiReg:
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def lower(dr):
|
def lower(dr):
|
||||||
|
|
|
@ -12,6 +12,7 @@ L = [
|
||||||
("ack", 1, DIR_S_TO_M)
|
("ack", 1, DIR_S_TO_M)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Test(Module):
|
class Test(Module):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
master = Record(L)
|
master = Record(L)
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from migen.fhdl.std import *
|
from migen.fhdl.std import *
|
||||||
from migen.fhdl import verilog
|
from migen.fhdl import verilog
|
||||||
|
|
||||||
|
|
||||||
class Example(Module):
|
class Example(Module):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
a = Signal(3)
|
a = Signal(3)
|
||||||
|
|
|
@ -3,6 +3,7 @@ from migen.fhdl import verilog
|
||||||
from migen.genlib.cdc import MultiReg
|
from migen.genlib.cdc import MultiReg
|
||||||
from migen.bank import description, csrgen
|
from migen.bank import description, csrgen
|
||||||
|
|
||||||
|
|
||||||
class Example(Module):
|
class Example(Module):
|
||||||
def __init__(self, ninputs=32, noutputs=32):
|
def __init__(self, ninputs=32, noutputs=32):
|
||||||
r_o = description.CSRStorage(noutputs, atomic_write=True)
|
r_o = description.CSRStorage(noutputs, atomic_write=True)
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from migen.fhdl.std import *
|
from migen.fhdl.std import *
|
||||||
from migen.fhdl import verilog
|
from migen.fhdl import verilog
|
||||||
|
|
||||||
|
|
||||||
class Example(Module):
|
class Example(Module):
|
||||||
def __init__(self, n=6):
|
def __init__(self, n=6):
|
||||||
self.pad = Signal(n)
|
self.pad = Signal(n)
|
||||||
|
|
|
@ -2,6 +2,7 @@ from migen.fhdl.std import *
|
||||||
from migen.fhdl import verilog
|
from migen.fhdl import verilog
|
||||||
from migen.genlib import divider
|
from migen.genlib import divider
|
||||||
|
|
||||||
|
|
||||||
@ResetInserter()
|
@ResetInserter()
|
||||||
@CEInserter()
|
@CEInserter()
|
||||||
class Example(Module):
|
class Example(Module):
|
||||||
|
|
|
@ -8,10 +8,12 @@ from migen.actorlib.sim import *
|
||||||
from migen.bus import wishbone
|
from migen.bus import wishbone
|
||||||
from migen.sim.generic import run_simulation
|
from migen.sim.generic import run_simulation
|
||||||
|
|
||||||
|
|
||||||
class MyModel:
|
class MyModel:
|
||||||
def read(self, address):
|
def read(self, address):
|
||||||
return address + 4
|
return address + 4
|
||||||
|
|
||||||
|
|
||||||
class MyModelWB(MyModel, wishbone.TargetModel):
|
class MyModelWB(MyModel, wishbone.TargetModel):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.prng = Random(763627)
|
self.prng = Random(763627)
|
||||||
|
@ -19,27 +21,32 @@ class MyModelWB(MyModel, wishbone.TargetModel):
|
||||||
def can_ack(self, bus):
|
def can_ack(self, bus):
|
||||||
return self.prng.randrange(0, 2)
|
return self.prng.randrange(0, 2)
|
||||||
|
|
||||||
|
|
||||||
def adrgen_gen():
|
def adrgen_gen():
|
||||||
for i in range(10):
|
for i in range(10):
|
||||||
print("Address: " + hex(i))
|
print("Address: " + hex(i))
|
||||||
yield Token("address", {"a": i})
|
yield Token("address", {"a": i})
|
||||||
|
|
||||||
|
|
||||||
class SimAdrGen(SimActor):
|
class SimAdrGen(SimActor):
|
||||||
def __init__(self, nbits):
|
def __init__(self, nbits):
|
||||||
self.address = Source([("a", nbits)])
|
self.address = Source([("a", nbits)])
|
||||||
SimActor.__init__(self, adrgen_gen())
|
SimActor.__init__(self, adrgen_gen())
|
||||||
|
|
||||||
|
|
||||||
def dumper_gen():
|
def dumper_gen():
|
||||||
while True:
|
while True:
|
||||||
t = Token("data", idle_wait=True)
|
t = Token("data", idle_wait=True)
|
||||||
yield t
|
yield t
|
||||||
print("Received: " + hex(t.value["d"]))
|
print("Received: " + hex(t.value["d"]))
|
||||||
|
|
||||||
|
|
||||||
class SimDumper(SimActor):
|
class SimDumper(SimActor):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.data = Sink([("d", 32)])
|
self.data = Sink([("d", 32)])
|
||||||
SimActor.__init__(self, dumper_gen())
|
SimActor.__init__(self, dumper_gen())
|
||||||
|
|
||||||
|
|
||||||
def trgen_gen():
|
def trgen_gen():
|
||||||
for i in range(10):
|
for i in range(10):
|
||||||
a = i
|
a = i
|
||||||
|
@ -47,11 +54,13 @@ def trgen_gen():
|
||||||
print("Address: " + hex(a) + " Data: " + hex(d))
|
print("Address: " + hex(a) + " Data: " + hex(d))
|
||||||
yield Token("address_data", {"a": a, "d": d})
|
yield Token("address_data", {"a": a, "d": d})
|
||||||
|
|
||||||
|
|
||||||
class SimTrGen(SimActor):
|
class SimTrGen(SimActor):
|
||||||
def __init__(self, a_nbits):
|
def __init__(self, a_nbits):
|
||||||
self.address_data = Source([("a", a_nbits), ("d", 32)])
|
self.address_data = Source([("a", a_nbits), ("d", 32)])
|
||||||
SimActor.__init__(self, trgen_gen())
|
SimActor.__init__(self, trgen_gen())
|
||||||
|
|
||||||
|
|
||||||
class TBWishbone(Module):
|
class TBWishbone(Module):
|
||||||
def __init__(self, master):
|
def __init__(self, master):
|
||||||
self.submodules.peripheral = wishbone.Target(MyModelWB())
|
self.submodules.peripheral = wishbone.Target(MyModelWB())
|
||||||
|
@ -59,6 +68,7 @@ class TBWishbone(Module):
|
||||||
self.submodules.interconnect = wishbone.InterconnectPointToPoint(master.bus,
|
self.submodules.interconnect = wishbone.InterconnectPointToPoint(master.bus,
|
||||||
self.peripheral.bus)
|
self.peripheral.bus)
|
||||||
|
|
||||||
|
|
||||||
class TBWishboneReader(TBWishbone):
|
class TBWishboneReader(TBWishbone):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.adrgen = SimAdrGen(30)
|
self.adrgen = SimAdrGen(30)
|
||||||
|
@ -70,6 +80,7 @@ class TBWishboneReader(TBWishbone):
|
||||||
self.submodules.comp = CompositeActor(g)
|
self.submodules.comp = CompositeActor(g)
|
||||||
TBWishbone.__init__(self, self.reader)
|
TBWishbone.__init__(self, self.reader)
|
||||||
|
|
||||||
|
|
||||||
class TBWishboneWriter(TBWishbone):
|
class TBWishboneWriter(TBWishbone):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.trgen = SimTrGen(30)
|
self.trgen = SimTrGen(30)
|
||||||
|
@ -79,10 +90,12 @@ class TBWishboneWriter(TBWishbone):
|
||||||
self.submodules.comp = CompositeActor(g)
|
self.submodules.comp = CompositeActor(g)
|
||||||
TBWishbone.__init__(self, self.writer)
|
TBWishbone.__init__(self, self.writer)
|
||||||
|
|
||||||
|
|
||||||
def test_wb_reader():
|
def test_wb_reader():
|
||||||
print("*** Testing Wishbone reader")
|
print("*** Testing Wishbone reader")
|
||||||
run_simulation(TBWishboneReader(), 100)
|
run_simulation(TBWishboneReader(), 100)
|
||||||
|
|
||||||
|
|
||||||
def test_wb_writer():
|
def test_wb_writer():
|
||||||
print("*** Testing Wishbone writer")
|
print("*** Testing Wishbone writer")
|
||||||
run_simulation(TBWishboneWriter(), 100)
|
run_simulation(TBWishboneWriter(), 100)
|
||||||
|
|
|
@ -4,23 +4,27 @@ from migen.actorlib import misc
|
||||||
from migen.actorlib.sim import *
|
from migen.actorlib.sim import *
|
||||||
from migen.sim.generic import run_simulation
|
from migen.sim.generic import run_simulation
|
||||||
|
|
||||||
|
|
||||||
def source_gen():
|
def source_gen():
|
||||||
for i in range(10):
|
for i in range(10):
|
||||||
v = i + 5
|
v = i + 5
|
||||||
print("==> " + str(v))
|
print("==> " + str(v))
|
||||||
yield Token("source", {"maximum": v})
|
yield Token("source", {"maximum": v})
|
||||||
|
|
||||||
|
|
||||||
class SimSource(SimActor):
|
class SimSource(SimActor):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.source = Source([("maximum", 32)])
|
self.source = Source([("maximum", 32)])
|
||||||
SimActor.__init__(self, source_gen())
|
SimActor.__init__(self, source_gen())
|
||||||
|
|
||||||
|
|
||||||
def sink_gen():
|
def sink_gen():
|
||||||
while True:
|
while True:
|
||||||
t = Token("sink")
|
t = Token("sink")
|
||||||
yield t
|
yield t
|
||||||
print(t.value["value"])
|
print(t.value["value"])
|
||||||
|
|
||||||
|
|
||||||
class SimSink(SimActor):
|
class SimSink(SimActor):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.sink = Sink([("value", 32)])
|
self.sink = Sink([("value", 32)])
|
||||||
|
|
|
@ -15,26 +15,31 @@ base_layout = [("value", 32)]
|
||||||
packed_layout = structuring.pack_layout(base_layout, pack_factor)
|
packed_layout = structuring.pack_layout(base_layout, pack_factor)
|
||||||
rawbits_layout = [("value", 32*pack_factor)]
|
rawbits_layout = [("value", 32*pack_factor)]
|
||||||
|
|
||||||
|
|
||||||
def source_gen():
|
def source_gen():
|
||||||
for i in count(0):
|
for i in count(0):
|
||||||
yield Token("source", {"value": i})
|
yield Token("source", {"value": i})
|
||||||
|
|
||||||
|
|
||||||
class SimSource(SimActor):
|
class SimSource(SimActor):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.source = Source(base_layout)
|
self.source = Source(base_layout)
|
||||||
SimActor.__init__(self, source_gen())
|
SimActor.__init__(self, source_gen())
|
||||||
|
|
||||||
|
|
||||||
def sink_gen():
|
def sink_gen():
|
||||||
while True:
|
while True:
|
||||||
t = Token("sink")
|
t = Token("sink")
|
||||||
yield t
|
yield t
|
||||||
print(t.value["value"])
|
print(t.value["value"])
|
||||||
|
|
||||||
|
|
||||||
class SimSink(SimActor):
|
class SimSink(SimActor):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.sink = Sink(base_layout)
|
self.sink = Sink(base_layout)
|
||||||
SimActor.__init__(self, sink_gen())
|
SimActor.__init__(self, sink_gen())
|
||||||
|
|
||||||
|
|
||||||
class TB(Module):
|
class TB(Module):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
source = SimSource()
|
source = SimSource()
|
||||||
|
|
|
@ -5,6 +5,7 @@ from migen.bus.transactions import *
|
||||||
from migen.bus import wishbone
|
from migen.bus import wishbone
|
||||||
from migen.sim.generic import run_simulation
|
from migen.sim.generic import run_simulation
|
||||||
|
|
||||||
|
|
||||||
# Our bus master.
|
# Our bus master.
|
||||||
# Python generators let us program bus transactions in an elegant sequential style.
|
# Python generators let us program bus transactions in an elegant sequential style.
|
||||||
def my_generator():
|
def my_generator():
|
||||||
|
@ -27,6 +28,7 @@ def my_generator():
|
||||||
for delay in range(prng.randrange(0, 3)):
|
for delay in range(prng.randrange(0, 3)):
|
||||||
yield None
|
yield None
|
||||||
|
|
||||||
|
|
||||||
# Our bus slave.
|
# Our bus slave.
|
||||||
class MyModelWB(wishbone.TargetModel):
|
class MyModelWB(wishbone.TargetModel):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
|
@ -39,6 +41,7 @@ class MyModelWB(wishbone.TargetModel):
|
||||||
# Simulate variable latency.
|
# Simulate variable latency.
|
||||||
return self.prng.randrange(0, 2)
|
return self.prng.randrange(0, 2)
|
||||||
|
|
||||||
|
|
||||||
class TB(Module):
|
class TB(Module):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
# The "wishbone.Initiator" library component runs our generator
|
# The "wishbone.Initiator" library component runs our generator
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from migen.fhdl.std import *
|
from migen.fhdl.std import *
|
||||||
from migen.sim.generic import run_simulation
|
from migen.sim.generic import run_simulation
|
||||||
|
|
||||||
|
|
||||||
# Our simple counter, which increments at every cycle
|
# Our simple counter, which increments at every cycle
|
||||||
# and prints its current value in simulation.
|
# and prints its current value in simulation.
|
||||||
class Counter(Module):
|
class Counter(Module):
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from migen.fhdl.std import *
|
from migen.fhdl.std import *
|
||||||
from migen.sim.generic import run_simulation
|
from migen.sim.generic import run_simulation
|
||||||
|
|
||||||
|
|
||||||
# A slightly more elaborate counter.
|
# A slightly more elaborate counter.
|
||||||
# Has a clock enable (CE) signal, counts on more bits
|
# Has a clock enable (CE) signal, counts on more bits
|
||||||
# and resets with a negative number.
|
# and resets with a negative number.
|
||||||
|
|
|
@ -5,27 +5,32 @@ from migen.flow.network import *
|
||||||
from migen.actorlib.sim import *
|
from migen.actorlib.sim import *
|
||||||
from migen.sim.generic import run_simulation
|
from migen.sim.generic import run_simulation
|
||||||
|
|
||||||
|
|
||||||
def source_gen():
|
def source_gen():
|
||||||
for i in range(10):
|
for i in range(10):
|
||||||
print("Sending: " + str(i))
|
print("Sending: " + str(i))
|
||||||
yield Token("source", {"value": i})
|
yield Token("source", {"value": i})
|
||||||
|
|
||||||
|
|
||||||
class SimSource(SimActor):
|
class SimSource(SimActor):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.source = Source([("value", 32)])
|
self.source = Source([("value", 32)])
|
||||||
SimActor.__init__(self, source_gen())
|
SimActor.__init__(self, source_gen())
|
||||||
|
|
||||||
|
|
||||||
def sink_gen():
|
def sink_gen():
|
||||||
while True:
|
while True:
|
||||||
t = Token("sink")
|
t = Token("sink")
|
||||||
yield t
|
yield t
|
||||||
print("Received: " + str(t.value["value"]))
|
print("Received: " + str(t.value["value"]))
|
||||||
|
|
||||||
|
|
||||||
class SimSink(SimActor):
|
class SimSink(SimActor):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.sink = Sink([("value", 32)])
|
self.sink = Sink([("value", 32)])
|
||||||
SimActor.__init__(self, sink_gen())
|
SimActor.__init__(self, sink_gen())
|
||||||
|
|
||||||
|
|
||||||
class TB(Module):
|
class TB(Module):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.source = SimSource()
|
self.source = SimSource()
|
||||||
|
|
|
@ -7,6 +7,7 @@ from migen.fhdl import verilog
|
||||||
from migen.genlib.misc import optree
|
from migen.genlib.misc import optree
|
||||||
from migen.sim.generic import run_simulation
|
from migen.sim.generic import run_simulation
|
||||||
|
|
||||||
|
|
||||||
# A synthesizable FIR filter.
|
# A synthesizable FIR filter.
|
||||||
class FIR(Module):
|
class FIR(Module):
|
||||||
def __init__(self, coef, wsize=16):
|
def __init__(self, coef, wsize=16):
|
||||||
|
@ -29,6 +30,7 @@ class FIR(Module):
|
||||||
self.sync += sum_full.eq(optree("+", muls))
|
self.sync += sum_full.eq(optree("+", muls))
|
||||||
self.comb += self.o.eq(sum_full[self.wsize-1:])
|
self.comb += self.o.eq(sum_full[self.wsize-1:])
|
||||||
|
|
||||||
|
|
||||||
# A test bench for our FIR filter.
|
# A test bench for our FIR filter.
|
||||||
# Generates a sine wave at the input and records the output.
|
# Generates a sine wave at the input and records the output.
|
||||||
class TB(Module):
|
class TB(Module):
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from migen.fhdl.std import *
|
from migen.fhdl.std import *
|
||||||
from migen.sim.generic import run_simulation
|
from migen.sim.generic import run_simulation
|
||||||
|
|
||||||
|
|
||||||
class Mem(Module):
|
class Mem(Module):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
# Initialize the beginning of the memory with integers
|
# Initialize the beginning of the memory with integers
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from mibuild.generic_platform import GenericPlatform
|
from mibuild.generic_platform import GenericPlatform
|
||||||
from mibuild.altera import common, quartus
|
from mibuild.altera import common, quartus
|
||||||
|
|
||||||
|
|
||||||
class AlteraPlatform(GenericPlatform):
|
class AlteraPlatform(GenericPlatform):
|
||||||
bitstream_ext = ".sof"
|
bitstream_ext = ".sof"
|
||||||
|
|
||||||
|
|
|
@ -2,6 +2,7 @@ import subprocess
|
||||||
|
|
||||||
from mibuild.generic_programmer import GenericProgrammer
|
from mibuild.generic_programmer import GenericProgrammer
|
||||||
|
|
||||||
|
|
||||||
class USBBlaster(GenericProgrammer):
|
class USBBlaster(GenericProgrammer):
|
||||||
needs_bitreverse = False
|
needs_bitreverse = False
|
||||||
|
|
||||||
|
|
|
@ -9,6 +9,7 @@ from mibuild.generic_platform import *
|
||||||
from mibuild import tools
|
from mibuild import tools
|
||||||
from mibuild.xilinx import common
|
from mibuild.xilinx import common
|
||||||
|
|
||||||
|
|
||||||
def _format_constraint(c):
|
def _format_constraint(c):
|
||||||
if isinstance(c, Pins):
|
if isinstance(c, Pins):
|
||||||
return "set_location_assignment PIN_" + c.identifiers[0]
|
return "set_location_assignment PIN_" + c.identifiers[0]
|
||||||
|
@ -17,6 +18,7 @@ def _format_constraint(c):
|
||||||
elif isinstance(c, Misc):
|
elif isinstance(c, Misc):
|
||||||
return c.misc
|
return c.misc
|
||||||
|
|
||||||
|
|
||||||
def _format_qsf(signame, pin, others, resname):
|
def _format_qsf(signame, pin, others, resname):
|
||||||
fmt_c = [_format_constraint(c) for c in ([Pins(pin)] + others)]
|
fmt_c = [_format_constraint(c) for c in ([Pins(pin)] + others)]
|
||||||
fmt_r = resname[0] + ":" + str(resname[1])
|
fmt_r = resname[0] + ":" + str(resname[1])
|
||||||
|
@ -27,6 +29,7 @@ def _format_qsf(signame, pin, others, resname):
|
||||||
r += c + " -to " + signame + " # " + fmt_r + "\n"
|
r += c + " -to " + signame + " # " + fmt_r + "\n"
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _build_qsf(named_sc, named_pc):
|
def _build_qsf(named_sc, named_pc):
|
||||||
r = ""
|
r = ""
|
||||||
for sig, pins, others, resname in named_sc:
|
for sig, pins, others, resname in named_sc:
|
||||||
|
@ -40,6 +43,7 @@ def _build_qsf(named_sc, named_pc):
|
||||||
r += "set_global_assignment -name top_level_entity top\n"
|
r += "set_global_assignment -name top_level_entity top\n"
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _build_files(device, sources, vincpaths, named_sc, named_pc, build_name):
|
def _build_files(device, sources, vincpaths, named_sc, named_pc, build_name):
|
||||||
qsf_contents = ""
|
qsf_contents = ""
|
||||||
for filename, language in sources:
|
for filename, language in sources:
|
||||||
|
@ -55,6 +59,7 @@ def _build_files(device, sources, vincpaths, named_sc, named_pc, build_name):
|
||||||
qsf_contents += "set_global_assignment -name DEVICE " + device
|
qsf_contents += "set_global_assignment -name DEVICE " + device
|
||||||
tools.write_to_file(build_name + ".qsf", qsf_contents)
|
tools.write_to_file(build_name + ".qsf", qsf_contents)
|
||||||
|
|
||||||
|
|
||||||
def _run_quartus(build_name, quartus_path):
|
def _run_quartus(build_name, quartus_path):
|
||||||
build_script_contents = """# Autogenerated by mibuild
|
build_script_contents = """# Autogenerated by mibuild
|
||||||
|
|
||||||
|
@ -71,6 +76,7 @@ quartus_sta {build_name} -c {build_name}
|
||||||
if r != 0:
|
if r != 0:
|
||||||
raise OSError("Subprocess failed")
|
raise OSError("Subprocess failed")
|
||||||
|
|
||||||
|
|
||||||
class AlteraQuartusToolchain:
|
class AlteraQuartusToolchain:
|
||||||
def build(self, platform, fragment, build_dir="build", build_name="top",
|
def build(self, platform, fragment, build_dir="build", build_name="top",
|
||||||
quartus_path="/opt/Altera", run=True):
|
quartus_path="/opt/Altera", run=True):
|
||||||
|
|
|
@ -9,42 +9,51 @@ from migen.util.misc import autotype
|
||||||
|
|
||||||
from mibuild import tools
|
from mibuild import tools
|
||||||
|
|
||||||
|
|
||||||
class ConstraintError(Exception):
|
class ConstraintError(Exception):
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class Pins:
|
class Pins:
|
||||||
def __init__(self, *identifiers):
|
def __init__(self, *identifiers):
|
||||||
self.identifiers = []
|
self.identifiers = []
|
||||||
for i in identifiers:
|
for i in identifiers:
|
||||||
self.identifiers += i.split()
|
self.identifiers += i.split()
|
||||||
|
|
||||||
|
|
||||||
class IOStandard:
|
class IOStandard:
|
||||||
def __init__(self, name):
|
def __init__(self, name):
|
||||||
self.name = name
|
self.name = name
|
||||||
|
|
||||||
|
|
||||||
class Drive:
|
class Drive:
|
||||||
def __init__(self, strength):
|
def __init__(self, strength):
|
||||||
self.strength = strength
|
self.strength = strength
|
||||||
|
|
||||||
|
|
||||||
class Misc:
|
class Misc:
|
||||||
def __init__(self, misc):
|
def __init__(self, misc):
|
||||||
self.misc = misc
|
self.misc = misc
|
||||||
|
|
||||||
|
|
||||||
class Subsignal:
|
class Subsignal:
|
||||||
def __init__(self, name, *constraints):
|
def __init__(self, name, *constraints):
|
||||||
self.name = name
|
self.name = name
|
||||||
self.constraints = list(constraints)
|
self.constraints = list(constraints)
|
||||||
|
|
||||||
|
|
||||||
class PlatformInfo:
|
class PlatformInfo:
|
||||||
def __init__(self, info):
|
def __init__(self, info):
|
||||||
self.info = info
|
self.info = info
|
||||||
|
|
||||||
|
|
||||||
def _lookup(description, name, number):
|
def _lookup(description, name, number):
|
||||||
for resource in description:
|
for resource in description:
|
||||||
if resource[0] == name and (number is None or resource[1] == number):
|
if resource[0] == name and (number is None or resource[1] == number):
|
||||||
return resource
|
return resource
|
||||||
raise ConstraintError("Resource not found: " + name + ":" + str(number))
|
raise ConstraintError("Resource not found: " + name + ":" + str(number))
|
||||||
|
|
||||||
|
|
||||||
def _resource_type(resource):
|
def _resource_type(resource):
|
||||||
t = None
|
t = None
|
||||||
for element in resource[2:]:
|
for element in resource[2:]:
|
||||||
|
@ -63,6 +72,7 @@ def _resource_type(resource):
|
||||||
t.append((element.name, n_bits))
|
t.append((element.name, n_bits))
|
||||||
return t
|
return t
|
||||||
|
|
||||||
|
|
||||||
class ConnectorManager:
|
class ConnectorManager:
|
||||||
def __init__(self, connectors):
|
def __init__(self, connectors):
|
||||||
self.connector_table = dict()
|
self.connector_table = dict()
|
||||||
|
@ -95,6 +105,7 @@ class ConnectorManager:
|
||||||
r.append(identifier)
|
r.append(identifier)
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _separate_pins(constraints):
|
def _separate_pins(constraints):
|
||||||
pins = None
|
pins = None
|
||||||
others = []
|
others = []
|
||||||
|
@ -106,6 +117,7 @@ def _separate_pins(constraints):
|
||||||
others.append(c)
|
others.append(c)
|
||||||
return pins, others
|
return pins, others
|
||||||
|
|
||||||
|
|
||||||
class ConstraintManager:
|
class ConstraintManager:
|
||||||
def __init__(self, io, connectors):
|
def __init__(self, io, connectors):
|
||||||
self.available = list(io)
|
self.available = list(io)
|
||||||
|
@ -177,6 +189,7 @@ class ConstraintManager:
|
||||||
def get_platform_commands(self):
|
def get_platform_commands(self):
|
||||||
return self.platform_commands
|
return self.platform_commands
|
||||||
|
|
||||||
|
|
||||||
class GenericPlatform:
|
class GenericPlatform:
|
||||||
def __init__(self, device, io, connectors=[], name=None):
|
def __init__(self, device, io, connectors=[], name=None):
|
||||||
self.device = device
|
self.device = device
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
import os
|
import os
|
||||||
|
|
||||||
|
|
||||||
class GenericProgrammer:
|
class GenericProgrammer:
|
||||||
def __init__(self, flash_proxy_basename=None):
|
def __init__(self, flash_proxy_basename=None):
|
||||||
self.flash_proxy_basename = flash_proxy_basename
|
self.flash_proxy_basename = flash_proxy_basename
|
||||||
|
|
|
@ -3,6 +3,7 @@ from migen.genlib.io import *
|
||||||
|
|
||||||
from migen.genlib.resetsync import AsyncResetSynchronizer
|
from migen.genlib.resetsync import AsyncResetSynchronizer
|
||||||
|
|
||||||
|
|
||||||
class LatticeAsyncResetSynchronizerImpl(Module):
|
class LatticeAsyncResetSynchronizerImpl(Module):
|
||||||
def __init__(self, cd, async_reset):
|
def __init__(self, cd, async_reset):
|
||||||
rst1 = Signal()
|
rst1 = Signal()
|
||||||
|
@ -13,11 +14,13 @@ class LatticeAsyncResetSynchronizerImpl(Module):
|
||||||
i_CK=cd.clk, o_Q=cd.rst)
|
i_CK=cd.clk, o_Q=cd.rst)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class LatticeAsyncResetSynchronizer:
|
class LatticeAsyncResetSynchronizer:
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def lower(dr):
|
def lower(dr):
|
||||||
return LatticeAsyncResetSynchronizerImpl(dr.cd, dr.async_reset)
|
return LatticeAsyncResetSynchronizerImpl(dr.cd, dr.async_reset)
|
||||||
|
|
||||||
|
|
||||||
class LatticeDDROutputImpl(Module):
|
class LatticeDDROutputImpl(Module):
|
||||||
def __init__(self, i1, i2, o, clk):
|
def __init__(self, i1, i2, o, clk):
|
||||||
self.specials += Instance("ODDRXD1",
|
self.specials += Instance("ODDRXD1",
|
||||||
|
@ -26,6 +29,7 @@ class LatticeDDROutputImpl(Module):
|
||||||
i_DA=i1, i_DB=i2, o_Q=o,
|
i_DA=i1, i_DB=i2, o_Q=o,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
class LatticeDDROutput:
|
class LatticeDDROutput:
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def lower(dr):
|
def lower(dr):
|
||||||
|
|
|
@ -9,6 +9,7 @@ from mibuild.generic_platform import *
|
||||||
from mibuild import tools
|
from mibuild import tools
|
||||||
from mibuild.lattice import common
|
from mibuild.lattice import common
|
||||||
|
|
||||||
|
|
||||||
def _format_constraint(c):
|
def _format_constraint(c):
|
||||||
if isinstance(c, Pins):
|
if isinstance(c, Pins):
|
||||||
return ("LOCATE COMP ", " SITE " + "\"" + c.identifiers[0] + "\"")
|
return ("LOCATE COMP ", " SITE " + "\"" + c.identifiers[0] + "\"")
|
||||||
|
@ -17,6 +18,7 @@ def _format_constraint(c):
|
||||||
elif isinstance(c, Misc):
|
elif isinstance(c, Misc):
|
||||||
return c.misc
|
return c.misc
|
||||||
|
|
||||||
|
|
||||||
def _format_lpf(signame, pin, others, resname):
|
def _format_lpf(signame, pin, others, resname):
|
||||||
fmt_c = [_format_constraint(c) for c in ([Pins(pin)] + others)]
|
fmt_c = [_format_constraint(c) for c in ([Pins(pin)] + others)]
|
||||||
r = ""
|
r = ""
|
||||||
|
@ -24,6 +26,7 @@ def _format_lpf(signame, pin, others, resname):
|
||||||
r += pre + "\""+ signame +"\"" + suf + ";\n"
|
r += pre + "\""+ signame +"\"" + suf + ";\n"
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _build_lpf(named_sc, named_pc):
|
def _build_lpf(named_sc, named_pc):
|
||||||
r = "BLOCK RESETPATHS;\n"
|
r = "BLOCK RESETPATHS;\n"
|
||||||
r += "BLOCK ASYNCPATHS;\n"
|
r += "BLOCK ASYNCPATHS;\n"
|
||||||
|
@ -37,6 +40,7 @@ def _build_lpf(named_sc, named_pc):
|
||||||
r += "\n" + "\n\n".join(named_pc)
|
r += "\n" + "\n\n".join(named_pc)
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _build_files(device, sources, vincpaths, build_name):
|
def _build_files(device, sources, vincpaths, build_name):
|
||||||
tcl = []
|
tcl = []
|
||||||
tcl.append("prj_project new -name \"%s\" -impl \"implementation\" -dev %s -synthesis \"synplify\"" %(build_name, device))
|
tcl.append("prj_project new -name \"%s\" -impl \"implementation\" -dev %s -synthesis \"synplify\"" %(build_name, device))
|
||||||
|
@ -51,6 +55,7 @@ def _build_files(device, sources, vincpaths, build_name):
|
||||||
tcl.append("prj_run Export -impl implementation -task Bitgen")
|
tcl.append("prj_run Export -impl implementation -task Bitgen")
|
||||||
tools.write_to_file(build_name + ".tcl", "\n".join(tcl))
|
tools.write_to_file(build_name + ".tcl", "\n".join(tcl))
|
||||||
|
|
||||||
|
|
||||||
def _run_diamond(build_name, source, ver=None):
|
def _run_diamond(build_name, source, ver=None):
|
||||||
if sys.platform == "win32" or sys.platform == "cygwin":
|
if sys.platform == "win32" or sys.platform == "cygwin":
|
||||||
build_script_contents = "REM Autogenerated by mibuild\n"
|
build_script_contents = "REM Autogenerated by mibuild\n"
|
||||||
|
@ -65,6 +70,7 @@ def _run_diamond(build_name, source, ver=None):
|
||||||
if r != 0:
|
if r != 0:
|
||||||
raise OSError("Subprocess failed")
|
raise OSError("Subprocess failed")
|
||||||
|
|
||||||
|
|
||||||
class LatticeDiamondToolchain:
|
class LatticeDiamondToolchain:
|
||||||
def build(self, platform, fragment, build_dir="build", build_name="top",
|
def build(self, platform, fragment, build_dir="build", build_name="top",
|
||||||
diamond_path="/opt/Diamond", run=True):
|
diamond_path="/opt/Diamond", run=True):
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from mibuild.generic_platform import GenericPlatform
|
from mibuild.generic_platform import GenericPlatform
|
||||||
from mibuild.lattice import common, diamond
|
from mibuild.lattice import common, diamond
|
||||||
|
|
||||||
|
|
||||||
class LatticePlatform(GenericPlatform):
|
class LatticePlatform(GenericPlatform):
|
||||||
bitstream_ext = ".bit"
|
bitstream_ext = ".bit"
|
||||||
|
|
||||||
|
|
|
@ -41,6 +41,7 @@ _xcf_template = """
|
||||||
</ispXCF>
|
</ispXCF>
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
|
||||||
class LatticeProgrammer(GenericProgrammer):
|
class LatticeProgrammer(GenericProgrammer):
|
||||||
needs_bitreverse = False
|
needs_bitreverse = False
|
||||||
|
|
||||||
|
|
|
@ -140,6 +140,7 @@ _connectors = [
|
||||||
"None") # 116 USBH2_CLK USB_HOST2 +2V5 PA0
|
"None") # 116 USBH2_CLK USB_HOST2 +2V5 PA0
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Platform(XilinxPlatform):
|
class Platform(XilinxPlatform):
|
||||||
default_clk_name = "clk0"
|
default_clk_name = "clk0"
|
||||||
default_clk_period = 10
|
default_clk_period = 10
|
||||||
|
|
|
@ -167,6 +167,7 @@ _connectors = [
|
||||||
"None") # 140 FPGA_BANK3_POWER
|
"None") # 140 FPGA_BANK3_POWER
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Platform(XilinxPlatform):
|
class Platform(XilinxPlatform):
|
||||||
default_clk_name = "clk3"
|
default_clk_name = "clk3"
|
||||||
default_clk_period = 10.526
|
default_clk_period = 10.526
|
||||||
|
|
|
@ -90,6 +90,7 @@ _io = [
|
||||||
),
|
),
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Platform(AlteraPlatform):
|
class Platform(AlteraPlatform):
|
||||||
default_clk_name = "clk50"
|
default_clk_name = "clk50"
|
||||||
default_clk_period = 20
|
default_clk_period = 20
|
||||||
|
|
|
@ -375,6 +375,7 @@ _connectors = [
|
||||||
)
|
)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Platform(XilinxPlatform):
|
class Platform(XilinxPlatform):
|
||||||
identifier = 0x4B37
|
identifier = 0x4B37
|
||||||
default_clk_name = "clk156"
|
default_clk_name = "clk156"
|
||||||
|
|
|
@ -117,6 +117,7 @@ _io = [
|
||||||
)
|
)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Platform(XilinxPlatform):
|
class Platform(XilinxPlatform):
|
||||||
identifier = 0x4D31
|
identifier = 0x4D31
|
||||||
default_clk_name = "clk50"
|
default_clk_name = "clk50"
|
||||||
|
|
|
@ -107,6 +107,7 @@ _connectors = [
|
||||||
("F", "E2 E1 E4 F4 F5 G3 F3 G1 H3 H1 H2 J1")
|
("F", "E2 E1 E4 F4 F5 G3 F3 G1 H3 H1 H2 J1")
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Platform(XilinxPlatform):
|
class Platform(XilinxPlatform):
|
||||||
default_clk_name = "clk32"
|
default_clk_name = "clk32"
|
||||||
default_clk_period = 31.25
|
default_clk_period = 31.25
|
||||||
|
|
|
@ -153,6 +153,7 @@ _io = [
|
||||||
),
|
),
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Platform(XilinxPlatform):
|
class Platform(XilinxPlatform):
|
||||||
identifier = 0x4D58
|
identifier = 0x4D58
|
||||||
default_clk_name = "clk50"
|
default_clk_name = "clk50"
|
||||||
|
|
|
@ -50,6 +50,7 @@ _io = [
|
||||||
)
|
)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Platform(XilinxPlatform):
|
class Platform(XilinxPlatform):
|
||||||
default_clk_name = "clk200"
|
default_clk_name = "clk200"
|
||||||
default_clk_period = 5
|
default_clk_period = 5
|
||||||
|
|
|
@ -48,6 +48,7 @@ _connectors = [
|
||||||
("C", "P114 P115 P116 P117 P118 P119 P120 P121 P123 P124 P126 P127 P131 P132 P133 P134")
|
("C", "P114 P115 P116 P117 P118 P119 P120 P121 P123 P124 P126 P127 P131 P132 P133 P134")
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Platform(XilinxPlatform):
|
class Platform(XilinxPlatform):
|
||||||
identifier = 0x5050
|
identifier = 0x5050
|
||||||
default_clk_name = "clk32"
|
default_clk_name = "clk32"
|
||||||
|
|
|
@ -123,6 +123,7 @@ _connectors = [
|
||||||
("C", "F17 F16 E16 G16 F15 G14 F14 H14 H13 J13 G13 H12 K14 K13 K12 L12"),
|
("C", "F17 F16 E16 G16 F15 G14 F14 H14 H13 J13 G13 H12 K14 K13 K12 L12"),
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Platform(XilinxPlatform):
|
class Platform(XilinxPlatform):
|
||||||
identifier = 0x5049
|
identifier = 0x5049
|
||||||
default_clk_name = "clk50"
|
default_clk_name = "clk50"
|
||||||
|
|
|
@ -132,6 +132,7 @@ _io = [
|
||||||
)
|
)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Platform(XilinxPlatform):
|
class Platform(XilinxPlatform):
|
||||||
default_clk_name = "clk100"
|
default_clk_name = "clk100"
|
||||||
default_clk_period = 10
|
default_clk_period = 10
|
||||||
|
|
|
@ -28,6 +28,7 @@ _io = [
|
||||||
),
|
),
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Platform(XilinxPlatform):
|
class Platform(XilinxPlatform):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
XilinxPlatform.__init__(self, "xc5vsx95t-ff1136-1", _io)
|
XilinxPlatform.__init__(self, "xc5vsx95t-ff1136-1", _io)
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from mibuild.generic_platform import *
|
from mibuild.generic_platform import *
|
||||||
from mibuild.sim import SimPlatform
|
from mibuild.sim import SimPlatform
|
||||||
|
|
||||||
|
|
||||||
class SimPins(Pins):
|
class SimPins(Pins):
|
||||||
def __init__(self, n):
|
def __init__(self, n):
|
||||||
Pins.__init__(self, "s "*n)
|
Pins.__init__(self, "s "*n)
|
||||||
|
@ -31,6 +32,7 @@ _io = [
|
||||||
),
|
),
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Platform(SimPlatform):
|
class Platform(SimPlatform):
|
||||||
is_sim = True
|
is_sim = True
|
||||||
default_clk_name = "sys_clk"
|
default_clk_name = "sys_clk"
|
||||||
|
|
|
@ -73,6 +73,7 @@ _io = [
|
||||||
),
|
),
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Platform(LatticePlatform):
|
class Platform(LatticePlatform):
|
||||||
default_clk_name = "clk100"
|
default_clk_name = "clk100"
|
||||||
default_clk_period = 10
|
default_clk_period = 10
|
||||||
|
|
|
@ -80,6 +80,7 @@ _io = [
|
||||||
|
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Platform(XilinxPlatform):
|
class Platform(XilinxPlatform):
|
||||||
default_clk_name = "clk_if"
|
default_clk_name = "clk_if"
|
||||||
default_clk_period = 20
|
default_clk_period = 20
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from mibuild.generic_platform import GenericPlatform
|
from mibuild.generic_platform import GenericPlatform
|
||||||
from mibuild.sim import common, verilator
|
from mibuild.sim import common, verilator
|
||||||
|
|
||||||
|
|
||||||
class SimPlatform(GenericPlatform):
|
class SimPlatform(GenericPlatform):
|
||||||
def __init__(self, *args, toolchain="verilator", **kwargs):
|
def __init__(self, *args, toolchain="verilator", **kwargs):
|
||||||
GenericPlatform.__init__(self, *args, **kwargs)
|
GenericPlatform.__init__(self, *args, **kwargs)
|
||||||
|
|
|
@ -10,6 +10,7 @@ from mibuild.generic_platform import *
|
||||||
from mibuild import tools
|
from mibuild import tools
|
||||||
from mibuild.sim import common
|
from mibuild.sim import common
|
||||||
|
|
||||||
|
|
||||||
def _build_tb(platform, vns, serial, template):
|
def _build_tb(platform, vns, serial, template):
|
||||||
|
|
||||||
def io_name(ressource, subsignal=None):
|
def io_name(ressource, subsignal=None):
|
||||||
|
@ -82,6 +83,7 @@ def _build_tb(platform, vns, serial, template):
|
||||||
f.close()
|
f.close()
|
||||||
tools.write_to_file("dut_tb.cpp", content)
|
tools.write_to_file("dut_tb.cpp", content)
|
||||||
|
|
||||||
|
|
||||||
def _build_sim(platform, vns, build_name, include_paths, sim_path, serial, verbose):
|
def _build_sim(platform, vns, build_name, include_paths, sim_path, serial, verbose):
|
||||||
include = ""
|
include = ""
|
||||||
for path in include_paths:
|
for path in include_paths:
|
||||||
|
@ -106,6 +108,7 @@ make -j -C obj_dir/ -f Vdut.mk Vdut
|
||||||
if r != 0:
|
if r != 0:
|
||||||
raise OSError("Subprocess failed")
|
raise OSError("Subprocess failed")
|
||||||
|
|
||||||
|
|
||||||
def _run_sim(build_name):
|
def _run_sim(build_name):
|
||||||
run_script_contents = """obj_dir/Vdut
|
run_script_contents = """obj_dir/Vdut
|
||||||
"""
|
"""
|
||||||
|
@ -115,6 +118,7 @@ def _run_sim(build_name):
|
||||||
if r != 0:
|
if r != 0:
|
||||||
raise OSError("Subprocess failed")
|
raise OSError("Subprocess failed")
|
||||||
|
|
||||||
|
|
||||||
class SimVerilatorToolchain:
|
class SimVerilatorToolchain:
|
||||||
# XXX fir sim_path
|
# XXX fir sim_path
|
||||||
def build(self, platform, fragment, build_dir="build", build_name="top",
|
def build(self, platform, fragment, build_dir="build", build_name="top",
|
||||||
|
|
|
@ -1,12 +1,14 @@
|
||||||
import os, struct
|
import os, struct
|
||||||
from distutils.version import StrictVersion
|
from distutils.version import StrictVersion
|
||||||
|
|
||||||
|
|
||||||
def mkdir_noerror(d):
|
def mkdir_noerror(d):
|
||||||
try:
|
try:
|
||||||
os.mkdir(d)
|
os.mkdir(d)
|
||||||
except OSError:
|
except OSError:
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
def language_by_filename(name):
|
def language_by_filename(name):
|
||||||
extension = name.rsplit(".")[-1]
|
extension = name.rsplit(".")[-1]
|
||||||
if extension in ["v", "vh", "vo"]:
|
if extension in ["v", "vh", "vo"]:
|
||||||
|
@ -15,6 +17,7 @@ def language_by_filename(name):
|
||||||
return "vhdl"
|
return "vhdl"
|
||||||
return None
|
return None
|
||||||
|
|
||||||
|
|
||||||
def write_to_file(filename, contents, force_unix=False):
|
def write_to_file(filename, contents, force_unix=False):
|
||||||
newline = None
|
newline = None
|
||||||
if force_unix:
|
if force_unix:
|
||||||
|
@ -22,9 +25,11 @@ def write_to_file(filename, contents, force_unix=False):
|
||||||
with open(filename, "w", newline=newline) as f:
|
with open(filename, "w", newline=newline) as f:
|
||||||
f.write(contents)
|
f.write(contents)
|
||||||
|
|
||||||
|
|
||||||
def arch_bits():
|
def arch_bits():
|
||||||
return struct.calcsize("P")*8
|
return struct.calcsize("P")*8
|
||||||
|
|
||||||
|
|
||||||
def versions(path):
|
def versions(path):
|
||||||
for n in os.listdir(path):
|
for n in os.listdir(path):
|
||||||
full = os.path.join(path, n)
|
full = os.path.join(path, n)
|
||||||
|
|
|
@ -8,6 +8,7 @@ from migen.genlib.resetsync import AsyncResetSynchronizer
|
||||||
from migen.genlib.io import *
|
from migen.genlib.io import *
|
||||||
from mibuild import tools
|
from mibuild import tools
|
||||||
|
|
||||||
|
|
||||||
def settings(path, ver=None, sub=None):
|
def settings(path, ver=None, sub=None):
|
||||||
vers = list(tools.versions(path))
|
vers = list(tools.versions(path))
|
||||||
if ver is None:
|
if ver is None:
|
||||||
|
@ -31,26 +32,31 @@ def settings(path, ver=None, sub=None):
|
||||||
|
|
||||||
raise OSError("no settings file found")
|
raise OSError("no settings file found")
|
||||||
|
|
||||||
|
|
||||||
class XilinxNoRetimingImpl(Module):
|
class XilinxNoRetimingImpl(Module):
|
||||||
def __init__(self, reg):
|
def __init__(self, reg):
|
||||||
self.specials += SynthesisDirective("attribute register_balancing of {r} is no", r=reg)
|
self.specials += SynthesisDirective("attribute register_balancing of {r} is no", r=reg)
|
||||||
|
|
||||||
|
|
||||||
class XilinxNoRetiming:
|
class XilinxNoRetiming:
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def lower(dr):
|
def lower(dr):
|
||||||
return XilinxNoRetimingImpl(dr.reg)
|
return XilinxNoRetimingImpl(dr.reg)
|
||||||
|
|
||||||
|
|
||||||
class XilinxMultiRegImpl(MultiRegImpl):
|
class XilinxMultiRegImpl(MultiRegImpl):
|
||||||
def __init__(self, *args, **kwargs):
|
def __init__(self, *args, **kwargs):
|
||||||
MultiRegImpl.__init__(self, *args, **kwargs)
|
MultiRegImpl.__init__(self, *args, **kwargs)
|
||||||
self.specials += [SynthesisDirective("attribute shreg_extract of {r} is no", r=r)
|
self.specials += [SynthesisDirective("attribute shreg_extract of {r} is no", r=r)
|
||||||
for r in self.regs]
|
for r in self.regs]
|
||||||
|
|
||||||
|
|
||||||
class XilinxMultiReg:
|
class XilinxMultiReg:
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def lower(dr):
|
def lower(dr):
|
||||||
return XilinxMultiRegImpl(dr.i, dr.o, dr.odomain, dr.n)
|
return XilinxMultiRegImpl(dr.i, dr.o, dr.odomain, dr.n)
|
||||||
|
|
||||||
|
|
||||||
class XilinxAsyncResetSynchronizerImpl(Module):
|
class XilinxAsyncResetSynchronizerImpl(Module):
|
||||||
def __init__(self, cd, async_reset):
|
def __init__(self, cd, async_reset):
|
||||||
rst1 = Signal()
|
rst1 = Signal()
|
||||||
|
@ -61,29 +67,35 @@ class XilinxAsyncResetSynchronizerImpl(Module):
|
||||||
i_CE=1, i_C=cd.clk, o_Q=cd.rst)
|
i_CE=1, i_C=cd.clk, o_Q=cd.rst)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class XilinxAsyncResetSynchronizer:
|
class XilinxAsyncResetSynchronizer:
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def lower(dr):
|
def lower(dr):
|
||||||
return XilinxAsyncResetSynchronizerImpl(dr.cd, dr.async_reset)
|
return XilinxAsyncResetSynchronizerImpl(dr.cd, dr.async_reset)
|
||||||
|
|
||||||
|
|
||||||
class XilinxDifferentialInputImpl(Module):
|
class XilinxDifferentialInputImpl(Module):
|
||||||
def __init__(self, i_p, i_n, o):
|
def __init__(self, i_p, i_n, o):
|
||||||
self.specials += Instance("IBUFDS", i_I=i_p, i_IB=i_n, o_O=o)
|
self.specials += Instance("IBUFDS", i_I=i_p, i_IB=i_n, o_O=o)
|
||||||
|
|
||||||
|
|
||||||
class XilinxDifferentialInput:
|
class XilinxDifferentialInput:
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def lower(dr):
|
def lower(dr):
|
||||||
return XilinxDifferentialInputImpl(dr.i_p, dr.i_n, dr.o)
|
return XilinxDifferentialInputImpl(dr.i_p, dr.i_n, dr.o)
|
||||||
|
|
||||||
|
|
||||||
class XilinxDifferentialOutputImpl(Module):
|
class XilinxDifferentialOutputImpl(Module):
|
||||||
def __init__(self, i, o_p, o_n):
|
def __init__(self, i, o_p, o_n):
|
||||||
self.specials += Instance("OBUFDS", i_I=i, o_O=o_p, o_OB=o_n)
|
self.specials += Instance("OBUFDS", i_I=i, o_O=o_p, o_OB=o_n)
|
||||||
|
|
||||||
|
|
||||||
class XilinxDifferentialOutput:
|
class XilinxDifferentialOutput:
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def lower(dr):
|
def lower(dr):
|
||||||
return XilinxDifferentialOutputImpl(dr.i, dr.o_p, dr.o_n)
|
return XilinxDifferentialOutputImpl(dr.i, dr.o_p, dr.o_n)
|
||||||
|
|
||||||
|
|
||||||
class XilinxDDROutputImpl(Module):
|
class XilinxDDROutputImpl(Module):
|
||||||
def __init__(self, i1, i2, o, clk):
|
def __init__(self, i1, i2, o, clk):
|
||||||
self.specials += Instance("ODDR",
|
self.specials += Instance("ODDR",
|
||||||
|
@ -92,6 +104,7 @@ class XilinxDDROutputImpl(Module):
|
||||||
i_D1=i1, i_D2=i2, o_Q=o,
|
i_D1=i1, i_D2=i2, o_Q=o,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
class XilinxDDROutput:
|
class XilinxDDROutput:
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def lower(dr):
|
def lower(dr):
|
||||||
|
|
|
@ -7,6 +7,7 @@ from mibuild.generic_platform import *
|
||||||
from mibuild import tools
|
from mibuild import tools
|
||||||
from mibuild.xilinx import common
|
from mibuild.xilinx import common
|
||||||
|
|
||||||
|
|
||||||
def _format_constraint(c):
|
def _format_constraint(c):
|
||||||
if isinstance(c, Pins):
|
if isinstance(c, Pins):
|
||||||
return "LOC=" + c.identifiers[0]
|
return "LOC=" + c.identifiers[0]
|
||||||
|
@ -17,6 +18,7 @@ def _format_constraint(c):
|
||||||
elif isinstance(c, Misc):
|
elif isinstance(c, Misc):
|
||||||
return c.misc
|
return c.misc
|
||||||
|
|
||||||
|
|
||||||
def _format_ucf(signame, pin, others, resname):
|
def _format_ucf(signame, pin, others, resname):
|
||||||
fmt_c = []
|
fmt_c = []
|
||||||
for c in [Pins(pin)] + others:
|
for c in [Pins(pin)] + others:
|
||||||
|
@ -28,6 +30,7 @@ def _format_ucf(signame, pin, others, resname):
|
||||||
fmt_r += "." + resname[2]
|
fmt_r += "." + resname[2]
|
||||||
return "NET \"" + signame + "\" " + " | ".join(fmt_c) + "; # " + fmt_r + "\n"
|
return "NET \"" + signame + "\" " + " | ".join(fmt_c) + "; # " + fmt_r + "\n"
|
||||||
|
|
||||||
|
|
||||||
def _build_ucf(named_sc, named_pc):
|
def _build_ucf(named_sc, named_pc):
|
||||||
r = ""
|
r = ""
|
||||||
for sig, pins, others, resname in named_sc:
|
for sig, pins, others, resname in named_sc:
|
||||||
|
@ -40,6 +43,7 @@ def _build_ucf(named_sc, named_pc):
|
||||||
r += "\n" + "\n\n".join(named_pc)
|
r += "\n" + "\n\n".join(named_pc)
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _build_xst_files(device, sources, vincpaths, build_name, xst_opt):
|
def _build_xst_files(device, sources, vincpaths, build_name, xst_opt):
|
||||||
prj_contents = ""
|
prj_contents = ""
|
||||||
for filename, language in sources:
|
for filename, language in sources:
|
||||||
|
@ -57,6 +61,7 @@ def _build_xst_files(device, sources, vincpaths, build_name, xst_opt):
|
||||||
xst_contents += "-vlgincdir " + path + "\n"
|
xst_contents += "-vlgincdir " + path + "\n"
|
||||||
tools.write_to_file(build_name + ".xst", xst_contents)
|
tools.write_to_file(build_name + ".xst", xst_contents)
|
||||||
|
|
||||||
|
|
||||||
def _run_yosys(device, sources, vincpaths, build_name):
|
def _run_yosys(device, sources, vincpaths, build_name):
|
||||||
ys_contents = ""
|
ys_contents = ""
|
||||||
incflags = ""
|
incflags = ""
|
||||||
|
@ -87,6 +92,7 @@ synth_xilinx -arch {arch} -top top -edif {build_name}.edif""".format(arch=arch,
|
||||||
if r != 0:
|
if r != 0:
|
||||||
raise OSError("Subprocess failed")
|
raise OSError("Subprocess failed")
|
||||||
|
|
||||||
|
|
||||||
def _run_ise(build_name, ise_path, source, mode, ngdbuild_opt,
|
def _run_ise(build_name, ise_path, source, mode, ngdbuild_opt,
|
||||||
bitgen_opt, ise_commands, map_opt, par_opt, ver=None):
|
bitgen_opt, ise_commands, map_opt, par_opt, ver=None):
|
||||||
if sys.platform == "win32" or sys.platform == "cygwin":
|
if sys.platform == "win32" or sys.platform == "cygwin":
|
||||||
|
@ -120,6 +126,7 @@ bitgen {bitgen_opt} {build_name}.ncd {build_name}.bit
|
||||||
if r != 0:
|
if r != 0:
|
||||||
raise OSError("Subprocess failed")
|
raise OSError("Subprocess failed")
|
||||||
|
|
||||||
|
|
||||||
class XilinxISEToolchain:
|
class XilinxISEToolchain:
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.xst_opt = """-ifmt MIXED
|
self.xst_opt = """-ifmt MIXED
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from mibuild.generic_platform import GenericPlatform
|
from mibuild.generic_platform import GenericPlatform
|
||||||
from mibuild.xilinx import common, vivado, ise
|
from mibuild.xilinx import common, vivado, ise
|
||||||
|
|
||||||
|
|
||||||
class XilinxPlatform(GenericPlatform):
|
class XilinxPlatform(GenericPlatform):
|
||||||
bitstream_ext = ".bit"
|
bitstream_ext = ".bit"
|
||||||
|
|
||||||
|
|
|
@ -3,11 +3,13 @@ import sys, subprocess
|
||||||
from mibuild.generic_programmer import GenericProgrammer
|
from mibuild.generic_programmer import GenericProgrammer
|
||||||
from mibuild.xilinx import common
|
from mibuild.xilinx import common
|
||||||
|
|
||||||
|
|
||||||
def _run_urjtag(cmds):
|
def _run_urjtag(cmds):
|
||||||
with subprocess.Popen("jtag", stdin=subprocess.PIPE) as process:
|
with subprocess.Popen("jtag", stdin=subprocess.PIPE) as process:
|
||||||
process.stdin.write(cmds.encode("ASCII"))
|
process.stdin.write(cmds.encode("ASCII"))
|
||||||
process.communicate()
|
process.communicate()
|
||||||
|
|
||||||
|
|
||||||
class UrJTAG(GenericProgrammer):
|
class UrJTAG(GenericProgrammer):
|
||||||
needs_bitreverse = True
|
needs_bitreverse = True
|
||||||
|
|
||||||
|
@ -32,6 +34,7 @@ flashmem "{address}" "{data_file}" noverify
|
||||||
""".format(flash_proxy=flash_proxy, address=address, data_file=data_file)
|
""".format(flash_proxy=flash_proxy, address=address, data_file=data_file)
|
||||||
_run_urjtag(cmds)
|
_run_urjtag(cmds)
|
||||||
|
|
||||||
|
|
||||||
class XC3SProg(GenericProgrammer):
|
class XC3SProg(GenericProgrammer):
|
||||||
needs_bitreverse = False
|
needs_bitreverse = False
|
||||||
|
|
||||||
|
@ -47,6 +50,7 @@ class XC3SProg(GenericProgrammer):
|
||||||
subprocess.call(["xc3sprog", "-v", "-c", self.cable, "-I"+flash_proxy, "{}:w:0x{:x}:BIN".format(data_file, address)])
|
subprocess.call(["xc3sprog", "-v", "-c", self.cable, "-I"+flash_proxy, "{}:w:0x{:x}:BIN".format(data_file, address)])
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
class FpgaProg(GenericProgrammer):
|
class FpgaProg(GenericProgrammer):
|
||||||
needs_bitreverse = False
|
needs_bitreverse = False
|
||||||
|
|
||||||
|
@ -63,11 +67,13 @@ class FpgaProg(GenericProgrammer):
|
||||||
subprocess.call(["fpgaprog", "-v", "-sa", "-r", "-b", flash_proxy,
|
subprocess.call(["fpgaprog", "-v", "-sa", "-r", "-b", flash_proxy,
|
||||||
"-f", data_file])
|
"-f", data_file])
|
||||||
|
|
||||||
|
|
||||||
def _run_impact(cmds):
|
def _run_impact(cmds):
|
||||||
with subprocess.Popen("impact -batch", stdin=subprocess.PIPE) as process:
|
with subprocess.Popen("impact -batch", stdin=subprocess.PIPE) as process:
|
||||||
process.stdin.write(cmds.encode("ASCII"))
|
process.stdin.write(cmds.encode("ASCII"))
|
||||||
process.communicate()
|
process.communicate()
|
||||||
|
|
||||||
|
|
||||||
class iMPACT(GenericProgrammer):
|
class iMPACT(GenericProgrammer):
|
||||||
needs_bitreverse = False
|
needs_bitreverse = False
|
||||||
|
|
||||||
|
@ -80,6 +86,7 @@ quit
|
||||||
""".format(bitstream=bitstream_file)
|
""".format(bitstream=bitstream_file)
|
||||||
_run_impact(cmds)
|
_run_impact(cmds)
|
||||||
|
|
||||||
|
|
||||||
def _run_vivado(path, ver, cmds):
|
def _run_vivado(path, ver, cmds):
|
||||||
if sys.platform == "win32" or sys.platform == "cygwin":
|
if sys.platform == "win32" or sys.platform == "cygwin":
|
||||||
vivado_cmd = "vivado -mode tcl"
|
vivado_cmd = "vivado -mode tcl"
|
||||||
|
@ -90,6 +97,7 @@ def _run_vivado(path, ver, cmds):
|
||||||
process.stdin.write(cmds.encode("ASCII"))
|
process.stdin.write(cmds.encode("ASCII"))
|
||||||
process.communicate()
|
process.communicate()
|
||||||
|
|
||||||
|
|
||||||
class VivadoProgrammer(GenericProgrammer):
|
class VivadoProgrammer(GenericProgrammer):
|
||||||
needs_bitreverse = False
|
needs_bitreverse = False
|
||||||
def __init__(self, vivado_path="/opt/Xilinx/Vivado", vivado_ver=None):
|
def __init__(self, vivado_path="/opt/Xilinx/Vivado", vivado_ver=None):
|
||||||
|
|
|
@ -10,6 +10,7 @@ from mibuild.generic_platform import *
|
||||||
from mibuild import tools
|
from mibuild import tools
|
||||||
from mibuild.xilinx import common
|
from mibuild.xilinx import common
|
||||||
|
|
||||||
|
|
||||||
def _format_constraint(c):
|
def _format_constraint(c):
|
||||||
if isinstance(c, Pins):
|
if isinstance(c, Pins):
|
||||||
return "set_property LOC " + c.identifiers[0]
|
return "set_property LOC " + c.identifiers[0]
|
||||||
|
@ -22,6 +23,7 @@ def _format_constraint(c):
|
||||||
else:
|
else:
|
||||||
raise ValueError("unknown constraint %s" % c)
|
raise ValueError("unknown constraint %s" % c)
|
||||||
|
|
||||||
|
|
||||||
def _format_xdc(signame, resname, *constraints):
|
def _format_xdc(signame, resname, *constraints):
|
||||||
fmt_c = [_format_constraint(c) for c in constraints]
|
fmt_c = [_format_constraint(c) for c in constraints]
|
||||||
fmt_r = resname[0] + ":" + str(resname[1])
|
fmt_r = resname[0] + ":" + str(resname[1])
|
||||||
|
@ -32,6 +34,7 @@ def _format_xdc(signame, resname, *constraints):
|
||||||
r += c + " [get_ports " + signame + "]\n"
|
r += c + " [get_ports " + signame + "]\n"
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _build_xdc(named_sc, named_pc):
|
def _build_xdc(named_sc, named_pc):
|
||||||
r = ""
|
r = ""
|
||||||
for sig, pins, others, resname in named_sc:
|
for sig, pins, others, resname in named_sc:
|
||||||
|
@ -46,6 +49,7 @@ def _build_xdc(named_sc, named_pc):
|
||||||
r += "\n" + "\n\n".join(named_pc)
|
r += "\n" + "\n\n".join(named_pc)
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _run_vivado(build_name, vivado_path, source, ver=None):
|
def _run_vivado(build_name, vivado_path, source, ver=None):
|
||||||
if sys.platform == "win32" or sys.platform == "cygwin":
|
if sys.platform == "win32" or sys.platform == "cygwin":
|
||||||
build_script_contents = "REM Autogenerated by mibuild\n"
|
build_script_contents = "REM Autogenerated by mibuild\n"
|
||||||
|
@ -65,6 +69,7 @@ def _run_vivado(build_name, vivado_path, source, ver=None):
|
||||||
if r != 0:
|
if r != 0:
|
||||||
raise OSError("Subprocess failed")
|
raise OSError("Subprocess failed")
|
||||||
|
|
||||||
|
|
||||||
class XilinxVivadoToolchain:
|
class XilinxVivadoToolchain:
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.bitstream_commands = []
|
self.bitstream_commands = []
|
||||||
|
|
|
@ -2,6 +2,7 @@ from migen.fhdl.std import *
|
||||||
from migen.bus import wishbone
|
from migen.bus import wishbone
|
||||||
from migen.flow.actor import *
|
from migen.flow.actor import *
|
||||||
|
|
||||||
|
|
||||||
class Reader(Module):
|
class Reader(Module):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.bus = wishbone.Interface()
|
self.bus = wishbone.Interface()
|
||||||
|
@ -34,6 +35,7 @@ class Reader(Module):
|
||||||
)
|
)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Writer(Module):
|
class Writer(Module):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.bus = wishbone.Interface()
|
self.bus = wishbone.Interface()
|
||||||
|
|
|
@ -2,6 +2,7 @@ from migen.fhdl.std import *
|
||||||
from migen.flow.actor import *
|
from migen.flow.actor import *
|
||||||
from migen.genlib import fifo
|
from migen.genlib import fifo
|
||||||
|
|
||||||
|
|
||||||
class _FIFOActor(Module):
|
class _FIFOActor(Module):
|
||||||
def __init__(self, fifo_class, layout, depth):
|
def __init__(self, fifo_class, layout, depth):
|
||||||
self.sink = Sink(layout)
|
self.sink = Sink(layout)
|
||||||
|
@ -42,6 +43,7 @@ class _FIFOActor(Module):
|
||||||
self.source.eop.eq(self.fifo.dout.eop)
|
self.source.eop.eq(self.fifo.dout.eop)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class SyncFIFO(_FIFOActor):
|
class SyncFIFO(_FIFOActor):
|
||||||
def __init__(self, layout, depth, buffered=False):
|
def __init__(self, layout, depth, buffered=False):
|
||||||
_FIFOActor.__init__(
|
_FIFOActor.__init__(
|
||||||
|
@ -49,6 +51,7 @@ class SyncFIFO(_FIFOActor):
|
||||||
fifo.SyncFIFOBuffered if buffered else fifo.SyncFIFO,
|
fifo.SyncFIFOBuffered if buffered else fifo.SyncFIFO,
|
||||||
layout, depth)
|
layout, depth)
|
||||||
|
|
||||||
|
|
||||||
class AsyncFIFO(_FIFOActor):
|
class AsyncFIFO(_FIFOActor):
|
||||||
def __init__(self, layout, depth):
|
def __init__(self, layout, depth):
|
||||||
_FIFOActor.__init__(self, fifo.AsyncFIFO, layout, depth)
|
_FIFOActor.__init__(self, fifo.AsyncFIFO, layout, depth)
|
||||||
|
|
|
@ -3,6 +3,7 @@ from migen.genlib.record import *
|
||||||
from migen.genlib.fsm import *
|
from migen.genlib.fsm import *
|
||||||
from migen.flow.actor import *
|
from migen.flow.actor import *
|
||||||
|
|
||||||
|
|
||||||
# Generates integers from start to maximum-1
|
# Generates integers from start to maximum-1
|
||||||
class IntSequence(Module):
|
class IntSequence(Module):
|
||||||
def __init__(self, nbits, offsetbits=0, step=1):
|
def __init__(self, nbits, offsetbits=0, step=1):
|
||||||
|
|
|
@ -3,6 +3,7 @@ from migen.flow.actor import *
|
||||||
from migen.flow.transactions import *
|
from migen.flow.transactions import *
|
||||||
from migen.util.misc import xdir
|
from migen.util.misc import xdir
|
||||||
|
|
||||||
|
|
||||||
def _sim_multiread(sim, obj):
|
def _sim_multiread(sim, obj):
|
||||||
if isinstance(obj, Signal):
|
if isinstance(obj, Signal):
|
||||||
return sim.rd(obj)
|
return sim.rd(obj)
|
||||||
|
@ -14,6 +15,7 @@ def _sim_multiread(sim, obj):
|
||||||
r[k] = rd
|
r[k] = rd
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _sim_multiwrite(sim, obj, value):
|
def _sim_multiwrite(sim, obj, value):
|
||||||
if isinstance(obj, Signal):
|
if isinstance(obj, Signal):
|
||||||
sim.wr(obj, value)
|
sim.wr(obj, value)
|
||||||
|
@ -21,6 +23,7 @@ def _sim_multiwrite(sim, obj, value):
|
||||||
for k, v in value.items():
|
for k, v in value.items():
|
||||||
_sim_multiwrite(sim, getattr(obj, k), v)
|
_sim_multiwrite(sim, getattr(obj, k), v)
|
||||||
|
|
||||||
|
|
||||||
# Generators yield None or a tuple of Tokens.
|
# Generators yield None or a tuple of Tokens.
|
||||||
# Tokens for Sink endpoints are pulled and the "value" field filled in.
|
# Tokens for Sink endpoints are pulled and the "value" field filled in.
|
||||||
# Tokens for Source endpoints are pushed according to their "value" field.
|
# Tokens for Source endpoints are pushed according to their "value" field.
|
||||||
|
@ -91,6 +94,7 @@ class TokenExchanger(Module):
|
||||||
self._update_control_signals(selfp)
|
self._update_control_signals(selfp)
|
||||||
do_simulation.passive = True
|
do_simulation.passive = True
|
||||||
|
|
||||||
|
|
||||||
class SimActor(Module):
|
class SimActor(Module):
|
||||||
def __init__(self, generator):
|
def __init__(self, generator):
|
||||||
self.busy = Signal()
|
self.busy = Signal()
|
||||||
|
@ -100,6 +104,7 @@ class SimActor(Module):
|
||||||
selfp.busy = self.token_exchanger.busy
|
selfp.busy = self.token_exchanger.busy
|
||||||
do_simulation.passive = True
|
do_simulation.passive = True
|
||||||
|
|
||||||
|
|
||||||
def _dumper_gen(prefix):
|
def _dumper_gen(prefix):
|
||||||
while True:
|
while True:
|
||||||
t = Token("result")
|
t = Token("result")
|
||||||
|
@ -110,6 +115,7 @@ def _dumper_gen(prefix):
|
||||||
s = str(list(t.value.values())[0])
|
s = str(list(t.value.values())[0])
|
||||||
print(prefix + s)
|
print(prefix + s)
|
||||||
|
|
||||||
|
|
||||||
class Dumper(SimActor):
|
class Dumper(SimActor):
|
||||||
def __init__(self, layout, prefix=""):
|
def __init__(self, layout, prefix=""):
|
||||||
self.result = Sink(layout)
|
self.result = Sink(layout)
|
||||||
|
|
|
@ -7,6 +7,7 @@ from migen.flow.network import *
|
||||||
from migen.flow import plumbing
|
from migen.flow import plumbing
|
||||||
from migen.actorlib import misc
|
from migen.actorlib import misc
|
||||||
|
|
||||||
|
|
||||||
# layout is a list of tuples, either:
|
# layout is a list of tuples, either:
|
||||||
# - (name, nbits, [reset value], [alignment bits])
|
# - (name, nbits, [reset value], [alignment bits])
|
||||||
# - (name, sublayout)
|
# - (name, sublayout)
|
||||||
|
@ -22,6 +23,7 @@ def _convert_layout(layout):
|
||||||
|
|
||||||
(MODE_EXTERNAL, MODE_SINGLE_SHOT, MODE_CONTINUOUS) = range(3)
|
(MODE_EXTERNAL, MODE_SINGLE_SHOT, MODE_CONTINUOUS) = range(3)
|
||||||
|
|
||||||
|
|
||||||
class SingleGenerator(Module, AutoCSR):
|
class SingleGenerator(Module, AutoCSR):
|
||||||
def __init__(self, layout, mode):
|
def __init__(self, layout, mode):
|
||||||
self.source = Source(_convert_layout(layout))
|
self.source = Source(_convert_layout(layout))
|
||||||
|
@ -68,6 +70,7 @@ class SingleGenerator(Module, AutoCSR):
|
||||||
self.sync += If(self.source.ack | ~self.source.stb,
|
self.sync += If(self.source.ack | ~self.source.stb,
|
||||||
getattr(target, name).eq(reg.storage))
|
getattr(target, name).eq(reg.storage))
|
||||||
|
|
||||||
|
|
||||||
class Collector(Module, AutoCSR):
|
class Collector(Module, AutoCSR):
|
||||||
def __init__(self, layout, depth=1024):
|
def __init__(self, layout, depth=1024):
|
||||||
self.sink = Sink(layout)
|
self.sink = Sink(layout)
|
||||||
|
@ -108,6 +111,7 @@ class Collector(Module, AutoCSR):
|
||||||
self._rd.status.eq(rp.dat_r)
|
self._rd.status.eq(rp.dat_r)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class _DMAController(Module):
|
class _DMAController(Module):
|
||||||
def __init__(self, bus_accessor, bus_aw, bus_dw, mode, base_reset=0, length_reset=0):
|
def __init__(self, bus_accessor, bus_aw, bus_dw, mode, base_reset=0, length_reset=0):
|
||||||
self.alignment_bits = bits_for(bus_dw//8) - 1
|
self.alignment_bits = bits_for(bus_dw//8) - 1
|
||||||
|
@ -126,6 +130,7 @@ class _DMAController(Module):
|
||||||
def get_csrs(self):
|
def get_csrs(self):
|
||||||
return self.generator.get_csrs() + [self.r_busy]
|
return self.generator.get_csrs() + [self.r_busy]
|
||||||
|
|
||||||
|
|
||||||
class DMAReadController(_DMAController):
|
class DMAReadController(_DMAController):
|
||||||
def __init__(self, bus_accessor, *args, **kwargs):
|
def __init__(self, bus_accessor, *args, **kwargs):
|
||||||
bus_aw = flen(bus_accessor.address.a)
|
bus_aw = flen(bus_accessor.address.a)
|
||||||
|
@ -145,6 +150,7 @@ class DMAReadController(_DMAController):
|
||||||
self.busy = comp_actor.busy
|
self.busy = comp_actor.busy
|
||||||
self.comb += self.r_busy.status.eq(self.busy)
|
self.comb += self.r_busy.status.eq(self.busy)
|
||||||
|
|
||||||
|
|
||||||
class DMAWriteController(_DMAController):
|
class DMAWriteController(_DMAController):
|
||||||
def __init__(self, bus_accessor, *args, ack_when_inactive=False, **kwargs):
|
def __init__(self, bus_accessor, *args, ack_when_inactive=False, **kwargs):
|
||||||
bus_aw = flen(bus_accessor.address_data.a)
|
bus_aw = flen(bus_accessor.address_data.a)
|
||||||
|
|
|
@ -4,12 +4,14 @@ from migen.fhdl.std import *
|
||||||
from migen.genlib.record import *
|
from migen.genlib.record import *
|
||||||
from migen.flow.actor import *
|
from migen.flow.actor import *
|
||||||
|
|
||||||
|
|
||||||
def _rawbits_layout(l):
|
def _rawbits_layout(l):
|
||||||
if isinstance(l, int):
|
if isinstance(l, int):
|
||||||
return [("rawbits", l)]
|
return [("rawbits", l)]
|
||||||
else:
|
else:
|
||||||
return l
|
return l
|
||||||
|
|
||||||
|
|
||||||
class Cast(CombinatorialActor):
|
class Cast(CombinatorialActor):
|
||||||
def __init__(self, layout_from, layout_to, reverse_from=False, reverse_to=False):
|
def __init__(self, layout_from, layout_to, reverse_from=False, reverse_to=False):
|
||||||
self.sink = Sink(_rawbits_layout(layout_from))
|
self.sink = Sink(_rawbits_layout(layout_from))
|
||||||
|
@ -28,9 +30,11 @@ class Cast(CombinatorialActor):
|
||||||
raise TypeError
|
raise TypeError
|
||||||
self.comb += Cat(*sigs_to).eq(Cat(*sigs_from))
|
self.comb += Cat(*sigs_to).eq(Cat(*sigs_from))
|
||||||
|
|
||||||
|
|
||||||
def pack_layout(l, n):
|
def pack_layout(l, n):
|
||||||
return [("chunk"+str(i), l) for i in range(n)]
|
return [("chunk"+str(i), l) for i in range(n)]
|
||||||
|
|
||||||
|
|
||||||
class Unpack(Module):
|
class Unpack(Module):
|
||||||
def __init__(self, n, layout_to, reverse=False):
|
def __init__(self, n, layout_to, reverse=False):
|
||||||
self.source = source = Source(layout_to)
|
self.source = source = Source(layout_to)
|
||||||
|
@ -77,6 +81,7 @@ class Unpack(Module):
|
||||||
source.eop.eq(sink.eop & last)
|
source.eop.eq(sink.eop & last)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Pack(Module):
|
class Pack(Module):
|
||||||
def __init__(self, layout_from, n, reverse=False):
|
def __init__(self, layout_from, n, reverse=False):
|
||||||
self.sink = sink = Sink(layout_from)
|
self.sink = sink = Sink(layout_from)
|
||||||
|
@ -136,6 +141,7 @@ class Pack(Module):
|
||||||
)
|
)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Chunkerize(CombinatorialActor):
|
class Chunkerize(CombinatorialActor):
|
||||||
def __init__(self, layout_from, layout_to, n, reverse=False):
|
def __init__(self, layout_from, layout_to, n, reverse=False):
|
||||||
self.sink = Sink(layout_from)
|
self.sink = Sink(layout_from)
|
||||||
|
@ -161,6 +167,7 @@ class Chunkerize(CombinatorialActor):
|
||||||
dst = getattr(self.source, f[0])
|
dst = getattr(self.source, f[0])
|
||||||
self.comb += dst.eq(src)
|
self.comb += dst.eq(src)
|
||||||
|
|
||||||
|
|
||||||
class Unchunkerize(CombinatorialActor):
|
class Unchunkerize(CombinatorialActor):
|
||||||
def __init__(self, layout_from, n, layout_to, reverse=False):
|
def __init__(self, layout_from, n, layout_to, reverse=False):
|
||||||
if isinstance(layout_from, EndpointDescription):
|
if isinstance(layout_from, EndpointDescription):
|
||||||
|
@ -188,6 +195,7 @@ class Unchunkerize(CombinatorialActor):
|
||||||
dst = getattr(self.source, f[0])
|
dst = getattr(self.source, f[0])
|
||||||
self.comb += dst.eq(src)
|
self.comb += dst.eq(src)
|
||||||
|
|
||||||
|
|
||||||
class Converter(Module):
|
class Converter(Module):
|
||||||
def __init__(self, layout_from, layout_to, reverse=False):
|
def __init__(self, layout_from, layout_to, reverse=False):
|
||||||
self.sink = Sink(layout_from)
|
self.sink = Sink(layout_from)
|
||||||
|
@ -231,6 +239,7 @@ class Converter(Module):
|
||||||
else:
|
else:
|
||||||
self.comb += Record.connect(self.sink, self.source)
|
self.comb += Record.connect(self.sink, self.source)
|
||||||
|
|
||||||
|
|
||||||
class Pipeline(Module):
|
class Pipeline(Module):
|
||||||
def __init__(self, *modules):
|
def __init__(self, *modules):
|
||||||
self.busy = Signal()
|
self.busy = Signal()
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from migen.fhdl.std import Module, bits_for
|
from migen.fhdl.std import Module, bits_for
|
||||||
from migen.bank.description import CSR
|
from migen.bank.description import CSR
|
||||||
|
|
||||||
|
|
||||||
class GenericBank(Module):
|
class GenericBank(Module):
|
||||||
def __init__(self, description, busword):
|
def __init__(self, description, busword):
|
||||||
# Turn description into simple CSRs and claim ownership of compound CSR modules
|
# Turn description into simple CSRs and claim ownership of compound CSR modules
|
||||||
|
@ -14,6 +15,7 @@ class GenericBank(Module):
|
||||||
self.submodules += c
|
self.submodules += c
|
||||||
self.decode_bits = bits_for(len(self.simple_csrs)-1)
|
self.decode_bits = bits_for(len(self.simple_csrs)-1)
|
||||||
|
|
||||||
|
|
||||||
def get_offset(description, name, busword):
|
def get_offset(description, name, busword):
|
||||||
offset = 0
|
offset = 0
|
||||||
for c in description:
|
for c in description:
|
||||||
|
|
|
@ -3,6 +3,7 @@ from migen.fhdl.std import *
|
||||||
from migen.bus import csr
|
from migen.bus import csr
|
||||||
from migen.bank.bank import GenericBank
|
from migen.bank.bank import GenericBank
|
||||||
|
|
||||||
|
|
||||||
class Bank(GenericBank):
|
class Bank(GenericBank):
|
||||||
def __init__(self, description, address=0, bus=None):
|
def __init__(self, description, address=0, bus=None):
|
||||||
if bus is None:
|
if bus is None:
|
||||||
|
@ -30,6 +31,7 @@ class Bank(GenericBank):
|
||||||
If(sel, Case(self.bus.adr[:self.decode_bits], brcases))
|
If(sel, Case(self.bus.adr[:self.decode_bits], brcases))
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
# address_map(name, memory) returns the CSR offset at which to map
|
# address_map(name, memory) returns the CSR offset at which to map
|
||||||
# the CSR object (register bank or memory).
|
# the CSR object (register bank or memory).
|
||||||
# If memory=None, the object is the register bank of object source.name.
|
# If memory=None, the object is the register bank of object source.name.
|
||||||
|
|
|
@ -2,6 +2,7 @@ from migen.util.misc import xdir
|
||||||
from migen.fhdl.std import *
|
from migen.fhdl.std import *
|
||||||
from migen.fhdl.tracer import get_obj_var_name
|
from migen.fhdl.tracer import get_obj_var_name
|
||||||
|
|
||||||
|
|
||||||
class _CSRBase(HUID):
|
class _CSRBase(HUID):
|
||||||
def __init__(self, size, name):
|
def __init__(self, size, name):
|
||||||
HUID.__init__(self)
|
HUID.__init__(self)
|
||||||
|
@ -10,6 +11,7 @@ class _CSRBase(HUID):
|
||||||
raise ValueError("Cannot extract CSR name from code, need to specify.")
|
raise ValueError("Cannot extract CSR name from code, need to specify.")
|
||||||
self.size = size
|
self.size = size
|
||||||
|
|
||||||
|
|
||||||
class CSR(_CSRBase):
|
class CSR(_CSRBase):
|
||||||
def __init__(self, size=1, name=None):
|
def __init__(self, size=1, name=None):
|
||||||
_CSRBase.__init__(self, size, name)
|
_CSRBase.__init__(self, size, name)
|
||||||
|
@ -17,6 +19,7 @@ class CSR(_CSRBase):
|
||||||
self.r = Signal(self.size, name=self.name + "_r")
|
self.r = Signal(self.size, name=self.name + "_r")
|
||||||
self.w = Signal(self.size, name=self.name + "_w")
|
self.w = Signal(self.size, name=self.name + "_w")
|
||||||
|
|
||||||
|
|
||||||
class _CompoundCSR(_CSRBase, Module):
|
class _CompoundCSR(_CSRBase, Module):
|
||||||
def __init__(self, size, name):
|
def __init__(self, size, name):
|
||||||
_CSRBase.__init__(self, size, name)
|
_CSRBase.__init__(self, size, name)
|
||||||
|
@ -30,6 +33,7 @@ class _CompoundCSR(_CSRBase, Module):
|
||||||
def do_finalize(self, busword):
|
def do_finalize(self, busword):
|
||||||
raise NotImplementedError
|
raise NotImplementedError
|
||||||
|
|
||||||
|
|
||||||
class CSRStatus(_CompoundCSR):
|
class CSRStatus(_CompoundCSR):
|
||||||
def __init__(self, size=1, reset=0, name=None):
|
def __init__(self, size=1, reset=0, name=None):
|
||||||
_CompoundCSR.__init__(self, size, name)
|
_CompoundCSR.__init__(self, size, name)
|
||||||
|
@ -43,6 +47,7 @@ class CSRStatus(_CompoundCSR):
|
||||||
self.comb += sc.w.eq(self.status[i*busword:i*busword+nbits])
|
self.comb += sc.w.eq(self.status[i*busword:i*busword+nbits])
|
||||||
self.simple_csrs.append(sc)
|
self.simple_csrs.append(sc)
|
||||||
|
|
||||||
|
|
||||||
class CSRStorage(_CompoundCSR):
|
class CSRStorage(_CompoundCSR):
|
||||||
def __init__(self, size=1, reset=0, atomic_write=False, write_from_dev=False, alignment_bits=0, name=None):
|
def __init__(self, size=1, reset=0, atomic_write=False, write_from_dev=False, alignment_bits=0, name=None):
|
||||||
_CompoundCSR.__init__(self, size, name)
|
_CompoundCSR.__init__(self, size, name)
|
||||||
|
@ -85,18 +90,21 @@ class CSRStorage(_CompoundCSR):
|
||||||
self.sync += If(sc.re, self.storage_full[lo:hi].eq(sc.r))
|
self.sync += If(sc.re, self.storage_full[lo:hi].eq(sc.r))
|
||||||
self.sync += self.re.eq(sc.re)
|
self.sync += self.re.eq(sc.re)
|
||||||
|
|
||||||
|
|
||||||
def csrprefix(prefix, csrs, done):
|
def csrprefix(prefix, csrs, done):
|
||||||
for csr in csrs:
|
for csr in csrs:
|
||||||
if csr.huid not in done:
|
if csr.huid not in done:
|
||||||
csr.name = prefix + csr.name
|
csr.name = prefix + csr.name
|
||||||
done.add(csr.huid)
|
done.add(csr.huid)
|
||||||
|
|
||||||
|
|
||||||
def memprefix(prefix, memories, done):
|
def memprefix(prefix, memories, done):
|
||||||
for memory in memories:
|
for memory in memories:
|
||||||
if memory.huid not in done:
|
if memory.huid not in done:
|
||||||
memory.name_override = prefix + memory.name_override
|
memory.name_override = prefix + memory.name_override
|
||||||
done.add(memory.huid)
|
done.add(memory.huid)
|
||||||
|
|
||||||
|
|
||||||
class AutoCSR:
|
class AutoCSR:
|
||||||
def get_memories(self):
|
def get_memories(self):
|
||||||
try:
|
try:
|
||||||
|
|
|
@ -3,6 +3,7 @@ from migen.fhdl.std import *
|
||||||
from migen.bank.description import *
|
from migen.bank.description import *
|
||||||
from migen.genlib.misc import optree
|
from migen.genlib.misc import optree
|
||||||
|
|
||||||
|
|
||||||
class _EventSource(HUID):
|
class _EventSource(HUID):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
HUID.__init__(self)
|
HUID.__init__(self)
|
||||||
|
@ -11,6 +12,7 @@ class _EventSource(HUID):
|
||||||
self.trigger = Signal() # trigger signal interface to the user design
|
self.trigger = Signal() # trigger signal interface to the user design
|
||||||
self.clear = Signal() # clearing attempt by W1C to pending register, ignored by some event sources
|
self.clear = Signal() # clearing attempt by W1C to pending register, ignored by some event sources
|
||||||
|
|
||||||
|
|
||||||
# set on a positive trigger pulse
|
# set on a positive trigger pulse
|
||||||
class EventSourcePulse(Module, _EventSource):
|
class EventSourcePulse(Module, _EventSource):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
|
@ -21,6 +23,7 @@ class EventSourcePulse(Module, _EventSource):
|
||||||
If(self.trigger, self.pending.eq(1))
|
If(self.trigger, self.pending.eq(1))
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
# set on the falling edge of the trigger, status = trigger
|
# set on the falling edge of the trigger, status = trigger
|
||||||
class EventSourceProcess(Module, _EventSource):
|
class EventSourceProcess(Module, _EventSource):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
|
@ -33,6 +36,7 @@ class EventSourceProcess(Module, _EventSource):
|
||||||
If(~self.trigger & old_trigger, self.pending.eq(1))
|
If(~self.trigger & old_trigger, self.pending.eq(1))
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
# all status set by external trigger
|
# all status set by external trigger
|
||||||
class EventSourceLevel(Module, _EventSource):
|
class EventSourceLevel(Module, _EventSource):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
|
@ -42,6 +46,7 @@ class EventSourceLevel(Module, _EventSource):
|
||||||
self.pending.eq(self.trigger)
|
self.pending.eq(self.trigger)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class EventManager(Module, AutoCSR):
|
class EventManager(Module, AutoCSR):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.irq = Signal()
|
self.irq = Signal()
|
||||||
|
@ -71,6 +76,7 @@ class EventManager(Module, AutoCSR):
|
||||||
raise FinalizeError
|
raise FinalizeError
|
||||||
self.submodules += value
|
self.submodules += value
|
||||||
|
|
||||||
|
|
||||||
class SharedIRQ(Module):
|
class SharedIRQ(Module):
|
||||||
def __init__(self, *event_managers):
|
def __init__(self, *event_managers):
|
||||||
self.irq = Signal()
|
self.irq = Signal()
|
||||||
|
|
|
@ -2,6 +2,7 @@ from migen.fhdl.std import *
|
||||||
from migen.bus import wishbone
|
from migen.bus import wishbone
|
||||||
from migen.bank.bank import GenericBank
|
from migen.bank.bank import GenericBank
|
||||||
|
|
||||||
|
|
||||||
class Bank(GenericBank):
|
class Bank(GenericBank):
|
||||||
def __init__(self, description, bus=None):
|
def __init__(self, description, bus=None):
|
||||||
if bus is None:
|
if bus is None:
|
||||||
|
|
|
@ -11,15 +11,18 @@ _layout = [
|
||||||
("dat_r", "data_width", DIR_S_TO_M)
|
("dat_r", "data_width", DIR_S_TO_M)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Interface(Record):
|
class Interface(Record):
|
||||||
def __init__(self, data_width=8, address_width=14):
|
def __init__(self, data_width=8, address_width=14):
|
||||||
Record.__init__(self, set_layout_parameters(_layout,
|
Record.__init__(self, set_layout_parameters(_layout,
|
||||||
data_width=data_width, address_width=address_width))
|
data_width=data_width, address_width=address_width))
|
||||||
|
|
||||||
|
|
||||||
class Interconnect(Module):
|
class Interconnect(Module):
|
||||||
def __init__(self, master, slaves):
|
def __init__(self, master, slaves):
|
||||||
self.comb += master.connect(*slaves)
|
self.comb += master.connect(*slaves)
|
||||||
|
|
||||||
|
|
||||||
class Initiator(Module):
|
class Initiator(Module):
|
||||||
def __init__(self, generator, bus=None):
|
def __init__(self, generator, bus=None):
|
||||||
self.generator = generator
|
self.generator = generator
|
||||||
|
@ -55,6 +58,7 @@ class Initiator(Module):
|
||||||
selfp.bus.we = 1
|
selfp.bus.we = 1
|
||||||
selfp.bus.dat_w = self.transaction.data
|
selfp.bus.dat_w = self.transaction.data
|
||||||
|
|
||||||
|
|
||||||
class SRAM(Module):
|
class SRAM(Module):
|
||||||
def __init__(self, mem_or_size, address, read_only=None, init=None, bus=None):
|
def __init__(self, mem_or_size, address, read_only=None, init=None, bus=None):
|
||||||
if bus is None:
|
if bus is None:
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from migen.fhdl.std import *
|
from migen.fhdl.std import *
|
||||||
from migen.bus.transactions import *
|
from migen.bus.transactions import *
|
||||||
|
|
||||||
|
|
||||||
def _byte_mask(orig, dat_w, sel):
|
def _byte_mask(orig, dat_w, sel):
|
||||||
r = 0
|
r = 0
|
||||||
shift = 0
|
shift = 0
|
||||||
|
@ -15,6 +16,7 @@ def _byte_mask(orig, dat_w, sel):
|
||||||
shift += 8
|
shift += 8
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
class Initiator(Module):
|
class Initiator(Module):
|
||||||
def __init__(self, generator, mem):
|
def __init__(self, generator, mem):
|
||||||
self.generator = generator
|
self.generator = generator
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
from migen.fhdl.std import *
|
from migen.fhdl.std import *
|
||||||
|
|
||||||
|
|
||||||
class Transaction:
|
class Transaction:
|
||||||
def __init__(self, address, data=0, sel=None, busname=None):
|
def __init__(self, address, data=0, sel=None, busname=None):
|
||||||
self.address = address
|
self.address = address
|
||||||
|
@ -14,8 +15,10 @@ class Transaction:
|
||||||
def __str__(self):
|
def __str__(self):
|
||||||
return "<" + self.__class__.__name__ + " adr:" + hex(self.address) + " dat:" + hex(self.data) + ">"
|
return "<" + self.__class__.__name__ + " adr:" + hex(self.address) + " dat:" + hex(self.data) + ">"
|
||||||
|
|
||||||
|
|
||||||
class TRead(Transaction):
|
class TRead(Transaction):
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class TWrite(Transaction):
|
class TWrite(Transaction):
|
||||||
pass
|
pass
|
||||||
|
|
|
@ -19,16 +19,19 @@ _layout = [
|
||||||
("err", 1, DIR_S_TO_M)
|
("err", 1, DIR_S_TO_M)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class Interface(Record):
|
class Interface(Record):
|
||||||
def __init__(self, data_width=32):
|
def __init__(self, data_width=32):
|
||||||
Record.__init__(self, set_layout_parameters(_layout,
|
Record.__init__(self, set_layout_parameters(_layout,
|
||||||
data_width=data_width,
|
data_width=data_width,
|
||||||
sel_width=data_width//8))
|
sel_width=data_width//8))
|
||||||
|
|
||||||
|
|
||||||
class InterconnectPointToPoint(Module):
|
class InterconnectPointToPoint(Module):
|
||||||
def __init__(self, master, slave):
|
def __init__(self, master, slave):
|
||||||
self.comb += master.connect(slave)
|
self.comb += master.connect(slave)
|
||||||
|
|
||||||
|
|
||||||
class Arbiter(Module):
|
class Arbiter(Module):
|
||||||
def __init__(self, masters, target):
|
def __init__(self, masters, target):
|
||||||
self.submodules.rr = roundrobin.RoundRobin(len(masters))
|
self.submodules.rr = roundrobin.RoundRobin(len(masters))
|
||||||
|
@ -54,6 +57,7 @@ class Arbiter(Module):
|
||||||
reqs = [m.cyc for m in masters]
|
reqs = [m.cyc for m in masters]
|
||||||
self.comb += self.rr.request.eq(Cat(*reqs))
|
self.comb += self.rr.request.eq(Cat(*reqs))
|
||||||
|
|
||||||
|
|
||||||
class Decoder(Module):
|
class Decoder(Module):
|
||||||
# slaves is a list of pairs:
|
# slaves is a list of pairs:
|
||||||
# 0) function that takes the address signal and returns a FHDL expression
|
# 0) function that takes the address signal and returns a FHDL expression
|
||||||
|
@ -94,12 +98,14 @@ class Decoder(Module):
|
||||||
masked = [Replicate(slave_sel_r[i], flen(master.dat_r)) & slaves[i][1].dat_r for i in range(ns)]
|
masked = [Replicate(slave_sel_r[i], flen(master.dat_r)) & slaves[i][1].dat_r for i in range(ns)]
|
||||||
self.comb += master.dat_r.eq(optree("|", masked))
|
self.comb += master.dat_r.eq(optree("|", masked))
|
||||||
|
|
||||||
|
|
||||||
class InterconnectShared(Module):
|
class InterconnectShared(Module):
|
||||||
def __init__(self, masters, slaves, register=False):
|
def __init__(self, masters, slaves, register=False):
|
||||||
shared = Interface()
|
shared = Interface()
|
||||||
self.submodules += Arbiter(masters, shared)
|
self.submodules += Arbiter(masters, shared)
|
||||||
self.submodules += Decoder(shared, slaves, register)
|
self.submodules += Decoder(shared, slaves, register)
|
||||||
|
|
||||||
|
|
||||||
class Crossbar(Module):
|
class Crossbar(Module):
|
||||||
def __init__(self, masters, slaves, register=False):
|
def __init__(self, masters, slaves, register=False):
|
||||||
matches, busses = zip(*slaves)
|
matches, busses = zip(*slaves)
|
||||||
|
@ -112,6 +118,7 @@ class Crossbar(Module):
|
||||||
for column, bus in zip(zip(*access), busses):
|
for column, bus in zip(zip(*access), busses):
|
||||||
self.submodules += Arbiter(column, bus)
|
self.submodules += Arbiter(column, bus)
|
||||||
|
|
||||||
|
|
||||||
class DownConverter(Module):
|
class DownConverter(Module):
|
||||||
# DownConverter splits Wishbone accesses of N bits in M accesses of L bits where:
|
# DownConverter splits Wishbone accesses of N bits in M accesses of L bits where:
|
||||||
# N is the original data-width
|
# N is the original data-width
|
||||||
|
@ -197,6 +204,7 @@ class DownConverter(Module):
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
class Tap(Module):
|
class Tap(Module):
|
||||||
def __init__(self, bus, handler=print):
|
def __init__(self, bus, handler=print):
|
||||||
self.bus = bus
|
self.bus = bus
|
||||||
|
@ -215,6 +223,7 @@ class Tap(Module):
|
||||||
self.handler(transaction)
|
self.handler(transaction)
|
||||||
do_simulation.passive = True
|
do_simulation.passive = True
|
||||||
|
|
||||||
|
|
||||||
class Initiator(Module):
|
class Initiator(Module):
|
||||||
def __init__(self, generator, bus=None):
|
def __init__(self, generator, bus=None):
|
||||||
self.generator = generator
|
self.generator = generator
|
||||||
|
@ -251,6 +260,7 @@ class Initiator(Module):
|
||||||
selfp.bus.cyc = 0
|
selfp.bus.cyc = 0
|
||||||
selfp.bus.stb = 0
|
selfp.bus.stb = 0
|
||||||
|
|
||||||
|
|
||||||
class TargetModel:
|
class TargetModel:
|
||||||
def read(self, address):
|
def read(self, address):
|
||||||
return 0
|
return 0
|
||||||
|
@ -261,6 +271,7 @@ class TargetModel:
|
||||||
def can_ack(self, bus):
|
def can_ack(self, bus):
|
||||||
return True
|
return True
|
||||||
|
|
||||||
|
|
||||||
class Target(Module):
|
class Target(Module):
|
||||||
def __init__(self, model, bus=None):
|
def __init__(self, model, bus=None):
|
||||||
if bus is None:
|
if bus is None:
|
||||||
|
@ -281,6 +292,7 @@ class Target(Module):
|
||||||
bus.ack = 0
|
bus.ack = 0
|
||||||
do_simulation.passive = True
|
do_simulation.passive = True
|
||||||
|
|
||||||
|
|
||||||
class SRAM(Module):
|
class SRAM(Module):
|
||||||
def __init__(self, mem_or_size, read_only=None, init=None, bus=None):
|
def __init__(self, mem_or_size, read_only=None, init=None, bus=None):
|
||||||
if bus is None:
|
if bus is None:
|
||||||
|
|
|
@ -3,6 +3,7 @@ from migen.bus import wishbone
|
||||||
from migen.bus import csr
|
from migen.bus import csr
|
||||||
from migen.genlib.misc import timeline
|
from migen.genlib.misc import timeline
|
||||||
|
|
||||||
|
|
||||||
class WB2CSR(Module):
|
class WB2CSR(Module):
|
||||||
def __init__(self, bus_wishbone=None, bus_csr=None):
|
def __init__(self, bus_wishbone=None, bus_csr=None):
|
||||||
if bus_wishbone is None:
|
if bus_wishbone is None:
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
from migen.fhdl import structure as f
|
from migen.fhdl import structure as f
|
||||||
|
|
||||||
|
|
||||||
def log2_int(n, need_pow2=True):
|
def log2_int(n, need_pow2=True):
|
||||||
l = 1
|
l = 1
|
||||||
r = 0
|
r = 0
|
||||||
|
@ -10,6 +11,7 @@ def log2_int(n, need_pow2=True):
|
||||||
raise ValueError("Not a power of 2")
|
raise ValueError("Not a power of 2")
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def bits_for(n, require_sign_bit=False):
|
def bits_for(n, require_sign_bit=False):
|
||||||
if n > 0:
|
if n > 0:
|
||||||
r = log2_int(n + 1, False)
|
r = log2_int(n + 1, False)
|
||||||
|
@ -20,6 +22,7 @@ def bits_for(n, require_sign_bit=False):
|
||||||
r += 1
|
r += 1
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def value_bits_sign(v):
|
def value_bits_sign(v):
|
||||||
if isinstance(v, bool):
|
if isinstance(v, bool):
|
||||||
return 1, False
|
return 1, False
|
||||||
|
@ -99,6 +102,7 @@ def value_bits_sign(v):
|
||||||
raise TypeError("Can not calculate bit length of {} {}".format(
|
raise TypeError("Can not calculate bit length of {} {}".format(
|
||||||
type(v), v))
|
type(v), v))
|
||||||
|
|
||||||
|
|
||||||
def flen(v):
|
def flen(v):
|
||||||
"""Bit length of an expression
|
"""Bit length of an expression
|
||||||
|
|
||||||
|
@ -120,6 +124,7 @@ def flen(v):
|
||||||
"""
|
"""
|
||||||
return value_bits_sign(v)[0]
|
return value_bits_sign(v)[0]
|
||||||
|
|
||||||
|
|
||||||
def fiter(v):
|
def fiter(v):
|
||||||
"""Bit iterator
|
"""Bit iterator
|
||||||
|
|
||||||
|
@ -146,6 +151,7 @@ def fiter(v):
|
||||||
else:
|
else:
|
||||||
raise TypeError("Can not bit-iterate {} {}".format(type(v), v))
|
raise TypeError("Can not bit-iterate {} {}".format(type(v), v))
|
||||||
|
|
||||||
|
|
||||||
def fslice(v, s):
|
def fslice(v, s):
|
||||||
"""Bit slice
|
"""Bit slice
|
||||||
|
|
||||||
|
@ -180,6 +186,7 @@ def fslice(v, s):
|
||||||
else:
|
else:
|
||||||
raise TypeError("Can not bit-slice {} {}".format(type(v), v))
|
raise TypeError("Can not bit-slice {} {}".format(type(v), v))
|
||||||
|
|
||||||
|
|
||||||
def freversed(v):
|
def freversed(v):
|
||||||
"""Bit reverse
|
"""Bit reverse
|
||||||
|
|
||||||
|
|
|
@ -4,6 +4,7 @@ from migen.fhdl.structure import *
|
||||||
from migen.fhdl.module import Module
|
from migen.fhdl.module import Module
|
||||||
from migen.fhdl.tools import insert_reset, rename_clock_domain
|
from migen.fhdl.tools import insert_reset, rename_clock_domain
|
||||||
|
|
||||||
|
|
||||||
class ModuleTransformer:
|
class ModuleTransformer:
|
||||||
# overload this in derived classes
|
# overload this in derived classes
|
||||||
def transform_instance(self, i):
|
def transform_instance(self, i):
|
||||||
|
@ -51,10 +52,12 @@ class ModuleTransformer:
|
||||||
warnings.warn("deprecated, use the plain transformer", DeprecationWarning, 2)
|
warnings.warn("deprecated, use the plain transformer", DeprecationWarning, 2)
|
||||||
return cls(*args, **kwargs)(i)
|
return cls(*args, **kwargs)(i)
|
||||||
|
|
||||||
|
|
||||||
def DecorateModule(transformer, *args, **kwargs):
|
def DecorateModule(transformer, *args, **kwargs):
|
||||||
warnings.warn("deprecated, use the plain transformer", DeprecationWarning, 2)
|
warnings.warn("deprecated, use the plain transformer", DeprecationWarning, 2)
|
||||||
return transformer.__self__(*args, **kwargs)
|
return transformer.__self__(*args, **kwargs)
|
||||||
|
|
||||||
|
|
||||||
class ControlInserter(ModuleTransformer):
|
class ControlInserter(ModuleTransformer):
|
||||||
control_name = None # override this
|
control_name = None # override this
|
||||||
|
|
||||||
|
@ -84,6 +87,7 @@ class ControlInserter(ModuleTransformer):
|
||||||
for cdn in self.clock_domains]
|
for cdn in self.clock_domains]
|
||||||
self.transform_fragment_insert(i, f, to_insert)
|
self.transform_fragment_insert(i, f, to_insert)
|
||||||
|
|
||||||
|
|
||||||
class CEInserter(ControlInserter):
|
class CEInserter(ControlInserter):
|
||||||
control_name = "ce"
|
control_name = "ce"
|
||||||
|
|
||||||
|
@ -93,6 +97,7 @@ class CEInserter(ControlInserter):
|
||||||
|
|
||||||
InsertCE = CEInserter.adhoc
|
InsertCE = CEInserter.adhoc
|
||||||
|
|
||||||
|
|
||||||
class ResetInserter(ControlInserter):
|
class ResetInserter(ControlInserter):
|
||||||
control_name = "reset"
|
control_name = "reset"
|
||||||
|
|
||||||
|
@ -102,6 +107,7 @@ class ResetInserter(ControlInserter):
|
||||||
|
|
||||||
InsertReset = ResetInserter.adhoc
|
InsertReset = ResetInserter.adhoc
|
||||||
|
|
||||||
|
|
||||||
class ClockDomainsRenamer(ModuleTransformer):
|
class ClockDomainsRenamer(ModuleTransformer):
|
||||||
def __init__(self, cd_remapping):
|
def __init__(self, cd_remapping):
|
||||||
if isinstance(cd_remapping, str):
|
if isinstance(cd_remapping, str):
|
||||||
|
|
|
@ -14,6 +14,7 @@ _Property = namedtuple("_Property", "name value")
|
||||||
_Instance = namedtuple("_Instance", "name cell properties")
|
_Instance = namedtuple("_Instance", "name cell properties")
|
||||||
_NetBranch = namedtuple("_NetBranch", "portname instancename")
|
_NetBranch = namedtuple("_NetBranch", "portname instancename")
|
||||||
|
|
||||||
|
|
||||||
def _write_cells(cells):
|
def _write_cells(cells):
|
||||||
r = ""
|
r = ""
|
||||||
for cell in cells:
|
for cell in cells:
|
||||||
|
@ -32,6 +33,7 @@ def _write_cells(cells):
|
||||||
)"""
|
)"""
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _write_io(ios):
|
def _write_io(ios):
|
||||||
r = ""
|
r = ""
|
||||||
for s in ios:
|
for s in ios:
|
||||||
|
@ -39,6 +41,7 @@ def _write_io(ios):
|
||||||
(port {0.name} (direction {0.direction}))""".format(s)
|
(port {0.name} (direction {0.direction}))""".format(s)
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _write_instantiations(instances, cell_library):
|
def _write_instantiations(instances, cell_library):
|
||||||
instantiations = ""
|
instantiations = ""
|
||||||
for instance in instances:
|
for instance in instances:
|
||||||
|
@ -52,6 +55,7 @@ def _write_instantiations(instances, cell_library):
|
||||||
)"""
|
)"""
|
||||||
return instantiations
|
return instantiations
|
||||||
|
|
||||||
|
|
||||||
def _write_connections(connections):
|
def _write_connections(connections):
|
||||||
r = ""
|
r = ""
|
||||||
for netname, branches in connections.items():
|
for netname, branches in connections.items():
|
||||||
|
@ -66,6 +70,7 @@ def _write_connections(connections):
|
||||||
)"""
|
)"""
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _write_edif(cells, ios, instances, connections, cell_library, design_name, part, vendor):
|
def _write_edif(cells, ios, instances, connections, cell_library, design_name, part, vendor):
|
||||||
r = """(edif {0}
|
r = """(edif {0}
|
||||||
(edifVersion 2 0 0)
|
(edifVersion 2 0 0)
|
||||||
|
@ -105,6 +110,7 @@ def _write_edif(cells, ios, instances, connections, cell_library, design_name, p
|
||||||
|
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _generate_cells(f):
|
def _generate_cells(f):
|
||||||
cell_dict = OrderedDict()
|
cell_dict = OrderedDict()
|
||||||
for special in f.specials:
|
for special in f.specials:
|
||||||
|
@ -130,6 +136,7 @@ def _generate_cells(f):
|
||||||
raise ValueError("EDIF conversion can only handle synthesized fragments")
|
raise ValueError("EDIF conversion can only handle synthesized fragments")
|
||||||
return [_Cell(k, v) for k, v in cell_dict.items()]
|
return [_Cell(k, v) for k, v in cell_dict.items()]
|
||||||
|
|
||||||
|
|
||||||
def _generate_instances(f,ns):
|
def _generate_instances(f,ns):
|
||||||
instances = []
|
instances = []
|
||||||
for special in f.specials:
|
for special in f.specials:
|
||||||
|
@ -151,6 +158,7 @@ def _generate_instances(f,ns):
|
||||||
raise ValueError("EDIF conversion can only handle synthesized fragments")
|
raise ValueError("EDIF conversion can only handle synthesized fragments")
|
||||||
return instances
|
return instances
|
||||||
|
|
||||||
|
|
||||||
def _generate_ios(f, ios, ns):
|
def _generate_ios(f, ios, ns):
|
||||||
outs = list_special_ios(f, False, True, False)
|
outs = list_special_ios(f, False, True, False)
|
||||||
inouts = list_special_ios(f, False, False, True)
|
inouts = list_special_ios(f, False, False, True)
|
||||||
|
@ -160,6 +168,7 @@ def _generate_ios(f, ios, ns):
|
||||||
r.append(_Port(name=ns.get_name(io), direction=direction))
|
r.append(_Port(name=ns.get_name(io), direction=direction))
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _generate_connections(f, ios, ns):
|
def _generate_connections(f, ios, ns):
|
||||||
r = OrderedDict()
|
r = OrderedDict()
|
||||||
for special in f.specials:
|
for special in f.specials:
|
||||||
|
@ -184,6 +193,7 @@ def _generate_connections(f, ios, ns):
|
||||||
r[io].append(_NetBranch(portname=io, instancename=""))
|
r[io].append(_NetBranch(portname=io, instancename=""))
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def convert(f, ios, cell_library, vendor, device, name="top"):
|
def convert(f, ios, cell_library, vendor, device, name="top"):
|
||||||
if not isinstance(f, _Fragment):
|
if not isinstance(f, _Fragment):
|
||||||
f = f.get_fragment()
|
f = f.get_fragment()
|
||||||
|
|
|
@ -7,24 +7,29 @@ from migen.fhdl.structure import _Fragment
|
||||||
from migen.fhdl.tools import rename_clock_domain
|
from migen.fhdl.tools import rename_clock_domain
|
||||||
from migen.sim.upper import gen_sim, proxy_sim
|
from migen.sim.upper import gen_sim, proxy_sim
|
||||||
|
|
||||||
|
|
||||||
class FinalizeError(Exception):
|
class FinalizeError(Exception):
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
def _flat_list(e):
|
def _flat_list(e):
|
||||||
if isinstance(e, collections.Iterable):
|
if isinstance(e, collections.Iterable):
|
||||||
return flat_iteration(e)
|
return flat_iteration(e)
|
||||||
else:
|
else:
|
||||||
return [e]
|
return [e]
|
||||||
|
|
||||||
|
|
||||||
class _ModuleProxy:
|
class _ModuleProxy:
|
||||||
def __init__(self, fm):
|
def __init__(self, fm):
|
||||||
object.__setattr__(self, "_fm", fm)
|
object.__setattr__(self, "_fm", fm)
|
||||||
|
|
||||||
|
|
||||||
class _ModuleComb(_ModuleProxy):
|
class _ModuleComb(_ModuleProxy):
|
||||||
def __iadd__(self, other):
|
def __iadd__(self, other):
|
||||||
self._fm._fragment.comb += _flat_list(other)
|
self._fm._fragment.comb += _flat_list(other)
|
||||||
return self
|
return self
|
||||||
|
|
||||||
|
|
||||||
def _cd_append(d, key, statements):
|
def _cd_append(d, key, statements):
|
||||||
try:
|
try:
|
||||||
l = d[key]
|
l = d[key]
|
||||||
|
@ -33,6 +38,7 @@ def _cd_append(d, key, statements):
|
||||||
d[key] = l
|
d[key] = l
|
||||||
l += _flat_list(statements)
|
l += _flat_list(statements)
|
||||||
|
|
||||||
|
|
||||||
class _ModuleSyncCD:
|
class _ModuleSyncCD:
|
||||||
def __init__(self, fm, cd):
|
def __init__(self, fm, cd):
|
||||||
self._fm = fm
|
self._fm = fm
|
||||||
|
@ -42,6 +48,7 @@ class _ModuleSyncCD:
|
||||||
_cd_append(self._fm._fragment.sync, self._cd, other)
|
_cd_append(self._fm._fragment.sync, self._cd, other)
|
||||||
return self
|
return self
|
||||||
|
|
||||||
|
|
||||||
class _ModuleSync(_ModuleProxy):
|
class _ModuleSync(_ModuleProxy):
|
||||||
def __iadd__(self, other):
|
def __iadd__(self, other):
|
||||||
_cd_append(self._fm._fragment.sync, "sys", other)
|
_cd_append(self._fm._fragment.sync, "sys", other)
|
||||||
|
@ -54,6 +61,7 @@ class _ModuleSync(_ModuleProxy):
|
||||||
if not isinstance(value, _ModuleSyncCD):
|
if not isinstance(value, _ModuleSyncCD):
|
||||||
raise AttributeError("Attempted to assign sync property - use += instead")
|
raise AttributeError("Attempted to assign sync property - use += instead")
|
||||||
|
|
||||||
|
|
||||||
# _ModuleForwardAttr enables user classes to do e.g.:
|
# _ModuleForwardAttr enables user classes to do e.g.:
|
||||||
# self.subm.foobar = SomeModule()
|
# self.subm.foobar = SomeModule()
|
||||||
# and then access the submodule with self.foobar.
|
# and then access the submodule with self.foobar.
|
||||||
|
@ -62,11 +70,13 @@ class _ModuleForwardAttr:
|
||||||
self.__iadd__(value)
|
self.__iadd__(value)
|
||||||
setattr(self._fm, name, value)
|
setattr(self._fm, name, value)
|
||||||
|
|
||||||
|
|
||||||
class _ModuleSpecials(_ModuleProxy, _ModuleForwardAttr):
|
class _ModuleSpecials(_ModuleProxy, _ModuleForwardAttr):
|
||||||
def __iadd__(self, other):
|
def __iadd__(self, other):
|
||||||
self._fm._fragment.specials |= set(_flat_list(other))
|
self._fm._fragment.specials |= set(_flat_list(other))
|
||||||
return self
|
return self
|
||||||
|
|
||||||
|
|
||||||
class _ModuleSubmodules(_ModuleProxy):
|
class _ModuleSubmodules(_ModuleProxy):
|
||||||
def __setattr__(self, name, value):
|
def __setattr__(self, name, value):
|
||||||
self._fm._submodules += [(name, e) for e in _flat_list(value)]
|
self._fm._submodules += [(name, e) for e in _flat_list(value)]
|
||||||
|
@ -76,11 +86,13 @@ class _ModuleSubmodules(_ModuleProxy):
|
||||||
self._fm._submodules += [(None, e) for e in _flat_list(other)]
|
self._fm._submodules += [(None, e) for e in _flat_list(other)]
|
||||||
return self
|
return self
|
||||||
|
|
||||||
|
|
||||||
class _ModuleClockDomains(_ModuleProxy, _ModuleForwardAttr):
|
class _ModuleClockDomains(_ModuleProxy, _ModuleForwardAttr):
|
||||||
def __iadd__(self, other):
|
def __iadd__(self, other):
|
||||||
self._fm._fragment.clock_domains += _flat_list(other)
|
self._fm._fragment.clock_domains += _flat_list(other)
|
||||||
return self
|
return self
|
||||||
|
|
||||||
|
|
||||||
class Module:
|
class Module:
|
||||||
def get_fragment(self):
|
def get_fragment(self):
|
||||||
assert(not self.get_fragment_called)
|
assert(not self.get_fragment_called)
|
||||||
|
|
|
@ -3,6 +3,7 @@ from itertools import combinations
|
||||||
|
|
||||||
from migen.fhdl.structure import *
|
from migen.fhdl.structure import *
|
||||||
|
|
||||||
|
|
||||||
class _Node:
|
class _Node:
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.signal_count = 0
|
self.signal_count = 0
|
||||||
|
@ -11,6 +12,7 @@ class _Node:
|
||||||
self.use_number = False
|
self.use_number = False
|
||||||
self.children = OrderedDict()
|
self.children = OrderedDict()
|
||||||
|
|
||||||
|
|
||||||
def _display_tree(filename, tree):
|
def _display_tree(filename, tree):
|
||||||
from migen.util.treeviz import RenderNode
|
from migen.util.treeviz import RenderNode
|
||||||
|
|
||||||
|
@ -32,6 +34,7 @@ def _display_tree(filename, tree):
|
||||||
top = _to_render_node("top", tree)
|
top = _to_render_node("top", tree)
|
||||||
top.to_svg(filename)
|
top.to_svg(filename)
|
||||||
|
|
||||||
|
|
||||||
def _build_tree(signals, basic_tree=None):
|
def _build_tree(signals, basic_tree=None):
|
||||||
root = _Node()
|
root = _Node()
|
||||||
for signal in signals:
|
for signal in signals:
|
||||||
|
@ -60,6 +63,7 @@ def _build_tree(signals, basic_tree=None):
|
||||||
current.signal_count += 1
|
current.signal_count += 1
|
||||||
return root
|
return root
|
||||||
|
|
||||||
|
|
||||||
def _set_use_name(node, node_name=""):
|
def _set_use_name(node, node_name=""):
|
||||||
cnames = [(k, _set_use_name(v, k)) for k, v in node.children.items()]
|
cnames = [(k, _set_use_name(v, k)) for k, v in node.children.items()]
|
||||||
for (c1_prefix, c1_names), (c2_prefix, c2_names) in combinations(cnames, 2):
|
for (c1_prefix, c1_names), (c2_prefix, c2_names) in combinations(cnames, 2):
|
||||||
|
@ -80,6 +84,7 @@ def _set_use_name(node, node_name=""):
|
||||||
|
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _name_signal(tree, signal):
|
def _name_signal(tree, signal):
|
||||||
elements = []
|
elements = []
|
||||||
treepos = tree
|
treepos = tree
|
||||||
|
@ -97,9 +102,11 @@ def _name_signal(tree, signal):
|
||||||
elements.append(elname)
|
elements.append(elname)
|
||||||
return "_".join(elements)
|
return "_".join(elements)
|
||||||
|
|
||||||
|
|
||||||
def _build_pnd_from_tree(tree, signals):
|
def _build_pnd_from_tree(tree, signals):
|
||||||
return dict((signal, _name_signal(tree, signal)) for signal in signals)
|
return dict((signal, _name_signal(tree, signal)) for signal in signals)
|
||||||
|
|
||||||
|
|
||||||
def _invert_pnd(pnd):
|
def _invert_pnd(pnd):
|
||||||
inv_pnd = dict()
|
inv_pnd = dict()
|
||||||
for k, v in pnd.items():
|
for k, v in pnd.items():
|
||||||
|
@ -107,6 +114,7 @@ def _invert_pnd(pnd):
|
||||||
inv_pnd[v].append(k)
|
inv_pnd[v].append(k)
|
||||||
return inv_pnd
|
return inv_pnd
|
||||||
|
|
||||||
|
|
||||||
def _list_conflicting_signals(pnd):
|
def _list_conflicting_signals(pnd):
|
||||||
inv_pnd = _invert_pnd(pnd)
|
inv_pnd = _invert_pnd(pnd)
|
||||||
r = set()
|
r = set()
|
||||||
|
@ -115,6 +123,7 @@ def _list_conflicting_signals(pnd):
|
||||||
r.update(v)
|
r.update(v)
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _set_use_number(tree, signals):
|
def _set_use_number(tree, signals):
|
||||||
for signal in signals:
|
for signal in signals:
|
||||||
current = tree
|
current = tree
|
||||||
|
@ -124,6 +133,7 @@ def _set_use_number(tree, signals):
|
||||||
|
|
||||||
_debug = False
|
_debug = False
|
||||||
|
|
||||||
|
|
||||||
def _build_pnd_for_group(group_n, signals):
|
def _build_pnd_for_group(group_n, signals):
|
||||||
basic_tree = _build_tree(signals)
|
basic_tree = _build_tree(signals)
|
||||||
_set_use_name(basic_tree)
|
_set_use_name(basic_tree)
|
||||||
|
@ -161,6 +171,7 @@ def _build_pnd_for_group(group_n, signals):
|
||||||
|
|
||||||
return pnd
|
return pnd
|
||||||
|
|
||||||
|
|
||||||
def _build_signal_groups(signals):
|
def _build_signal_groups(signals):
|
||||||
r = []
|
r = []
|
||||||
for signal in signals:
|
for signal in signals:
|
||||||
|
@ -181,6 +192,7 @@ def _build_signal_groups(signals):
|
||||||
s1 -= s2
|
s1 -= s2
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _build_pnd(signals):
|
def _build_pnd(signals):
|
||||||
groups = _build_signal_groups(signals)
|
groups = _build_signal_groups(signals)
|
||||||
gpnds = [_build_pnd_for_group(n, gsignals) for n, gsignals in enumerate(groups)]
|
gpnds = [_build_pnd_for_group(n, gsignals) for n, gsignals in enumerate(groups)]
|
||||||
|
@ -199,6 +211,7 @@ def _build_pnd(signals):
|
||||||
|
|
||||||
return pnd
|
return pnd
|
||||||
|
|
||||||
|
|
||||||
def build_namespace(signals):
|
def build_namespace(signals):
|
||||||
pnd = _build_pnd(signals)
|
pnd = _build_pnd(signals)
|
||||||
ns = Namespace(pnd)
|
ns = Namespace(pnd)
|
||||||
|
@ -208,6 +221,7 @@ def build_namespace(signals):
|
||||||
ns.get_name(signal)
|
ns.get_name(signal)
|
||||||
return ns
|
return ns
|
||||||
|
|
||||||
|
|
||||||
class Namespace:
|
class Namespace:
|
||||||
def __init__(self, pnd):
|
def __init__(self, pnd):
|
||||||
self.counts = {}
|
self.counts = {}
|
||||||
|
|
|
@ -3,6 +3,7 @@ from migen.fhdl.specials import _MemoryPort
|
||||||
from migen.fhdl.decorators import ModuleTransformer
|
from migen.fhdl.decorators import ModuleTransformer
|
||||||
from migen.util.misc import gcd_multiple
|
from migen.util.misc import gcd_multiple
|
||||||
|
|
||||||
|
|
||||||
class FullMemoryWE(ModuleTransformer):
|
class FullMemoryWE(ModuleTransformer):
|
||||||
def transform_fragment(self, i, f):
|
def transform_fragment(self, i, f):
|
||||||
newspecials = set()
|
newspecials = set()
|
||||||
|
|
|
@ -6,6 +6,7 @@ from migen.fhdl.tools import *
|
||||||
from migen.fhdl.tracer import get_obj_var_name
|
from migen.fhdl.tracer import get_obj_var_name
|
||||||
from migen.fhdl.verilog import _printexpr as verilog_printexpr
|
from migen.fhdl.verilog import _printexpr as verilog_printexpr
|
||||||
|
|
||||||
|
|
||||||
class Special(HUID):
|
class Special(HUID):
|
||||||
def iter_expressions(self):
|
def iter_expressions(self):
|
||||||
for x in []:
|
for x in []:
|
||||||
|
@ -31,6 +32,7 @@ class Special(HUID):
|
||||||
r.update(signals)
|
r.update(signals)
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
class Tristate(Special):
|
class Tristate(Special):
|
||||||
def __init__(self, target, o, oe, i=None):
|
def __init__(self, target, o, oe, i=None):
|
||||||
Special.__init__(self)
|
Special.__init__(self)
|
||||||
|
@ -60,6 +62,7 @@ class Tristate(Special):
|
||||||
r += "\n"
|
r += "\n"
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
class TSTriple:
|
class TSTriple:
|
||||||
def __init__(self, bits_sign=None, min=None, max=None, reset_o=0, reset_oe=0):
|
def __init__(self, bits_sign=None, min=None, max=None, reset_o=0, reset_oe=0):
|
||||||
self.o = Signal(bits_sign, min=min, max=max, reset=reset_o)
|
self.o = Signal(bits_sign, min=min, max=max, reset=reset_o)
|
||||||
|
@ -69,6 +72,7 @@ class TSTriple:
|
||||||
def get_tristate(self, target):
|
def get_tristate(self, target):
|
||||||
return Tristate(target, self.o, self.oe, self.i)
|
return Tristate(target, self.o, self.oe, self.i)
|
||||||
|
|
||||||
|
|
||||||
class Instance(Special):
|
class Instance(Special):
|
||||||
class _IO:
|
class _IO:
|
||||||
def __init__(self, name, expr=None):
|
def __init__(self, name, expr=None):
|
||||||
|
@ -169,6 +173,7 @@ class Instance(Special):
|
||||||
|
|
||||||
(READ_FIRST, WRITE_FIRST, NO_CHANGE) = range(3)
|
(READ_FIRST, WRITE_FIRST, NO_CHANGE) = range(3)
|
||||||
|
|
||||||
|
|
||||||
class _MemoryPort(Special):
|
class _MemoryPort(Special):
|
||||||
def __init__(self, adr, dat_r, we=None, dat_w=None,
|
def __init__(self, adr, dat_r, we=None, dat_w=None,
|
||||||
async_read=False, re=None, we_granularity=0, mode=WRITE_FIRST,
|
async_read=False, re=None, we_granularity=0, mode=WRITE_FIRST,
|
||||||
|
@ -201,6 +206,7 @@ class _MemoryPort(Special):
|
||||||
def emit_verilog(port, ns, add_data_file):
|
def emit_verilog(port, ns, add_data_file):
|
||||||
return "" # done by parent Memory object
|
return "" # done by parent Memory object
|
||||||
|
|
||||||
|
|
||||||
class Memory(Special):
|
class Memory(Special):
|
||||||
def __init__(self, width, depth, init=None, name=None):
|
def __init__(self, width, depth, init=None, name=None):
|
||||||
Special.__init__(self)
|
Special.__init__(self)
|
||||||
|
@ -319,6 +325,7 @@ class Memory(Special):
|
||||||
|
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
class SynthesisDirective(Special):
|
class SynthesisDirective(Special):
|
||||||
def __init__(self, template, **signals):
|
def __init__(self, template, **signals):
|
||||||
Special.__init__(self)
|
Special.__init__(self)
|
||||||
|
|
|
@ -4,6 +4,7 @@ from collections import defaultdict
|
||||||
from migen.fhdl import tracer
|
from migen.fhdl import tracer
|
||||||
from migen.util.misc import flat_iteration
|
from migen.util.misc import flat_iteration
|
||||||
|
|
||||||
|
|
||||||
class HUID:
|
class HUID:
|
||||||
__next_uid = 0
|
__next_uid = 0
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
|
@ -13,6 +14,7 @@ class HUID:
|
||||||
def __hash__(self):
|
def __hash__(self):
|
||||||
return self.huid
|
return self.huid
|
||||||
|
|
||||||
|
|
||||||
class Value(HUID):
|
class Value(HUID):
|
||||||
"""Base class for operands
|
"""Base class for operands
|
||||||
|
|
||||||
|
@ -116,12 +118,14 @@ class Value(HUID):
|
||||||
def __hash__(self):
|
def __hash__(self):
|
||||||
return HUID.__hash__(self)
|
return HUID.__hash__(self)
|
||||||
|
|
||||||
|
|
||||||
class _Operator(Value):
|
class _Operator(Value):
|
||||||
def __init__(self, op, operands):
|
def __init__(self, op, operands):
|
||||||
Value.__init__(self)
|
Value.__init__(self)
|
||||||
self.op = op
|
self.op = op
|
||||||
self.operands = operands
|
self.operands = operands
|
||||||
|
|
||||||
|
|
||||||
def Mux(sel, val1, val0):
|
def Mux(sel, val1, val0):
|
||||||
"""Multiplex between two values
|
"""Multiplex between two values
|
||||||
|
|
||||||
|
@ -141,6 +145,7 @@ def Mux(sel, val1, val0):
|
||||||
"""
|
"""
|
||||||
return _Operator("m", [sel, val1, val0])
|
return _Operator("m", [sel, val1, val0])
|
||||||
|
|
||||||
|
|
||||||
class _Slice(Value):
|
class _Slice(Value):
|
||||||
def __init__(self, value, start, stop):
|
def __init__(self, value, start, stop):
|
||||||
Value.__init__(self)
|
Value.__init__(self)
|
||||||
|
@ -148,6 +153,7 @@ class _Slice(Value):
|
||||||
self.start = start
|
self.start = start
|
||||||
self.stop = stop
|
self.stop = stop
|
||||||
|
|
||||||
|
|
||||||
class Cat(Value):
|
class Cat(Value):
|
||||||
"""Concatenate values
|
"""Concatenate values
|
||||||
|
|
||||||
|
@ -176,6 +182,7 @@ class Cat(Value):
|
||||||
Value.__init__(self)
|
Value.__init__(self)
|
||||||
self.l = list(flat_iteration(args))
|
self.l = list(flat_iteration(args))
|
||||||
|
|
||||||
|
|
||||||
class Replicate(Value):
|
class Replicate(Value):
|
||||||
"""Replicate a value
|
"""Replicate a value
|
||||||
|
|
||||||
|
@ -201,6 +208,7 @@ class Replicate(Value):
|
||||||
self.v = v
|
self.v = v
|
||||||
self.n = n
|
self.n = n
|
||||||
|
|
||||||
|
|
||||||
class Signal(Value):
|
class Signal(Value):
|
||||||
"""A `Value` that can change
|
"""A `Value` that can change
|
||||||
|
|
||||||
|
@ -292,6 +300,7 @@ class Signal(Value):
|
||||||
from migen.fhdl.bitcontainer import value_bits_sign
|
from migen.fhdl.bitcontainer import value_bits_sign
|
||||||
return cls(bits_sign=value_bits_sign(other), **kwargs)
|
return cls(bits_sign=value_bits_sign(other), **kwargs)
|
||||||
|
|
||||||
|
|
||||||
class ClockSignal(Value):
|
class ClockSignal(Value):
|
||||||
"""Clock signal for a given clock domain
|
"""Clock signal for a given clock domain
|
||||||
|
|
||||||
|
@ -307,6 +316,7 @@ class ClockSignal(Value):
|
||||||
Value.__init__(self)
|
Value.__init__(self)
|
||||||
self.cd = cd
|
self.cd = cd
|
||||||
|
|
||||||
|
|
||||||
class ResetSignal(Value):
|
class ResetSignal(Value):
|
||||||
"""Reset signal for a given clock domain
|
"""Reset signal for a given clock domain
|
||||||
|
|
||||||
|
@ -324,11 +334,13 @@ class ResetSignal(Value):
|
||||||
|
|
||||||
# statements
|
# statements
|
||||||
|
|
||||||
|
|
||||||
class _Assign:
|
class _Assign:
|
||||||
def __init__(self, l, r):
|
def __init__(self, l, r):
|
||||||
self.l = l
|
self.l = l
|
||||||
self.r = r
|
self.r = r
|
||||||
|
|
||||||
|
|
||||||
class If:
|
class If:
|
||||||
"""Conditional execution of statements
|
"""Conditional execution of statements
|
||||||
|
|
||||||
|
@ -383,6 +395,7 @@ class If:
|
||||||
_insert_else(self, [If(cond, *t)])
|
_insert_else(self, [If(cond, *t)])
|
||||||
return self
|
return self
|
||||||
|
|
||||||
|
|
||||||
def _insert_else(obj, clause):
|
def _insert_else(obj, clause):
|
||||||
o = obj
|
o = obj
|
||||||
while o.f:
|
while o.f:
|
||||||
|
@ -391,6 +404,7 @@ def _insert_else(obj, clause):
|
||||||
o = o.f[0]
|
o = o.f[0]
|
||||||
o.f = clause
|
o.f = clause
|
||||||
|
|
||||||
|
|
||||||
class Case:
|
class Case:
|
||||||
"""Case/Switch statement
|
"""Case/Switch statement
|
||||||
|
|
||||||
|
@ -440,6 +454,7 @@ class Case:
|
||||||
|
|
||||||
# arrays
|
# arrays
|
||||||
|
|
||||||
|
|
||||||
class _ArrayProxy(Value):
|
class _ArrayProxy(Value):
|
||||||
def __init__(self, choices, key):
|
def __init__(self, choices, key):
|
||||||
self.choices = choices
|
self.choices = choices
|
||||||
|
@ -453,6 +468,7 @@ class _ArrayProxy(Value):
|
||||||
return _ArrayProxy([choice.__getitem__(key) for choice in self.choices],
|
return _ArrayProxy([choice.__getitem__(key) for choice in self.choices],
|
||||||
self.key)
|
self.key)
|
||||||
|
|
||||||
|
|
||||||
class Array(list):
|
class Array(list):
|
||||||
"""Addressable multiplexer
|
"""Addressable multiplexer
|
||||||
|
|
||||||
|
@ -488,6 +504,7 @@ class Array(list):
|
||||||
else:
|
else:
|
||||||
return list.__getitem__(self, key)
|
return list.__getitem__(self, key)
|
||||||
|
|
||||||
|
|
||||||
class ClockDomain:
|
class ClockDomain:
|
||||||
"""Synchronous domain
|
"""Synchronous domain
|
||||||
|
|
||||||
|
@ -537,6 +554,7 @@ class ClockDomain:
|
||||||
if self.rst is not None:
|
if self.rst is not None:
|
||||||
self.rst.name_override = new_name + "_rst"
|
self.rst.name_override = new_name + "_rst"
|
||||||
|
|
||||||
|
|
||||||
class _ClockDomainList(list):
|
class _ClockDomainList(list):
|
||||||
def __getitem__(self, key):
|
def __getitem__(self, key):
|
||||||
if isinstance(key, str):
|
if isinstance(key, str):
|
||||||
|
@ -549,9 +567,11 @@ class _ClockDomainList(list):
|
||||||
|
|
||||||
(SPECIAL_INPUT, SPECIAL_OUTPUT, SPECIAL_INOUT) = range(3)
|
(SPECIAL_INPUT, SPECIAL_OUTPUT, SPECIAL_INOUT) = range(3)
|
||||||
|
|
||||||
|
|
||||||
class StopSimulation(Exception):
|
class StopSimulation(Exception):
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class _Fragment:
|
class _Fragment:
|
||||||
def __init__(self, comb=None, sync=None, specials=None, clock_domains=None, sim=None):
|
def __init__(self, comb=None, sync=None, specials=None, clock_domains=None, sim=None):
|
||||||
if comb is None: comb = []
|
if comb is None: comb = []
|
||||||
|
|
|
@ -4,6 +4,7 @@ from migen.fhdl.visit import NodeVisitor, NodeTransformer
|
||||||
from migen.fhdl.bitcontainer import value_bits_sign
|
from migen.fhdl.bitcontainer import value_bits_sign
|
||||||
from migen.util.misc import flat_iteration
|
from migen.util.misc import flat_iteration
|
||||||
|
|
||||||
|
|
||||||
class _SignalLister(NodeVisitor):
|
class _SignalLister(NodeVisitor):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.output_list = set()
|
self.output_list = set()
|
||||||
|
@ -11,6 +12,7 @@ class _SignalLister(NodeVisitor):
|
||||||
def visit_Signal(self, node):
|
def visit_Signal(self, node):
|
||||||
self.output_list.add(node)
|
self.output_list.add(node)
|
||||||
|
|
||||||
|
|
||||||
class _TargetLister(NodeVisitor):
|
class _TargetLister(NodeVisitor):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.output_list = set()
|
self.output_list = set()
|
||||||
|
@ -29,20 +31,24 @@ class _TargetLister(NodeVisitor):
|
||||||
for choice in node.choices:
|
for choice in node.choices:
|
||||||
self.visit(choice)
|
self.visit(choice)
|
||||||
|
|
||||||
|
|
||||||
def list_signals(node):
|
def list_signals(node):
|
||||||
lister = _SignalLister()
|
lister = _SignalLister()
|
||||||
lister.visit(node)
|
lister.visit(node)
|
||||||
return lister.output_list
|
return lister.output_list
|
||||||
|
|
||||||
|
|
||||||
def list_targets(node):
|
def list_targets(node):
|
||||||
lister = _TargetLister()
|
lister = _TargetLister()
|
||||||
lister.visit(node)
|
lister.visit(node)
|
||||||
return lister.output_list
|
return lister.output_list
|
||||||
|
|
||||||
|
|
||||||
def _resort_statements(ol):
|
def _resort_statements(ol):
|
||||||
return [statement for i, statement in
|
return [statement for i, statement in
|
||||||
sorted(ol, key=lambda x: x[0])]
|
sorted(ol, key=lambda x: x[0])]
|
||||||
|
|
||||||
|
|
||||||
def group_by_targets(sl):
|
def group_by_targets(sl):
|
||||||
groups = []
|
groups = []
|
||||||
seen = set()
|
seen = set()
|
||||||
|
@ -63,12 +69,14 @@ def group_by_targets(sl):
|
||||||
return [(targets, _resort_statements(stmts))
|
return [(targets, _resort_statements(stmts))
|
||||||
for targets, stmts in groups]
|
for targets, stmts in groups]
|
||||||
|
|
||||||
|
|
||||||
def list_special_ios(f, ins, outs, inouts):
|
def list_special_ios(f, ins, outs, inouts):
|
||||||
r = set()
|
r = set()
|
||||||
for special in f.specials:
|
for special in f.specials:
|
||||||
r |= special.list_ios(ins, outs, inouts)
|
r |= special.list_ios(ins, outs, inouts)
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
class _ClockDomainLister(NodeVisitor):
|
class _ClockDomainLister(NodeVisitor):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.clock_domains = set()
|
self.clock_domains = set()
|
||||||
|
@ -84,11 +92,13 @@ class _ClockDomainLister(NodeVisitor):
|
||||||
self.clock_domains.add(clockname)
|
self.clock_domains.add(clockname)
|
||||||
self.visit(statements)
|
self.visit(statements)
|
||||||
|
|
||||||
|
|
||||||
def list_clock_domains_expr(f):
|
def list_clock_domains_expr(f):
|
||||||
cdl = _ClockDomainLister()
|
cdl = _ClockDomainLister()
|
||||||
cdl.visit(f)
|
cdl.visit(f)
|
||||||
return cdl.clock_domains
|
return cdl.clock_domains
|
||||||
|
|
||||||
|
|
||||||
def list_clock_domains(f):
|
def list_clock_domains(f):
|
||||||
r = list_clock_domains_expr(f)
|
r = list_clock_domains_expr(f)
|
||||||
for special in f.specials:
|
for special in f.specials:
|
||||||
|
@ -97,6 +107,7 @@ def list_clock_domains(f):
|
||||||
r.add(cd.name)
|
r.add(cd.name)
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def is_variable(node):
|
def is_variable(node):
|
||||||
if isinstance(node, Signal):
|
if isinstance(node, Signal):
|
||||||
return node.variable
|
return node.variable
|
||||||
|
@ -112,13 +123,16 @@ def is_variable(node):
|
||||||
else:
|
else:
|
||||||
raise TypeError
|
raise TypeError
|
||||||
|
|
||||||
|
|
||||||
def generate_reset(rst, sl):
|
def generate_reset(rst, sl):
|
||||||
targets = list_targets(sl)
|
targets = list_targets(sl)
|
||||||
return [t.eq(t.reset) for t in sorted(targets, key=lambda x: x.huid)]
|
return [t.eq(t.reset) for t in sorted(targets, key=lambda x: x.huid)]
|
||||||
|
|
||||||
|
|
||||||
def insert_reset(rst, sl):
|
def insert_reset(rst, sl):
|
||||||
return [If(rst, *generate_reset(rst, sl)).Else(*sl)]
|
return [If(rst, *generate_reset(rst, sl)).Else(*sl)]
|
||||||
|
|
||||||
|
|
||||||
def insert_resets(f):
|
def insert_resets(f):
|
||||||
newsync = dict()
|
newsync = dict()
|
||||||
for k, v in f.sync.items():
|
for k, v in f.sync.items():
|
||||||
|
@ -128,6 +142,7 @@ def insert_resets(f):
|
||||||
newsync[k] = v
|
newsync[k] = v
|
||||||
f.sync = newsync
|
f.sync = newsync
|
||||||
|
|
||||||
|
|
||||||
class _Lowerer(NodeTransformer):
|
class _Lowerer(NodeTransformer):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.target_context = False
|
self.target_context = False
|
||||||
|
@ -149,6 +164,7 @@ class _Lowerer(NodeTransformer):
|
||||||
self.target_context, self.extra_stmts = old_target_context, old_extra_stmts
|
self.target_context, self.extra_stmts = old_target_context, old_extra_stmts
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
# Basics are FHDL structure elements that back-ends are not required to support
|
# Basics are FHDL structure elements that back-ends are not required to support
|
||||||
# but can be expressed in terms of other elements (lowered) before conversion.
|
# but can be expressed in terms of other elements (lowered) before conversion.
|
||||||
class _BasicLowerer(_Lowerer):
|
class _BasicLowerer(_Lowerer):
|
||||||
|
@ -177,6 +193,7 @@ class _BasicLowerer(_Lowerer):
|
||||||
def visit_ResetSignal(self, node):
|
def visit_ResetSignal(self, node):
|
||||||
return self.clock_domains[node.cd].rst
|
return self.clock_domains[node.cd].rst
|
||||||
|
|
||||||
|
|
||||||
class _ComplexSliceLowerer(_Lowerer):
|
class _ComplexSliceLowerer(_Lowerer):
|
||||||
def visit_Slice(self, node):
|
def visit_Slice(self, node):
|
||||||
if not isinstance(node.value, Signal):
|
if not isinstance(node.value, Signal):
|
||||||
|
@ -189,6 +206,7 @@ class _ComplexSliceLowerer(_Lowerer):
|
||||||
node = _Slice(slice_proxy, node.start, node.stop)
|
node = _Slice(slice_proxy, node.start, node.stop)
|
||||||
return NodeTransformer.visit_Slice(self, node)
|
return NodeTransformer.visit_Slice(self, node)
|
||||||
|
|
||||||
|
|
||||||
def _apply_lowerer(l, f):
|
def _apply_lowerer(l, f):
|
||||||
f = l.visit(f)
|
f = l.visit(f)
|
||||||
f.comb += l.comb
|
f.comb += l.comb
|
||||||
|
@ -208,12 +226,15 @@ def _apply_lowerer(l, f):
|
||||||
|
|
||||||
return f
|
return f
|
||||||
|
|
||||||
|
|
||||||
def lower_basics(f):
|
def lower_basics(f):
|
||||||
return _apply_lowerer(_BasicLowerer(f.clock_domains), f)
|
return _apply_lowerer(_BasicLowerer(f.clock_domains), f)
|
||||||
|
|
||||||
|
|
||||||
def lower_complex_slices(f):
|
def lower_complex_slices(f):
|
||||||
return _apply_lowerer(_ComplexSliceLowerer(), f)
|
return _apply_lowerer(_ComplexSliceLowerer(), f)
|
||||||
|
|
||||||
|
|
||||||
class _ClockDomainRenamer(NodeVisitor):
|
class _ClockDomainRenamer(NodeVisitor):
|
||||||
def __init__(self, old, new):
|
def __init__(self, old, new):
|
||||||
self.old = old
|
self.old = old
|
||||||
|
@ -227,10 +248,12 @@ class _ClockDomainRenamer(NodeVisitor):
|
||||||
if node.cd == self.old:
|
if node.cd == self.old:
|
||||||
node.cd = self.new
|
node.cd = self.new
|
||||||
|
|
||||||
|
|
||||||
def rename_clock_domain_expr(f, old, new):
|
def rename_clock_domain_expr(f, old, new):
|
||||||
cdr = _ClockDomainRenamer(old, new)
|
cdr = _ClockDomainRenamer(old, new)
|
||||||
cdr.visit(f)
|
cdr.visit(f)
|
||||||
|
|
||||||
|
|
||||||
def rename_clock_domain(f, old, new):
|
def rename_clock_domain(f, old, new):
|
||||||
rename_clock_domain_expr(f, old, new)
|
rename_clock_domain_expr(f, old, new)
|
||||||
if old in f.sync:
|
if old in f.sync:
|
||||||
|
|
|
@ -2,6 +2,7 @@ import inspect
|
||||||
from opcode import opname
|
from opcode import opname
|
||||||
from collections import defaultdict
|
from collections import defaultdict
|
||||||
|
|
||||||
|
|
||||||
def get_var_name(frame):
|
def get_var_name(frame):
|
||||||
code = frame.f_code
|
code = frame.f_code
|
||||||
call_index = frame.f_lasti
|
call_index = frame.f_lasti
|
||||||
|
@ -29,11 +30,13 @@ def get_var_name(frame):
|
||||||
else:
|
else:
|
||||||
return None
|
return None
|
||||||
|
|
||||||
|
|
||||||
def remove_underscore(s):
|
def remove_underscore(s):
|
||||||
if len(s) > 2 and s[0] == "_" and s[1] != "_":
|
if len(s) > 2 and s[0] == "_" and s[1] != "_":
|
||||||
s = s[1:]
|
s = s[1:]
|
||||||
return s
|
return s
|
||||||
|
|
||||||
|
|
||||||
def get_obj_var_name(override=None, default=None):
|
def get_obj_var_name(override=None, default=None):
|
||||||
if override:
|
if override:
|
||||||
return override
|
return override
|
||||||
|
@ -55,12 +58,14 @@ def get_obj_var_name(override=None, default=None):
|
||||||
name_to_idx = defaultdict(int)
|
name_to_idx = defaultdict(int)
|
||||||
classname_to_objs = dict()
|
classname_to_objs = dict()
|
||||||
|
|
||||||
|
|
||||||
def index_id(l, obj):
|
def index_id(l, obj):
|
||||||
for n, e in enumerate(l):
|
for n, e in enumerate(l):
|
||||||
if id(e) == id(obj):
|
if id(e) == id(obj):
|
||||||
return n
|
return n
|
||||||
raise ValueError
|
raise ValueError
|
||||||
|
|
||||||
|
|
||||||
def trace_back(varname=None):
|
def trace_back(varname=None):
|
||||||
l = []
|
l = []
|
||||||
frame = inspect.currentframe().f_back.f_back
|
frame = inspect.currentframe().f_back.f_back
|
||||||
|
|
|
@ -8,6 +8,7 @@ from migen.fhdl.bitcontainer import bits_for, flen
|
||||||
from migen.fhdl.namer import Namespace, build_namespace
|
from migen.fhdl.namer import Namespace, build_namespace
|
||||||
from migen.fhdl.conv_output import ConvOutput
|
from migen.fhdl.conv_output import ConvOutput
|
||||||
|
|
||||||
|
|
||||||
def _printsig(ns, s):
|
def _printsig(ns, s):
|
||||||
if s.signed:
|
if s.signed:
|
||||||
n = "signed "
|
n = "signed "
|
||||||
|
@ -18,6 +19,7 @@ def _printsig(ns, s):
|
||||||
n += ns.get_name(s)
|
n += ns.get_name(s)
|
||||||
return n
|
return n
|
||||||
|
|
||||||
|
|
||||||
def _printintbool(node):
|
def _printintbool(node):
|
||||||
if isinstance(node, bool):
|
if isinstance(node, bool):
|
||||||
if node:
|
if node:
|
||||||
|
@ -33,6 +35,7 @@ def _printintbool(node):
|
||||||
else:
|
else:
|
||||||
raise TypeError
|
raise TypeError
|
||||||
|
|
||||||
|
|
||||||
def _printexpr(ns, node):
|
def _printexpr(ns, node):
|
||||||
if isinstance(node, (int, bool)):
|
if isinstance(node, (int, bool)):
|
||||||
return _printintbool(node)
|
return _printintbool(node)
|
||||||
|
@ -96,6 +99,7 @@ def _printexpr(ns, node):
|
||||||
|
|
||||||
(_AT_BLOCKING, _AT_NONBLOCKING, _AT_SIGNAL) = range(3)
|
(_AT_BLOCKING, _AT_NONBLOCKING, _AT_SIGNAL) = range(3)
|
||||||
|
|
||||||
|
|
||||||
def _printnode(ns, at, level, node):
|
def _printnode(ns, at, level, node):
|
||||||
if node is None:
|
if node is None:
|
||||||
return ""
|
return ""
|
||||||
|
@ -138,6 +142,7 @@ def _printnode(ns, at, level, node):
|
||||||
else:
|
else:
|
||||||
raise TypeError("Node of unrecognized type: "+str(type(node)))
|
raise TypeError("Node of unrecognized type: "+str(type(node)))
|
||||||
|
|
||||||
|
|
||||||
def _list_comb_wires(f):
|
def _list_comb_wires(f):
|
||||||
r = set()
|
r = set()
|
||||||
groups = group_by_targets(f.comb)
|
groups = group_by_targets(f.comb)
|
||||||
|
@ -146,6 +151,7 @@ def _list_comb_wires(f):
|
||||||
r |= g[0]
|
r |= g[0]
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _printheader(f, ios, name, ns):
|
def _printheader(f, ios, name, ns):
|
||||||
sigs = list_signals(f) | list_special_ios(f, True, True, True)
|
sigs = list_signals(f) | list_special_ios(f, True, True, True)
|
||||||
special_outs = list_special_ios(f, False, True, True)
|
special_outs = list_special_ios(f, False, True, True)
|
||||||
|
@ -180,6 +186,7 @@ def _printheader(f, ios, name, ns):
|
||||||
r += "\n"
|
r += "\n"
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _printcomb(f, ns, display_run):
|
def _printcomb(f, ns, display_run):
|
||||||
r = ""
|
r = ""
|
||||||
if f.comb:
|
if f.comb:
|
||||||
|
@ -217,6 +224,7 @@ def _printcomb(f, ns, display_run):
|
||||||
r += "\n"
|
r += "\n"
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _printsync(f, ns):
|
def _printsync(f, ns):
|
||||||
r = ""
|
r = ""
|
||||||
for k, v in sorted(f.sync.items(), key=itemgetter(0)):
|
for k, v in sorted(f.sync.items(), key=itemgetter(0)):
|
||||||
|
@ -225,6 +233,7 @@ def _printsync(f, ns):
|
||||||
r += "end\n\n"
|
r += "end\n\n"
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def _call_special_classmethod(overrides, obj, method, *args, **kwargs):
|
def _call_special_classmethod(overrides, obj, method, *args, **kwargs):
|
||||||
cl = obj.__class__
|
cl = obj.__class__
|
||||||
if cl in overrides:
|
if cl in overrides:
|
||||||
|
@ -234,6 +243,7 @@ def _call_special_classmethod(overrides, obj, method, *args, **kwargs):
|
||||||
else:
|
else:
|
||||||
return None
|
return None
|
||||||
|
|
||||||
|
|
||||||
def _lower_specials_step(overrides, specials):
|
def _lower_specials_step(overrides, specials):
|
||||||
f = _Fragment()
|
f = _Fragment()
|
||||||
lowered_specials = set()
|
lowered_specials = set()
|
||||||
|
@ -244,6 +254,7 @@ def _lower_specials_step(overrides, specials):
|
||||||
lowered_specials.add(special)
|
lowered_specials.add(special)
|
||||||
return f, lowered_specials
|
return f, lowered_specials
|
||||||
|
|
||||||
|
|
||||||
def _can_lower(overrides, specials):
|
def _can_lower(overrides, specials):
|
||||||
for special in specials:
|
for special in specials:
|
||||||
cl = special.__class__
|
cl = special.__class__
|
||||||
|
@ -253,6 +264,7 @@ def _can_lower(overrides, specials):
|
||||||
return True
|
return True
|
||||||
return False
|
return False
|
||||||
|
|
||||||
|
|
||||||
def _lower_specials(overrides, specials):
|
def _lower_specials(overrides, specials):
|
||||||
f, lowered_specials = _lower_specials_step(overrides, specials)
|
f, lowered_specials = _lower_specials_step(overrides, specials)
|
||||||
while _can_lower(overrides, f.specials):
|
while _can_lower(overrides, f.specials):
|
||||||
|
@ -262,6 +274,7 @@ def _lower_specials(overrides, specials):
|
||||||
f.specials -= lowered_specials2
|
f.specials -= lowered_specials2
|
||||||
return f, lowered_specials
|
return f, lowered_specials
|
||||||
|
|
||||||
|
|
||||||
def _printspecials(overrides, specials, ns, add_data_file):
|
def _printspecials(overrides, specials, ns, add_data_file):
|
||||||
r = ""
|
r = ""
|
||||||
for special in sorted(specials, key=lambda x: x.huid):
|
for special in sorted(specials, key=lambda x: x.huid):
|
||||||
|
@ -271,6 +284,7 @@ def _printspecials(overrides, specials, ns, add_data_file):
|
||||||
r += pr
|
r += pr
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def convert(f, ios=None, name="top",
|
def convert(f, ios=None, name="top",
|
||||||
special_overrides=dict(),
|
special_overrides=dict(),
|
||||||
create_clock_domains=True,
|
create_clock_domains=True,
|
||||||
|
|
|
@ -3,6 +3,7 @@ from copy import copy
|
||||||
from migen.fhdl.structure import *
|
from migen.fhdl.structure import *
|
||||||
from migen.fhdl.structure import _Operator, _Slice, _Assign, _ArrayProxy, _Fragment
|
from migen.fhdl.structure import _Operator, _Slice, _Assign, _ArrayProxy, _Fragment
|
||||||
|
|
||||||
|
|
||||||
class NodeVisitor:
|
class NodeVisitor:
|
||||||
def visit(self, node):
|
def visit(self, node):
|
||||||
if isinstance(node, (int, bool)):
|
if isinstance(node, (int, bool)):
|
||||||
|
@ -98,6 +99,7 @@ class NodeVisitor:
|
||||||
def visit_unknown(self, node):
|
def visit_unknown(self, node):
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
# Default methods always copy the node, except for:
|
# Default methods always copy the node, except for:
|
||||||
# - Signals, ClockSignals and ResetSignals
|
# - Signals, ClockSignals and ResetSignals
|
||||||
# - Unknown objects
|
# - Unknown objects
|
||||||
|
|
|
@ -3,6 +3,7 @@ from migen.fhdl.std import *
|
||||||
from migen.genlib.misc import optree
|
from migen.genlib.misc import optree
|
||||||
from migen.genlib.record import *
|
from migen.genlib.record import *
|
||||||
|
|
||||||
|
|
||||||
def _make_m2s(layout):
|
def _make_m2s(layout):
|
||||||
r = []
|
r = []
|
||||||
for f in layout:
|
for f in layout:
|
||||||
|
@ -12,6 +13,7 @@ def _make_m2s(layout):
|
||||||
r.append((f[0], _make_m2s(f[1])))
|
r.append((f[0], _make_m2s(f[1])))
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
class EndpointDescription:
|
class EndpointDescription:
|
||||||
def __init__(self, payload_layout, param_layout=[], packetized=False):
|
def __init__(self, payload_layout, param_layout=[], packetized=False):
|
||||||
self.payload_layout = payload_layout
|
self.payload_layout = payload_layout
|
||||||
|
@ -56,14 +58,17 @@ class _Endpoint(Record):
|
||||||
except:
|
except:
|
||||||
return getattr(object.__getattribute__(self, "param"), name)
|
return getattr(object.__getattribute__(self, "param"), name)
|
||||||
|
|
||||||
|
|
||||||
class Source(_Endpoint):
|
class Source(_Endpoint):
|
||||||
def connect(self, sink):
|
def connect(self, sink):
|
||||||
return Record.connect(self, sink)
|
return Record.connect(self, sink)
|
||||||
|
|
||||||
|
|
||||||
class Sink(_Endpoint):
|
class Sink(_Endpoint):
|
||||||
def connect(self, source):
|
def connect(self, source):
|
||||||
return source.connect(self)
|
return source.connect(self)
|
||||||
|
|
||||||
|
|
||||||
def get_endpoints(obj, filt=_Endpoint):
|
def get_endpoints(obj, filt=_Endpoint):
|
||||||
if hasattr(obj, "get_endpoints") and callable(obj.get_endpoints):
|
if hasattr(obj, "get_endpoints") and callable(obj.get_endpoints):
|
||||||
return obj.get_endpoints(filt)
|
return obj.get_endpoints(filt)
|
||||||
|
@ -73,12 +78,14 @@ def get_endpoints(obj, filt=_Endpoint):
|
||||||
r[k] = v
|
r[k] = v
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def get_single_ep(obj, filt):
|
def get_single_ep(obj, filt):
|
||||||
eps = get_endpoints(obj, filt)
|
eps = get_endpoints(obj, filt)
|
||||||
if len(eps) != 1:
|
if len(eps) != 1:
|
||||||
raise ValueError("More than one endpoint")
|
raise ValueError("More than one endpoint")
|
||||||
return list(eps.items())[0]
|
return list(eps.items())[0]
|
||||||
|
|
||||||
|
|
||||||
class BinaryActor(Module):
|
class BinaryActor(Module):
|
||||||
def __init__(self, *args, **kwargs):
|
def __init__(self, *args, **kwargs):
|
||||||
self.busy = Signal()
|
self.busy = Signal()
|
||||||
|
@ -89,6 +96,7 @@ class BinaryActor(Module):
|
||||||
def build_binary_control(self, sink, source):
|
def build_binary_control(self, sink, source):
|
||||||
raise NotImplementedError("Binary actor classes must overload build_binary_control_fragment")
|
raise NotImplementedError("Binary actor classes must overload build_binary_control_fragment")
|
||||||
|
|
||||||
|
|
||||||
class CombinatorialActor(BinaryActor):
|
class CombinatorialActor(BinaryActor):
|
||||||
def build_binary_control(self, sink, source):
|
def build_binary_control(self, sink, source):
|
||||||
self.comb += [
|
self.comb += [
|
||||||
|
@ -102,6 +110,7 @@ class CombinatorialActor(BinaryActor):
|
||||||
source.eop.eq(sink.eop)
|
source.eop.eq(sink.eop)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class SequentialActor(BinaryActor):
|
class SequentialActor(BinaryActor):
|
||||||
def __init__(self, delay):
|
def __init__(self, delay):
|
||||||
self.trigger = Signal()
|
self.trigger = Signal()
|
||||||
|
@ -134,6 +143,7 @@ class SequentialActor(BinaryActor):
|
||||||
source.eop.eq(sink.eop)
|
source.eop.eq(sink.eop)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class PipelinedActor(BinaryActor):
|
class PipelinedActor(BinaryActor):
|
||||||
def __init__(self, latency):
|
def __init__(self, latency):
|
||||||
self.pipe_ce = Signal()
|
self.pipe_ce = Signal()
|
||||||
|
|
|
@ -3,6 +3,7 @@ from collections import defaultdict
|
||||||
from migen.fhdl.std import *
|
from migen.fhdl.std import *
|
||||||
from migen.flow.actor import *
|
from migen.flow.actor import *
|
||||||
|
|
||||||
|
|
||||||
class EndpointSimHook(Module):
|
class EndpointSimHook(Module):
|
||||||
def __init__(self, endpoint):
|
def __init__(self, endpoint):
|
||||||
self.endpoint = endpoint
|
self.endpoint = endpoint
|
||||||
|
@ -25,6 +26,7 @@ class EndpointSimHook(Module):
|
||||||
else:
|
else:
|
||||||
self.on_inactive()
|
self.on_inactive()
|
||||||
|
|
||||||
|
|
||||||
class DFGHook(Module):
|
class DFGHook(Module):
|
||||||
def __init__(self, dfg, create):
|
def __init__(self, dfg, create):
|
||||||
assert(not dfg.is_abstract())
|
assert(not dfg.is_abstract())
|
||||||
|
|
|
@ -4,6 +4,7 @@ from migen.flow.hooks import DFGHook
|
||||||
|
|
||||||
ISD_MAGIC = 0x6ab4
|
ISD_MAGIC = 0x6ab4
|
||||||
|
|
||||||
|
|
||||||
class EndpointReporter(Module, AutoCSR):
|
class EndpointReporter(Module, AutoCSR):
|
||||||
def __init__(self, endpoint, nbits):
|
def __init__(self, endpoint, nbits):
|
||||||
self.reset = Signal()
|
self.reset = Signal()
|
||||||
|
@ -43,6 +44,7 @@ class EndpointReporter(Module, AutoCSR):
|
||||||
)
|
)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class DFGReporter(DFGHook, AutoCSR):
|
class DFGReporter(DFGHook, AutoCSR):
|
||||||
def __init__(self, dfg, nbits):
|
def __init__(self, dfg, nbits):
|
||||||
self._magic = CSRStatus(16)
|
self._magic = CSRStatus(16)
|
||||||
|
|
|
@ -9,6 +9,7 @@ from migen.flow import plumbing
|
||||||
# from the dictionary. They are needed to enable actor duplication or sharing during
|
# from the dictionary. They are needed to enable actor duplication or sharing during
|
||||||
# elaboration, and automatic parametrization of plumbing actors.
|
# elaboration, and automatic parametrization of plumbing actors.
|
||||||
|
|
||||||
|
|
||||||
class AbstractActor:
|
class AbstractActor:
|
||||||
def __init__(self, actor_class, parameters=dict(), name=None):
|
def __init__(self, actor_class, parameters=dict(), name=None):
|
||||||
self.actor_class = actor_class
|
self.actor_class = actor_class
|
||||||
|
@ -26,6 +27,7 @@ class AbstractActor:
|
||||||
r += ">"
|
r += ">"
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
class MultiDiGraph:
|
class MultiDiGraph:
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
self.edges = defaultdict(list)
|
self.edges = defaultdict(list)
|
||||||
|
@ -89,6 +91,7 @@ class MultiDiGraph:
|
||||||
e.append((source, sink, edge))
|
e.append((source, sink, edge))
|
||||||
return e
|
return e
|
||||||
|
|
||||||
|
|
||||||
# TODO: rewrite this without non-determinism
|
# TODO: rewrite this without non-determinism
|
||||||
class DataFlowGraph(MultiDiGraph):
|
class DataFlowGraph(MultiDiGraph):
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
|
@ -280,6 +283,7 @@ class DataFlowGraph(MultiDiGraph):
|
||||||
optimizer(self)
|
optimizer(self)
|
||||||
self._instantiate_actors()
|
self._instantiate_actors()
|
||||||
|
|
||||||
|
|
||||||
class CompositeActor(Module):
|
class CompositeActor(Module):
|
||||||
def __init__(self, dfg):
|
def __init__(self, dfg):
|
||||||
dfg.elaborate()
|
dfg.elaborate()
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
from migen.flow.hooks import *
|
from migen.flow.hooks import *
|
||||||
|
|
||||||
|
|
||||||
class EndpointReporter(EndpointSimHook):
|
class EndpointReporter(EndpointSimHook):
|
||||||
def __init__(self, endpoint):
|
def __init__(self, endpoint):
|
||||||
EndpointSimHook.__init__(self, endpoint)
|
EndpointSimHook.__init__(self, endpoint)
|
||||||
|
@ -37,6 +38,7 @@ class EndpointReporter(EndpointSimHook):
|
||||||
def on_inactive(self):
|
def on_inactive(self):
|
||||||
self.inactive += 1
|
self.inactive += 1
|
||||||
|
|
||||||
|
|
||||||
class DFGReporter(DFGHook):
|
class DFGReporter(DFGHook):
|
||||||
def __init__(self, dfg):
|
def __init__(self, dfg):
|
||||||
DFGHook.__init__(self, dfg, lambda u, ep, v: EndpointReporter(getattr(u, ep)))
|
DFGHook.__init__(self, dfg, lambda u, ep, v: EndpointReporter(getattr(u, ep)))
|
||||||
|
|
|
@ -3,6 +3,7 @@ from migen.flow.actor import *
|
||||||
from migen.genlib.record import *
|
from migen.genlib.record import *
|
||||||
from migen.genlib.misc import optree
|
from migen.genlib.misc import optree
|
||||||
|
|
||||||
|
|
||||||
class Buffer(PipelinedActor):
|
class Buffer(PipelinedActor):
|
||||||
def __init__(self, layout):
|
def __init__(self, layout):
|
||||||
self.d = Sink(layout)
|
self.d = Sink(layout)
|
||||||
|
@ -14,6 +15,7 @@ class Buffer(PipelinedActor):
|
||||||
self.q.param.eq(self.d.param)
|
self.q.param.eq(self.d.param)
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
class Combinator(Module):
|
class Combinator(Module):
|
||||||
def __init__(self, layout, subrecords):
|
def __init__(self, layout, subrecords):
|
||||||
self.source = Source(layout)
|
self.source = Source(layout)
|
||||||
|
@ -34,6 +36,7 @@ class Combinator(Module):
|
||||||
self.comb += [self.source.payload.eq(sink.payload) for sink in sinks]
|
self.comb += [self.source.payload.eq(sink.payload) for sink in sinks]
|
||||||
self.comb += [self.source.param.eq(sink.param) for sink in sinks]
|
self.comb += [self.source.param.eq(sink.param) for sink in sinks]
|
||||||
|
|
||||||
|
|
||||||
class Splitter(Module):
|
class Splitter(Module):
|
||||||
def __init__(self, layout, subrecords):
|
def __init__(self, layout, subrecords):
|
||||||
self.sink = Sink(layout)
|
self.sink = Sink(layout)
|
||||||
|
@ -58,6 +61,7 @@ class Splitter(Module):
|
||||||
for n, s in enumerate(sources):
|
for n, s in enumerate(sources):
|
||||||
self.comb += s.stb.eq(self.sink.stb & ~already_acked[n])
|
self.comb += s.stb.eq(self.sink.stb & ~already_acked[n])
|
||||||
|
|
||||||
|
|
||||||
class Multiplexer(Module):
|
class Multiplexer(Module):
|
||||||
def __init__(self, layout, n):
|
def __init__(self, layout, n):
|
||||||
self.source = Source(layout)
|
self.source = Source(layout)
|
||||||
|
@ -76,6 +80,7 @@ class Multiplexer(Module):
|
||||||
cases[i] = Record.connect(sink, self.source)
|
cases[i] = Record.connect(sink, self.source)
|
||||||
self.comb += Case(self.sel, cases)
|
self.comb += Case(self.sel, cases)
|
||||||
|
|
||||||
|
|
||||||
class Demultiplexer(Module):
|
class Demultiplexer(Module):
|
||||||
def __init__(self, layout, n):
|
def __init__(self, layout, n):
|
||||||
self.sink = Sink(layout)
|
self.sink = Sink(layout)
|
||||||
|
|
|
@ -3,6 +3,7 @@ from migen.fhdl.bitcontainer import value_bits_sign
|
||||||
from migen.fhdl.specials import Special
|
from migen.fhdl.specials import Special
|
||||||
from migen.fhdl.tools import list_signals
|
from migen.fhdl.tools import list_signals
|
||||||
|
|
||||||
|
|
||||||
class NoRetiming(Special):
|
class NoRetiming(Special):
|
||||||
def __init__(self, reg):
|
def __init__(self, reg):
|
||||||
Special.__init__(self)
|
Special.__init__(self)
|
||||||
|
@ -13,6 +14,7 @@ class NoRetiming(Special):
|
||||||
def lower(dr):
|
def lower(dr):
|
||||||
return Module()
|
return Module()
|
||||||
|
|
||||||
|
|
||||||
class MultiRegImpl(Module):
|
class MultiRegImpl(Module):
|
||||||
def __init__(self, i, o, odomain, n):
|
def __init__(self, i, o, odomain, n):
|
||||||
self.i = i
|
self.i = i
|
||||||
|
@ -32,6 +34,7 @@ class MultiRegImpl(Module):
|
||||||
self.comb += self.o.eq(src)
|
self.comb += self.o.eq(src)
|
||||||
self.specials += [NoRetiming(reg) for reg in self.regs]
|
self.specials += [NoRetiming(reg) for reg in self.regs]
|
||||||
|
|
||||||
|
|
||||||
class MultiReg(Special):
|
class MultiReg(Special):
|
||||||
def __init__(self, i, o, odomain="sys", n=2):
|
def __init__(self, i, o, odomain="sys", n=2):
|
||||||
Special.__init__(self)
|
Special.__init__(self)
|
||||||
|
@ -58,6 +61,7 @@ class MultiReg(Special):
|
||||||
def lower(dr):
|
def lower(dr):
|
||||||
return MultiRegImpl(dr.i, dr.o, dr.odomain, dr.n)
|
return MultiRegImpl(dr.i, dr.o, dr.odomain, dr.n)
|
||||||
|
|
||||||
|
|
||||||
class PulseSynchronizer(Module):
|
class PulseSynchronizer(Module):
|
||||||
def __init__(self, idomain, odomain):
|
def __init__(self, idomain, odomain):
|
||||||
self.i = Signal()
|
self.i = Signal()
|
||||||
|
@ -77,6 +81,7 @@ class PulseSynchronizer(Module):
|
||||||
sync_o += toggle_o_r.eq(toggle_o)
|
sync_o += toggle_o_r.eq(toggle_o)
|
||||||
self.comb += self.o.eq(toggle_o ^ toggle_o_r)
|
self.comb += self.o.eq(toggle_o ^ toggle_o_r)
|
||||||
|
|
||||||
|
|
||||||
class GrayCounter(Module):
|
class GrayCounter(Module):
|
||||||
def __init__(self, width):
|
def __init__(self, width):
|
||||||
self.ce = Signal()
|
self.ce = Signal()
|
||||||
|
|
|
@ -4,6 +4,7 @@ from migen.fhdl.std import *
|
||||||
Encoders and decoders between binary and one-hot representation
|
Encoders and decoders between binary and one-hot representation
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
|
||||||
class Encoder(Module):
|
class Encoder(Module):
|
||||||
"""Encode one-hot to binary
|
"""Encode one-hot to binary
|
||||||
|
|
||||||
|
@ -32,6 +33,7 @@ class Encoder(Module):
|
||||||
act["default"] = self.n.eq(1)
|
act["default"] = self.n.eq(1)
|
||||||
self.comb += Case(self.i, act)
|
self.comb += Case(self.i, act)
|
||||||
|
|
||||||
|
|
||||||
class PriorityEncoder(Module):
|
class PriorityEncoder(Module):
|
||||||
"""Priority encode requests to binary
|
"""Priority encode requests to binary
|
||||||
|
|
||||||
|
@ -60,6 +62,7 @@ class PriorityEncoder(Module):
|
||||||
self.comb += If(self.i[j], self.o.eq(j))
|
self.comb += If(self.i[j], self.o.eq(j))
|
||||||
self.comb += self.n.eq(self.i == 0)
|
self.comb += self.n.eq(self.i == 0)
|
||||||
|
|
||||||
|
|
||||||
class Decoder(Module):
|
class Decoder(Module):
|
||||||
"""Decode binary to one-hot
|
"""Decode binary to one-hot
|
||||||
|
|
||||||
|
@ -89,5 +92,6 @@ class Decoder(Module):
|
||||||
self.comb += Case(self.i, act)
|
self.comb += Case(self.i, act)
|
||||||
self.comb += If(self.n, self.o.eq(0))
|
self.comb += If(self.n, self.o.eq(0))
|
||||||
|
|
||||||
|
|
||||||
class PriorityDecoder(Decoder):
|
class PriorityDecoder(Decoder):
|
||||||
pass # same
|
pass # same
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
from migen.fhdl.std import *
|
from migen.fhdl.std import *
|
||||||
|
|
||||||
|
|
||||||
class Complex:
|
class Complex:
|
||||||
def __init__(self, real, imag):
|
def __init__(self, real, imag):
|
||||||
self.real = real
|
self.real = real
|
||||||
|
@ -46,6 +47,7 @@ class Complex:
|
||||||
else:
|
else:
|
||||||
return self.real.eq(r), self.imag.eq(0)
|
return self.real.eq(r), self.imag.eq(0)
|
||||||
|
|
||||||
|
|
||||||
def SignalC(*args, **kwargs):
|
def SignalC(*args, **kwargs):
|
||||||
real = Signal(*args, **kwargs)
|
real = Signal(*args, **kwargs)
|
||||||
imag = Signal(*args, **kwargs)
|
imag = Signal(*args, **kwargs)
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
from migen.fhdl.std import *
|
from migen.fhdl.std import *
|
||||||
|
|
||||||
|
|
||||||
class Divider(Module):
|
class Divider(Module):
|
||||||
def __init__(self, w):
|
def __init__(self, w):
|
||||||
self.start_i = Signal()
|
self.start_i = Signal()
|
||||||
|
|
|
@ -2,6 +2,7 @@ from migen.fhdl.std import *
|
||||||
from migen.genlib.cdc import NoRetiming, MultiReg, GrayCounter
|
from migen.genlib.cdc import NoRetiming, MultiReg, GrayCounter
|
||||||
from migen.genlib.record import layout_len, Record
|
from migen.genlib.record import layout_len, Record
|
||||||
|
|
||||||
|
|
||||||
def _inc(signal, modulo):
|
def _inc(signal, modulo):
|
||||||
if modulo == 2**flen(signal):
|
if modulo == 2**flen(signal):
|
||||||
return signal.eq(signal + 1)
|
return signal.eq(signal + 1)
|
||||||
|
@ -12,6 +13,7 @@ def _inc(signal, modulo):
|
||||||
signal.eq(signal + 1)
|
signal.eq(signal + 1)
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
class _FIFOInterface:
|
class _FIFOInterface:
|
||||||
"""
|
"""
|
||||||
Data written to the input interface (`din`, `we`, `writable`) is
|
Data written to the input interface (`din`, `we`, `writable`) is
|
||||||
|
@ -63,6 +65,7 @@ class _FIFOInterface:
|
||||||
self.dout_bits = self.dout
|
self.dout_bits = self.dout
|
||||||
self.width = width_or_layout
|
self.width = width_or_layout
|
||||||
|
|
||||||
|
|
||||||
class SyncFIFO(Module, _FIFOInterface):
|
class SyncFIFO(Module, _FIFOInterface):
|
||||||
"""Synchronous FIFO (first in, first out)
|
"""Synchronous FIFO (first in, first out)
|
||||||
|
|
||||||
|
@ -130,6 +133,7 @@ class SyncFIFO(Module, _FIFOInterface):
|
||||||
self.readable.eq(self.level != 0)
|
self.readable.eq(self.level != 0)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class SyncFIFOBuffered(Module, _FIFOInterface):
|
class SyncFIFOBuffered(Module, _FIFOInterface):
|
||||||
def __init__(self, width_or_layout, depth):
|
def __init__(self, width_or_layout, depth):
|
||||||
_FIFOInterface.__init__(self, width_or_layout, depth)
|
_FIFOInterface.__init__(self, width_or_layout, depth)
|
||||||
|
@ -154,6 +158,7 @@ class SyncFIFOBuffered(Module, _FIFOInterface):
|
||||||
)
|
)
|
||||||
self.comb += self.level.eq(fifo.level + self.readable)
|
self.comb += self.level.eq(fifo.level + self.readable)
|
||||||
|
|
||||||
|
|
||||||
class AsyncFIFO(Module, _FIFOInterface):
|
class AsyncFIFO(Module, _FIFOInterface):
|
||||||
"""Asynchronous FIFO (first in, first out)
|
"""Asynchronous FIFO (first in, first out)
|
||||||
|
|
||||||
|
|
|
@ -5,20 +5,24 @@ from migen.fhdl.module import FinalizeError
|
||||||
from migen.fhdl.visit import NodeTransformer
|
from migen.fhdl.visit import NodeTransformer
|
||||||
from migen.fhdl.bitcontainer import value_bits_sign
|
from migen.fhdl.bitcontainer import value_bits_sign
|
||||||
|
|
||||||
|
|
||||||
class AnonymousState:
|
class AnonymousState:
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
# do not use namedtuple here as it inherits tuple
|
# do not use namedtuple here as it inherits tuple
|
||||||
# and the latter is used elsewhere in FHDL
|
# and the latter is used elsewhere in FHDL
|
||||||
class NextState:
|
class NextState:
|
||||||
def __init__(self, state):
|
def __init__(self, state):
|
||||||
self.state = state
|
self.state = state
|
||||||
|
|
||||||
|
|
||||||
class NextValue:
|
class NextValue:
|
||||||
def __init__(self, register, value):
|
def __init__(self, register, value):
|
||||||
self.register = register
|
self.register = register
|
||||||
self.value = value
|
self.value = value
|
||||||
|
|
||||||
|
|
||||||
class _LowerNext(NodeTransformer):
|
class _LowerNext(NodeTransformer):
|
||||||
def __init__(self, next_state_signal, encoding, aliases):
|
def __init__(self, next_state_signal, encoding, aliases):
|
||||||
self.next_state_signal = next_state_signal
|
self.next_state_signal = next_state_signal
|
||||||
|
@ -46,6 +50,7 @@ class _LowerNext(NodeTransformer):
|
||||||
else:
|
else:
|
||||||
return node
|
return node
|
||||||
|
|
||||||
|
|
||||||
class FSM(Module):
|
class FSM(Module):
|
||||||
def __init__(self, reset_state=None):
|
def __init__(self, reset_state=None):
|
||||||
self.actions = OrderedDict()
|
self.actions = OrderedDict()
|
||||||
|
|
|
@ -2,6 +2,7 @@ from migen.fhdl.std import *
|
||||||
from migen.fhdl.specials import Special
|
from migen.fhdl.specials import Special
|
||||||
from migen.fhdl.tools import list_signals
|
from migen.fhdl.tools import list_signals
|
||||||
|
|
||||||
|
|
||||||
class DifferentialInput(Special):
|
class DifferentialInput(Special):
|
||||||
def __init__(self, i_p, i_n, o):
|
def __init__(self, i_p, i_n, o):
|
||||||
Special.__init__(self)
|
Special.__init__(self)
|
||||||
|
@ -18,6 +19,7 @@ class DifferentialInput(Special):
|
||||||
def lower(dr):
|
def lower(dr):
|
||||||
raise NotImplementedError("Attempted to use a differential input, but platform does not support them")
|
raise NotImplementedError("Attempted to use a differential input, but platform does not support them")
|
||||||
|
|
||||||
|
|
||||||
class DifferentialOutput(Special):
|
class DifferentialOutput(Special):
|
||||||
def __init__(self, i, o_p, o_n):
|
def __init__(self, i, o_p, o_n):
|
||||||
Special.__init__(self)
|
Special.__init__(self)
|
||||||
|
@ -34,6 +36,7 @@ class DifferentialOutput(Special):
|
||||||
def lower(dr):
|
def lower(dr):
|
||||||
raise NotImplementedError("Attempted to use a differential output, but platform does not support them")
|
raise NotImplementedError("Attempted to use a differential output, but platform does not support them")
|
||||||
|
|
||||||
|
|
||||||
class CRG(Module):
|
class CRG(Module):
|
||||||
def __init__(self, clk, rst=0):
|
def __init__(self, clk, rst=0):
|
||||||
self.clock_domains.cd_sys = ClockDomain()
|
self.clock_domains.cd_sys = ClockDomain()
|
||||||
|
@ -53,6 +56,7 @@ class CRG(Module):
|
||||||
self.cd_sys.rst.eq(~rst_n)
|
self.cd_sys.rst.eq(~rst_n)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
class DDRInput(Special):
|
class DDRInput(Special):
|
||||||
def __init__(self, i, o1, o2, clk=ClockSignal()):
|
def __init__(self, i, o1, o2, clk=ClockSignal()):
|
||||||
Special.__init__(self)
|
Special.__init__(self)
|
||||||
|
@ -71,6 +75,7 @@ class DDRInput(Special):
|
||||||
def lower(dr):
|
def lower(dr):
|
||||||
raise NotImplementedError("Attempted to use a DDR input, but platform does not support them")
|
raise NotImplementedError("Attempted to use a DDR input, but platform does not support them")
|
||||||
|
|
||||||
|
|
||||||
class DDROutput(Special):
|
class DDROutput(Special):
|
||||||
def __init__(self, i1, i2, o, clk=ClockSignal()):
|
def __init__(self, i1, i2, o, clk=ClockSignal()):
|
||||||
Special.__init__(self)
|
Special.__init__(self)
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
from migen.fhdl.std import *
|
from migen.fhdl.std import *
|
||||||
from migen.fhdl.structure import _Operator
|
from migen.fhdl.structure import _Operator
|
||||||
|
|
||||||
|
|
||||||
def optree(op, operands, lb=None, ub=None, default=None):
|
def optree(op, operands, lb=None, ub=None, default=None):
|
||||||
if lb is None:
|
if lb is None:
|
||||||
lb = 0
|
lb = 0
|
||||||
|
@ -20,6 +21,7 @@ def optree(op, operands, lb=None, ub=None, default=None):
|
||||||
[optree(op, operands, lb, s, default),
|
[optree(op, operands, lb, s, default),
|
||||||
optree(op, operands, s, ub, default)])
|
optree(op, operands, s, ub, default)])
|
||||||
|
|
||||||
|
|
||||||
def split(v, *counts):
|
def split(v, *counts):
|
||||||
r = []
|
r = []
|
||||||
offset = 0
|
offset = 0
|
||||||
|
@ -31,6 +33,7 @@ def split(v, *counts):
|
||||||
offset += n
|
offset += n
|
||||||
return tuple(r)
|
return tuple(r)
|
||||||
|
|
||||||
|
|
||||||
def displacer(signal, shift, output, n=None, reverse=False):
|
def displacer(signal, shift, output, n=None, reverse=False):
|
||||||
if shift is None:
|
if shift is None:
|
||||||
return output.eq(signal)
|
return output.eq(signal)
|
||||||
|
@ -44,6 +47,7 @@ def displacer(signal, shift, output, n=None, reverse=False):
|
||||||
l = [Replicate(shift == i, w) & signal for i in r]
|
l = [Replicate(shift == i, w) & signal for i in r]
|
||||||
return output.eq(Cat(*l))
|
return output.eq(Cat(*l))
|
||||||
|
|
||||||
|
|
||||||
def chooser(signal, shift, output, n=None, reverse=False):
|
def chooser(signal, shift, output, n=None, reverse=False):
|
||||||
if shift is None:
|
if shift is None:
|
||||||
return output.eq(signal)
|
return output.eq(signal)
|
||||||
|
@ -59,6 +63,7 @@ def chooser(signal, shift, output, n=None, reverse=False):
|
||||||
cases[i] = [output.eq(signal[s*w:(s+1)*w])]
|
cases[i] = [output.eq(signal[s*w:(s+1)*w])]
|
||||||
return Case(shift, cases).makedefault()
|
return Case(shift, cases).makedefault()
|
||||||
|
|
||||||
|
|
||||||
def timeline(trigger, events):
|
def timeline(trigger, events):
|
||||||
lastevent = max([e[0] for e in events])
|
lastevent = max([e[0] for e in events])
|
||||||
counter = Signal(max=lastevent+1)
|
counter = Signal(max=lastevent+1)
|
||||||
|
@ -86,6 +91,7 @@ def timeline(trigger, events):
|
||||||
sync.append(counterlogic)
|
sync.append(counterlogic)
|
||||||
return sync
|
return sync
|
||||||
|
|
||||||
|
|
||||||
@ResetInserter()
|
@ResetInserter()
|
||||||
@CEInserter()
|
@CEInserter()
|
||||||
class FlipFlop(Module):
|
class FlipFlop(Module):
|
||||||
|
@ -94,6 +100,7 @@ class FlipFlop(Module):
|
||||||
self.q = Signal(*args, **kwargs)
|
self.q = Signal(*args, **kwargs)
|
||||||
self.sync += self.q.eq(self.d)
|
self.sync += self.q.eq(self.d)
|
||||||
|
|
||||||
|
|
||||||
@ResetInserter()
|
@ResetInserter()
|
||||||
@CEInserter()
|
@CEInserter()
|
||||||
class Counter(Module):
|
class Counter(Module):
|
||||||
|
@ -102,6 +109,7 @@ class Counter(Module):
|
||||||
self.width = flen(self.value)
|
self.width = flen(self.value)
|
||||||
self.sync += self.value.eq(self.value+increment)
|
self.sync += self.value.eq(self.value+increment)
|
||||||
|
|
||||||
|
|
||||||
@ResetInserter()
|
@ResetInserter()
|
||||||
@CEInserter()
|
@CEInserter()
|
||||||
class Timeout(Module):
|
class Timeout(Module):
|
||||||
|
|
|
@ -11,6 +11,7 @@ from migen.genlib.misc import optree
|
||||||
# size can be an int, or a (int, bool) tuple for signed numbers
|
# size can be an int, or a (int, bool) tuple for signed numbers
|
||||||
# sublayout must be a list
|
# sublayout must be a list
|
||||||
|
|
||||||
|
|
||||||
def set_layout_parameters(layout, **layout_dict):
|
def set_layout_parameters(layout, **layout_dict):
|
||||||
def resolve(p):
|
def resolve(p):
|
||||||
if isinstance(p, str):
|
if isinstance(p, str):
|
||||||
|
@ -34,6 +35,7 @@ def set_layout_parameters(layout, **layout_dict):
|
||||||
raise TypeError
|
raise TypeError
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def layout_len(layout):
|
def layout_len(layout):
|
||||||
r = 0
|
r = 0
|
||||||
for f in layout:
|
for f in layout:
|
||||||
|
@ -53,12 +55,14 @@ def layout_len(layout):
|
||||||
r += fsize
|
r += fsize
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
def layout_get(layout, name):
|
def layout_get(layout, name):
|
||||||
for f in layout:
|
for f in layout:
|
||||||
if f[0] == name:
|
if f[0] == name:
|
||||||
return f
|
return f
|
||||||
raise KeyError(name)
|
raise KeyError(name)
|
||||||
|
|
||||||
|
|
||||||
def layout_partial(layout, *elements):
|
def layout_partial(layout, *elements):
|
||||||
r = []
|
r = []
|
||||||
for path in elements:
|
for path in elements:
|
||||||
|
@ -77,6 +81,7 @@ def layout_partial(layout, *elements):
|
||||||
insert_ref.append(layout_get(copy_ref, last))
|
insert_ref.append(layout_get(copy_ref, last))
|
||||||
return r
|
return r
|
||||||
|
|
||||||
|
|
||||||
class Record:
|
class Record:
|
||||||
def __init__(self, layout, name=None):
|
def __init__(self, layout, name=None):
|
||||||
self.name = get_obj_var_name(name, "")
|
self.name = get_obj_var_name(name, "")
|
||||||
|
|
|
@ -2,6 +2,7 @@ from migen.fhdl.std import *
|
||||||
from migen.fhdl.specials import Special
|
from migen.fhdl.specials import Special
|
||||||
from migen.fhdl.tools import list_signals
|
from migen.fhdl.tools import list_signals
|
||||||
|
|
||||||
|
|
||||||
class AsyncResetSynchronizer(Special):
|
class AsyncResetSynchronizer(Special):
|
||||||
def __init__(self, cd, async_reset):
|
def __init__(self, cd, async_reset):
|
||||||
Special.__init__(self)
|
Special.__init__(self)
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
from migen.fhdl.std import *
|
from migen.fhdl.std import *
|
||||||
|
|
||||||
|
|
||||||
class ReorderSlot:
|
class ReorderSlot:
|
||||||
def __init__(self, tag_width, data_width):
|
def __init__(self, tag_width, data_width):
|
||||||
self.wait_data = Signal()
|
self.wait_data = Signal()
|
||||||
|
@ -7,6 +8,7 @@ class ReorderSlot:
|
||||||
self.tag = Signal(tag_width)
|
self.tag = Signal(tag_width)
|
||||||
self.data = Signal(data_width)
|
self.data = Signal(data_width)
|
||||||
|
|
||||||
|
|
||||||
class ReorderBuffer(Module):
|
class ReorderBuffer(Module):
|
||||||
def __init__(self, tag_width, data_width, depth):
|
def __init__(self, tag_width, data_width, depth):
|
||||||
# issue
|
# issue
|
||||||
|
|
|
@ -2,6 +2,7 @@ from migen.fhdl.std import *
|
||||||
|
|
||||||
(SP_WITHDRAW, SP_CE) = range(2)
|
(SP_WITHDRAW, SP_CE) = range(2)
|
||||||
|
|
||||||
|
|
||||||
class RoundRobin(Module):
|
class RoundRobin(Module):
|
||||||
def __init__(self, n, switch_policy=SP_WITHDRAW):
|
def __init__(self, n, switch_policy=SP_WITHDRAW):
|
||||||
self.request = Signal(n)
|
self.request = Signal(n)
|
||||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue