diff --git a/nmigen/back/rtlil.py b/nmigen/back/rtlil.py index 5cd9f97f..e4774018 100644 --- a/nmigen/back/rtlil.py +++ b/nmigen/back/rtlil.py @@ -826,10 +826,12 @@ def _convert_fragment(builder, fragment, name_map, hierarchy): data_mask = (1 << memory.width) - 1 for addr in range(memory.depth): if addr < len(memory.init): - data = memory.init[addr] & data_mask + data = "{:0{}b}".format( + memory.init[addr] & data_mask, memory.width + ) else: - data = 0 - data_parts.append("{:0{}b}".format(data, memory.width)) + data = ("0" if not memory.reset_less else "x") * memory.width + data_parts.append(data) module.cell("$meminit", ports={ "\\ADDR": rhs_compiler(ast.Const(0, addr_bits)), "\\DATA": "{}'".format(memory.width * memory.depth) + diff --git a/nmigen/hdl/mem.py b/nmigen/hdl/mem.py index 93d5d160..da475d24 100644 --- a/nmigen/hdl/mem.py +++ b/nmigen/hdl/mem.py @@ -9,7 +9,11 @@ class Memory: - def __init__(self, *, width, depth, init=None, name=None, simulate=True): + # Configuration options to configure default behaviour for all generated memories + # These options should only be set in top level of code and not in modules + reset_less = False + + def __init__(self, *, width, depth, init=None, name=None, simulate=True, reset_less=None): if not isinstance(width, int) or width < 0: raise TypeError("Memory width must be a non-negative integer, not {!r}" .format(width)) @@ -30,6 +34,9 @@ def __init__(self, *, width, depth, init=None, name=None, simulate=True): self._array.append(Signal(self.width, name="{}({})" .format(name or "memory", addr))) + if reset_less is not None: + self.reset_less = reset_less + self.init = init @property diff --git a/nmigen/test/test_hdl_mem.py b/nmigen/test/test_hdl_mem.py index e7fc232a..3b13bf5e 100644 --- a/nmigen/test/test_hdl_mem.py +++ b/nmigen/test/test_hdl_mem.py @@ -42,6 +42,19 @@ def test_init_wrong_type(self): "'str' object cannot be interpreted as an integer"): m = Memory(width=8, depth=4, init=[1, "0"]) + def test_reset_less(self): + mem = Memory(width=8, depth=4, reset_less=True) + self.assertEqual(mem.reset_less, True) + + orig_reset_less = Memory.reset_less + Memory.reset_less = True + mem = Memory(width=8, depth=4) + self.assertEqual(mem.reset_less, True) + Memory.reset_less = False + mem = Memory(width=8, depth=4) + self.assertEqual(mem.reset_less, False) + Memory.reset_less = orig_reset_less + def test_read_port_transparent(self): mem = Memory(width=8, depth=4) rdport = mem.read_port()