back.pysim: implement "sync processes", like migen.sim generators.
authorwhitequark <cz@m-labs.hk>
Fri, 14 Dec 2018 05:13:58 +0000 (05:13 +0000)
committerwhitequark <cz@m-labs.hk>
Fri, 14 Dec 2018 05:13:58 +0000 (05:13 +0000)
examples/ctrl.py
nmigen/back/pysim.py

index 851c493724c5e79829ede0058a0bf32b3adea1aa..ea388efdcfea7037b355a561ea16477e3a219566 100644 (file)
@@ -23,11 +23,12 @@ print(verilog.convert(frag, ports=[ctr.o, ctr.ce]))
 
 sim = pysim.Simulator(frag, vcd_file=open("ctrl.vcd", "w"))
 sim.add_clock("sync", 1e-6)
-def sim_proc():
-    yield pysim.Delay(15.25e-6)
-    yield ctr.ce.eq(Const(1))
-    yield pysim.Delay(15.25e-6)
-    yield pysim.Tick("sync")
-    yield ctr.ce.eq(Const(0))
-sim.add_process(sim_proc())
+def ce_proc():
+    yield; yield; yield
+    yield ctr.ce.eq(1)
+    yield; yield; yield
+    yield ctr.ce.eq(0)
+    yield; yield; yield
+    yield ctr.ce.eq(1)
+sim.add_sync_process(ce_proc())
 with sim: sim.run_until(100e-6, run_passive=True)
index 966ebc2d447a379cb44b0ab4a4bf191e6e5b5844..3975443897c670b0a070bf5862848fe391455ba2 100644 (file)
@@ -223,8 +223,8 @@ class Simulator:
         for subfragment, name in fragment.subfragments:
             self._add_fragment(subfragment, (*hierarchy, name))
 
-    def add_process(self, fn):
-        self._processes.add(fn)
+    def add_process(self, process):
+        self._processes.add(process)
 
     def add_clock(self, domain, period):
         clk = self._domains[domain].clk
@@ -238,6 +238,16 @@ class Simulator:
                 yield Delay(half_period)
         self.add_process(clk_process())
 
+    def add_sync_process(self, process, domain="sync"):
+        def sync_process():
+            try:
+                result = process.send(None)
+                while True:
+                    result = process.send((yield (result or Tick(domain))))
+            except StopIteration:
+                pass
+        self.add_process(sync_process())
+
     def _signal_name_in_fragment(self, fragment, signal):
         for subfragment, name in fragment.subfragments:
             if signal in subfragment.ports: