sim: support generators yielding statements
authorSebastien Bourdeauducq <sb@m-labs.hk>
Sun, 20 Sep 2015 07:04:15 +0000 (15:04 +0800)
committerSebastien Bourdeauducq <sb@m-labs.hk>
Sun, 20 Sep 2015 07:04:15 +0000 (15:04 +0800)
examples/basic/graycounter.py
examples/sim/basic2.py
examples/sim/fir.py
examples/sim/memory.py
migen/sim.py
migen/test/test_coding.py
migen/test/test_divider.py
migen/test/test_fifo.py
migen/test/test_signed.py
migen/test/test_sort.py

index bedd466588164db9fa36a4b1c433606e98426378..bf73e78990ff44302354b21c981413a320a35139 100644 (file)
@@ -9,7 +9,7 @@ def tb(dut):
     for i in range(35):
         print("{0:0{1}b} CE={2} bin={3}".format((yield dut.q),
             flen(dut.q), (yield dut.ce), (yield dut.q_binary)))
-        yield dut.ce, prng.getrandbits(1)
+        yield dut.ce.eq(prng.getrandbits(1))
         yield
 
 
index 524f4435b720e885c444cea1d24a6a743e5a781c..518286020c876ca5f00588461670c814e19b5320 100644 (file)
@@ -18,9 +18,9 @@ def counter_test(dut):
         # Only assert CE every second cycle.
         # => each counter value is held for two cycles.
         if cycle % 2:
-            yield dut.ce, 0  # This is how you write to a signal.
+            yield dut.ce.eq(0)  # This is how you write to a signal.
         else:
-            yield dut.ce, 1
+            yield dut.ce.eq(1)
         print("Cycle: {} Count: {}".format(cycle, (yield dut.count)))
         yield
 
index c9adcb2cde6971ea1a21a4a9b59e77346fcc6f31..a7b98036c2a10224ba23fd6068f07fe8ca515271 100644 (file)
@@ -38,7 +38,7 @@ def fir_tb(dut, frequency, inputs, outputs):
     f = 2**(dut.wsize - 1)
     for cycle in range(200):
         v = 0.1*cos(2*pi*frequency*cycle)
-        yield dut.i, int(f*v)
+        yield dut.i.eq(int(f*v))
         inputs.append(v)
         outputs.append((yield dut.o)/f)
         yield
index 3071bc9ece727a237035421e2ce1821b9c3a67fb..4d8ca675bb28d60fd7dd44e6ffed91c4ac045171 100644 (file)
@@ -11,7 +11,7 @@ class Mem(Module):
 def memory_test(dut):
     # write (only first 5 values)
     for i in range(5):
-        yield dut.mem[i], 42 + i
+        yield dut.mem[i].eq(42 + i)
     # remember: values are written after the tick, and read before the tick.
     # wait one tick for the memory to update.
     yield
index b34d442486673b07240b5493fb1644046a4ecc7b..eee9a41b2dea33f494c1f02f7e6150c348552981 100644 (file)
@@ -1,7 +1,8 @@
 import operator
 
 from migen.fhdl.structure import *
