lib.io: allow Pin(xdr=0), representing a combinatorial I/O buffer.
This commit is contained in:
parent
3327deae92
commit
c30617fc05
|
@ -18,19 +18,19 @@ def pin_layout(width, dir, xdr=1):
|
||||||
if dir not in ("i", "o", "io"):
|
if dir not in ("i", "o", "io"):
|
||||||
raise TypeError("Direction must be one of \"i\", \"o\" or \"io\", not '{!r}'"""
|
raise TypeError("Direction must be one of \"i\", \"o\" or \"io\", not '{!r}'"""
|
||||||
.format(dir))
|
.format(dir))
|
||||||
if not isinstance(xdr, int) or xdr < 1:
|
if not isinstance(xdr, int) or xdr < 0:
|
||||||
raise TypeError("Gearing ratio must be a positive integer, not '{!r}'"
|
raise TypeError("Gearing ratio must be a non-negative integer, not '{!r}'"
|
||||||
.format(xdr))
|
.format(xdr))
|
||||||
|
|
||||||
fields = []
|
fields = []
|
||||||
if dir in ("i", "io"):
|
if dir in ("i", "io"):
|
||||||
if xdr == 1:
|
if xdr in (0, 1):
|
||||||
fields.append(("i", width))
|
fields.append(("i", width))
|
||||||
else:
|
else:
|
||||||
for n in range(xdr):
|
for n in range(xdr):
|
||||||
fields.append(("i{}".format(n), width))
|
fields.append(("i{}".format(n), width))
|
||||||
if dir in ("o", "io"):
|
if dir in ("o", "io"):
|
||||||
if xdr == 1:
|
if xdr in (0, 1):
|
||||||
fields.append(("o", width))
|
fields.append(("o", width))
|
||||||
else:
|
else:
|
||||||
for n in range(xdr):
|
for n in range(xdr):
|
||||||
|
@ -60,7 +60,8 @@ class Pin(Record):
|
||||||
is specified, both the ``i``/``iN`` and ``o``/``oN`` signals are present, and an ``oe``
|
is specified, both the ``i``/``iN`` and ``o``/``oN`` signals are present, and an ``oe``
|
||||||
signal is present.
|
signal is present.
|
||||||
xdr : int
|
xdr : int
|
||||||
Gearbox ratio. If equal to 1, the I/O buffer is SDR, and only ``i``/``o`` signals are
|
Gearbox ratio. If equal to 0, the I/O buffer is combinatorial, and only ``i``/``o``
|
||||||
|
signals are present. If equal to 1, the I/O buffer is SDR, and only ``i``/``o`` signals are
|
||||||
present. If greater than 1, the I/O buffer includes a gearbox, and ``iN``/``oN`` signals
|
present. If greater than 1, the I/O buffer includes a gearbox, and ``iN``/``oN`` signals
|
||||||
are present instead, where ``N in range(0, N)``. For example, if ``xdr=2``, the I/O buffer
|
are present instead, where ``N in range(0, N)``. For example, if ``xdr=2``, the I/O buffer
|
||||||
is DDR; the signal ``i0`` reflects the value at the rising edge, and the signal ``i1``
|
is DDR; the signal ``i0`` reflects the value at the rising edge, and the signal ``i1``
|
||||||
|
@ -72,13 +73,13 @@ class Pin(Record):
|
||||||
----------
|
----------
|
||||||
i : Signal, out
|
i : Signal, out
|
||||||
I/O buffer input, without gearing. Present if ``dir="i"`` or ``dir="io"``, and ``xdr`` is
|
I/O buffer input, without gearing. Present if ``dir="i"`` or ``dir="io"``, and ``xdr`` is
|
||||||
equal to 1.
|
equal to 0 or 1.
|
||||||
i0, i1, ... : Signal, out
|
i0, i1, ... : Signal, out
|
||||||
I/O buffer inputs, with gearing. Present if ``dir="i"`` or ``dir="io"``, and ``xdr`` is
|
I/O buffer inputs, with gearing. Present if ``dir="i"`` or ``dir="io"``, and ``xdr`` is
|
||||||
greater than 1.
|
greater than 1.
|
||||||
o : Signal, in
|
o : Signal, in
|
||||||
I/O buffer output, without gearing. Present if ``dir="o"`` or ``dir="io"``, and ``xdr`` is
|
I/O buffer output, without gearing. Present if ``dir="o"`` or ``dir="io"``, and ``xdr`` is
|
||||||
equal to 1.
|
equal to 0 or 1.
|
||||||
o0, o1, ... : Signal, in
|
o0, o1, ... : Signal, in
|
||||||
I/O buffer outputs, with gearing. Present if ``dir="o"`` or ``dir="io"``, and ``xdr`` is
|
I/O buffer outputs, with gearing. Present if ``dir="o"`` or ``dir="io"``, and ``xdr`` is
|
||||||
greater than 1.
|
greater than 1.
|
||||||
|
@ -86,7 +87,7 @@ class Pin(Record):
|
||||||
I/O buffer output enable. Present if ``dir="io"``. Buffers generally cannot change
|
I/O buffer output enable. Present if ``dir="io"``. Buffers generally cannot change
|
||||||
direction more than once per cycle, so at most one output enable signal is present.
|
direction more than once per cycle, so at most one output enable signal is present.
|
||||||
"""
|
"""
|
||||||
def __init__(self, width, dir, xdr=1, name=None):
|
def __init__(self, width, dir, xdr=0, name=None):
|
||||||
self.width = width
|
self.width = width
|
||||||
self.dir = dir
|
self.dir = dir
|
||||||
self.xdr = xdr
|
self.xdr = xdr
|
||||||
|
|
|
@ -4,7 +4,7 @@ from ..hdl.rec import *
|
||||||
from ..lib.io import *
|
from ..lib.io import *
|
||||||
|
|
||||||
|
|
||||||
class PinLayoutSDRTestCase(FHDLTestCase):
|
class PinLayoutCombTestCase(FHDLTestCase):
|
||||||
def test_pin_layout_i(self):
|
def test_pin_layout_i(self):
|
||||||
layout_1 = pin_layout(1, dir="i")
|
layout_1 = pin_layout(1, dir="i")
|
||||||
self.assertEqual(layout_1.fields, {
|
self.assertEqual(layout_1.fields, {
|
||||||
|
@ -43,6 +43,45 @@ class PinLayoutSDRTestCase(FHDLTestCase):
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|
||||||
|
class PinLayoutSDRTestCase(FHDLTestCase):
|
||||||
|
def test_pin_layout_i(self):
|
||||||
|
layout_1 = pin_layout(1, dir="i", xdr=1)
|
||||||
|
self.assertEqual(layout_1.fields, {
|
||||||
|
"i": ((1, False), DIR_NONE),
|
||||||
|
})
|
||||||
|
|
||||||
|
layout_2 = pin_layout(2, dir="i", xdr=1)
|
||||||
|
self.assertEqual(layout_2.fields, {
|
||||||
|
"i": ((2, False), DIR_NONE),
|
||||||
|
})
|
||||||
|
|
||||||
|
def test_pin_layout_o(self):
|
||||||
|
layout_1 = pin_layout(1, dir="o", xdr=1)
|
||||||
|
self.assertEqual(layout_1.fields, {
|
||||||
|
"o": ((1, False), DIR_NONE),
|
||||||
|
})
|
||||||
|
|
||||||
|
layout_2 = pin_layout(2, dir="o", xdr=1)
|
||||||
|
self.assertEqual(layout_2.fields, {
|
||||||
|
"o": ((2, False), DIR_NONE),
|
||||||
|
})
|
||||||
|
|
||||||
|
def test_pin_layout_io(self):
|
||||||
|
layout_1 = pin_layout(1, dir="io", xdr=1)
|
||||||
|
self.assertEqual(layout_1.fields, {
|
||||||
|
"i": ((1, False), DIR_NONE),
|
||||||
|
"o": ((1, False), DIR_NONE),
|
||||||
|
"oe": ((1, False), DIR_NONE),
|
||||||
|
})
|
||||||
|
|
||||||
|
layout_2 = pin_layout(2, dir="io", xdr=1)
|
||||||
|
self.assertEqual(layout_2.fields, {
|
||||||
|
"i": ((2, False), DIR_NONE),
|
||||||
|
"o": ((2, False), DIR_NONE),
|
||||||
|
"oe": ((1, False), DIR_NONE),
|
||||||
|
})
|
||||||
|
|
||||||
|
|
||||||
class PinLayoutDDRTestCase(FHDLTestCase):
|
class PinLayoutDDRTestCase(FHDLTestCase):
|
||||||
def test_pin_layout_i(self):
|
def test_pin_layout_i(self):
|
||||||
layout_1 = pin_layout(1, dir="i", xdr=2)
|
layout_1 = pin_layout(1, dir="i", xdr=2)
|
||||||
|
|
Loading…
Reference in a new issue