forked from M-Labs/artiq
48 lines
1.5 KiB
Python
48 lines
1.5 KiB
Python
from migen import *
|
|
from misoc.interconnect.stream import Endpoint
|
|
|
|
|
|
class Spline(Module):
|
|
def __init__(self, order, width, step=1, time_width=None):
|
|
if not (step == 1 or order <= 2):
|
|
raise ValueError("For non-linear splines, "
|
|
"`step` needs to be one.")
|
|
layout = [("a{}".format(i), (width, True)) for i in range(order)]
|
|
self.i = Endpoint(layout)
|
|
self.o = Endpoint(layout)
|
|
self.latency = 1
|
|
|
|
###
|
|
|
|
o = self.o.payload.flatten()
|
|
|
|
self.comb += self.i.ack.eq(~self.o.stb | self.o.ack)
|
|
self.sync += [
|
|
If(self.o.ack,
|
|
self.o.stb.eq(0),
|
|
),
|
|
If(self.i.ack,
|
|
self.o.stb.eq(1),
|
|
[o[i].eq(o[i] + (o[i + 1] << log2_int(step)))
|
|
for i in range(order - 1)],
|
|
If(self.i.stb,
|
|
self.o.payload.eq(self.i.payload),
|
|
),
|
|
),
|
|
]
|
|
|
|
def tri(self, time_width):
|
|
layout = [(name, (length - i*time_width, signed))
|
|
for i, (name, (length, signed), dir) in
|
|
enumerate(self.i.payload.layout[::-1])]
|
|
layout.reverse()
|
|
i = Endpoint(layout)
|
|
i.latency = self.latency
|
|
self.comb += [
|
|
self.i.stb.eq(i.stb),
|
|
i.ack.eq(self.i.ack),
|
|
[i0[-len(i1):].eq(i1) for i0, i1 in
|
|
zip(self.i.payload.flatten(), i.payload.flatten())]
|
|
]
|
|
return i
|