Add handling of byte reads and writes
authorMichael Nolan <mtnolan2640@gmail.com>
Wed, 24 Jun 2020 17:16:13 +0000 (13:16 -0400)
committerMichael Nolan <mtnolan2640@gmail.com>
Wed, 24 Jun 2020 17:16:13 +0000 (13:16 -0400)
src/soc/experiment/lsmem.py

index 3b89163d45f40051902a5f642238e44042b49ed6..6256d0e5819a4ad3ac5b7c1ea9aa10b82909c9f7 100644 (file)
@@ -18,10 +18,10 @@ class TestMemLoadStoreUnit(LoadStoreUnitInterface, Elaboratable):
             self.regwid, self.addrwid, granularity=8)
 
         m.d.comb += [
-            mem.rdport.addr.eq(self.x_addr),
+            mem.rdport.addr.eq(self.x_addr[2:]),
             self.m_load_data.eq(mem.rdport.data),
 
-            mem.wrport.addr.eq(self.x_addr),
+            mem.wrport.addr.eq(self.x_addr[2:]),
             mem.wrport.en.eq(Mux(self.x_store, self.x_mask, 0)),
             mem.wrport.data.eq(self.x_store_data)
             ]
@@ -53,6 +53,31 @@ def read_from_addr(dut, addr):
     assert (yield dut.x_valid)
     return (yield dut.m_load_data)
 
+def write_byte(dut, addr, val):
+    offset = addr & 0x3
+    yield dut.x_addr.eq(addr)
+    yield dut.x_store.eq(1)
+    yield dut.x_store_data.eq(val << (offset * 8))
+    yield dut.x_mask.eq(1 << offset)
+
+    yield
+    yield dut.x_store.eq(0)
+    while (yield dut.x_stall):
+        yield
+
+def read_byte(dut, addr):
+    offset = addr & 0x3
+    yield dut.x_addr.eq(addr)
+    yield dut.x_load.eq(1)
+    yield
+    yield dut.x_load.eq(0)
+    yield Settle()
+    while (yield dut.x_stall):
+        yield
+    assert (yield dut.x_valid)
+    val = (yield dut.m_load_data)
+    return (val >> (offset * 8)) & 0xff
+
 if __name__ == '__main__':
     m = Module()
     dut = TestMemLoadStoreUnit(regwid=32, addrwid=4)
@@ -66,9 +91,16 @@ if __name__ == '__main__':
         values = [random.randint(0, (1<<32)-1) for x in range(16)]
 
         for addr, val in enumerate(values):
-            yield from write_to_addr(dut, addr, val)
+            yield from write_to_addr(dut, addr << 2, val)
+        for addr, val in enumerate(values):
+            x = yield from read_from_addr(dut, addr << 2)
+            assert x == val
+
+        values = [random.randint(0, 255) for x in range(16*4)]
+        for addr, val in enumerate(values):
+            yield from write_byte(dut, addr, val)
         for addr, val in enumerate(values):
-            x = yield from read_from_addr(dut, addr)
+            x = yield from read_byte(dut, addr)
             assert x == val
 
     sim.add_sync_process(process)