-from migen.fhdl.structure import (_Value, _Operator, _Slice, _ArrayProxy,
+from migen.fhdl.structure import (_Value, _Statement,
+                                  _Operator, _Slice, _ArrayProxy,
                                   _Assign, _Fragment)
 from migen.fhdl.bitcontainer import flen
 from migen.fhdl.tools import list_targets
@@ -207,11 +208,14 @@ class Simulator:
             self.evaluator.execute(self.fragment.comb)
             modified = self.evaluator.commit()
 
-    def _eval_nested_lists(self, x):
+    def _evalexec_nested_lists(self, x):
         if isinstance(x, list):
-            return [self._eval_nested_lists(e) for e in x]
+            return [self._evalexec_nested_lists(e) for e in x]
         elif isinstance(x, _Value):
             return self.evaluator.eval(x)
+        elif isinstance(x, _Statement):
+            self.evaluator.execute([x])
+            return None
         else:
             raise ValueError
 
@@ -224,10 +228,8 @@ class Simulator:
                     request = generator.send(reply)
                     if request is None:
                         break  # next cycle
-                    elif isinstance(request, tuple):
-                        self.evaluator.assign(*request)
                     else:
-                        reply = self._eval_nested_lists(request)
+                        reply = self._evalexec_nested_lists(request)
                 except StopIteration:
                     exhausted.append(generator)
                     break
index 965a7e9751e068cfa6f59ad7f7dec9bb66746610..84d92eb3d654c3bf51bde51d9661b9e657069110 100644 (file)
@@ -21,7 +21,7 @@ class EncCase(SimCase, unittest.TestCase):
         def gen():
             for _ in range(256):
                 if seq:
-                    yield self.tb.dut.i, seq.pop(0)
+                    yield self.tb.dut.i.eq(seq.pop(0))
                 if (yield self.tb.dut.n):
                     self.assertNotIn((yield self.tb.dut.i), [1<<i for i in range(8)])
                 else:
@@ -45,7 +45,7 @@ class PrioEncCase(SimCase, unittest.TestCase):
         def gen():
             for _ in range(256):
                 if seq:
-                    yield self.tb.dut.i, seq.pop(0)
+                    yield self.tb.dut.i.eq(seq.pop(0))
                 i = yield self.tb.dut.i
                 if (yield self.tb.dut.n):
                     self.assertEqual(i, 0)
@@ -74,8 +74,8 @@ class DecCase(SimCase, unittest.TestCase):
             for _ in range(256):
                 if seq:
                     i = seq.pop()
-                    yield self.tb.dut.i, i//2
-                    yield self.tb.dut.n, i%2
+                    yield self.tb.dut.i.eq(i//2)
+                    yield self.tb.dut.n.eq(i%2)
                 i = yield self.tb.dut.i
                 o = yield self.tb.dut.o
                 if (yield self.tb.dut.n):
@@ -100,7 +100,7 @@ class SmallPrioEncCase(SimCase, unittest.TestCase):
         def gen():
             for _ in range(5):
                 if seq:
-                    yield self.tb.dut.i, seq.pop(0)
+                    yield self.tb.dut.i.eq(seq.pop(0))
                 i = yield self.tb.dut.i
                 if (yield self.tb.dut.n):
                     self.assertEqual(i, 0)
index 5040d9965a2ab3fefb4ee7746d0d9bdb843a755a..8ccb00e56d5be1b7b0dede72b24c83a9ae12d28b 100644 (file)
@@ -14,11 +14,11 @@ class DivisionCase(SimCase, unittest.TestCase):
         def gen():
             for dividend in range(16):
                 for divisor in range(1, 16):
-                    yield self.tb.dut.dividend_i, dividend
-                    yield self.tb.dut.divisor_i, divisor
-                    yield self.tb.dut.start_i, 1
+                    yield self.tb.dut.dividend_i.eq(dividend)
+                    yield self.tb.dut.divisor_i.eq(divisor)
+                    yield self.tb.dut.start_i.eq(1)
                     yield
-                    yield self.tb.dut.start_i, 0
+                    yield self.tb.dut.start_i.eq(0)
                     while not (yield self.tb.dut.ready_o):
                         yield
                     self.assertEqual((yield self.tb.dut.quotient_o), dividend//divisor)
index 1d5e8fda21f2038b1d1c6819ddec6b681217d45d..e5f30a1e6baf23264127461356b0bfb4b8ae88d2 100644 (file)
@@ -28,8 +28,8 @@ class SyncFIFOCase(SimCase, unittest.TestCase):
         def gen():
             for cycle in count():
                 # fire re and we at "random"
-                yield self.tb.dut.we, cycle % 2 == 0
-                yield self.tb.dut.re, cycle % 3 == 0
+                yield self.tb.dut.we.eq(cycle % 2 == 0)
+                yield self.tb.dut.re.eq(cycle % 3 == 0)
                 # the output if valid must be correct
                 if (yield self.tb.dut.readable) and (yield self.tb.dut.re):
                     try:
@@ -45,9 +45,10 @@ class SyncFIFOCase(SimCase, unittest.TestCase):
         seq = [x for x in range(20) if x % 5]
         def gen():
             for cycle in count():
-                yield self.tb.dut.we, cycle % 2 == 0
-                yield self.tb.dut.re, cycle % 7 == 0
-                yield self.tb.dut.replace, (yield self.tb.dut.din.a) % 5 == 1
+                yield self.tb.dut.we.eq(cycle % 2 == 0)
+                yield self.tb.dut.re.eq(cycle % 7 == 0)
+                yield self.tb.dut.replace.eq(
+                    (yield self.tb.dut.din.a) % 5 == 1)
                 if (yield self.tb.dut.readable) and (yield self.tb.dut.re):
                     try:
                         i = seq.pop(0)
index 9f065827955b323d15f55609bd500d1f1695175f..8b114f3f137cdb6b4637ad6df6cef4cdc3a4b103 100644 (file)
@@ -29,8 +29,8 @@ class SignedCase(SimCase, unittest.TestCase):
     def test_comparisons(self):
         def gen():
             for i in range(-4, 4):
-                yield self.tb.a, i
-                yield self.tb.b, i
+                yield self.tb.a.eq(i)
+                yield self.tb.b.eq(i)
                 a = yield self.tb.a
                 b = yield self.tb.b
                 for asign, bsign, f, r, op in self.tb.vals:
index 13227528f6ebf9f7c8e4f2c4453ef397576dba3a..93579078e3b8c511317f78dacad51c46d6ed62c1 100644 (file)
@@ -23,7 +23,7 @@ class BitonicCase(SimCase, unittest.TestCase):
         def gen():
             for repeat in range(20):
                 for i in self.tb.dut.i:
-                    yield i, randrange(1<<flen(i))
+                    yield i.eq(randrange(1<<flen(i)))
                 yield
                 self.assertEqual(sorted((yield self.tb.dut.i)),
                                  (yield self.tb.dut.o))