Compare commits

...

2 Commits

  1. 19
      src/kyupy/circuit.py
  2. 12
      src/kyupy/logic_sim.py

19
src/kyupy/circuit.py

@ -96,10 +96,10 @@ class Node: @@ -96,10 +96,10 @@ class Node:
by allocating an array or list :code:`my_data` of length :code:`len(n.circuit.nodes)` and
accessing it by :code:`my_data[n.index]` or simply by :code:`my_data[n]`.
"""
self.ins: list[Line] = GrowingList()
self.ins: GrowingList[Line] = GrowingList()
"""A list of input connections (:class:`Line` objects).
"""
self.outs: list[Line] = GrowingList()
self.outs: GrowingList[Line] = GrowingList()
"""A list of output connections (:class:`Line` objects).
"""
@ -615,6 +615,21 @@ class Circuit: @@ -615,6 +615,21 @@ class Circuit:
if marks[n]:
yield n
def fanout(self, origin_nodes):
"""Generator function to iterate over the fan-out cone of a given list of origin nodes.
Nodes are yielded in topological order.
"""
marks = [False] * len(self.nodes)
for n in origin_nodes:
marks[n] = True
for n in self.topological_order():
if not marks[n]:
for line in n.ins.without_nones():
marks[n] |= marks[line.driver]
if marks[n]:
yield n
def fanout_free_regions(self):
for stem in self.reversed_topological_order():
if len(stem.outs) == 1 and 'dff' not in stem.kind.lower(): continue

12
src/kyupy/logic_sim.py

@ -52,7 +52,7 @@ class LogicSim(sim.SimOps): @@ -52,7 +52,7 @@ class LogicSim(sim.SimOps):
"""
self.c[self.pippi_c_locs] = self.s[0, self.pippi_s_locs, :self.mdim]
def c_prop(self, sims=None, inject_cb=None):
def c_prop(self, sims=None, inject_cb=None, flip_line=-1):
"""Propagate the input values through the combinational circuit towards the outputs.
Performs all logic operations in topological order.
@ -68,7 +68,7 @@ class LogicSim(sim.SimOps): @@ -68,7 +68,7 @@ class LogicSim(sim.SimOps):
t1 = self.c_locs[self.tmp2_idx]
if self.m == 2:
if inject_cb is None:
_prop_cpu(self.ops, self.c_locs, self.c)
_prop_cpu(self.ops, self.c_locs, self.c, int(flip_line))
else:
for op, o0l, i0l, i1l, i2l, i3l in self.ops[:,:6]:
o0, i0, i1, i2, i3 = [self.c_locs[x] for x in (o0l, i0l, i1l, i2l, i3l)]
@ -298,9 +298,9 @@ class LogicSim(sim.SimOps): @@ -298,9 +298,9 @@ class LogicSim(sim.SimOps):
@numba.njit
def _prop_cpu(ops, c_locs, c):
for op, o0, i0, i1, i2, i3 in ops[:,:6]:
o0, i0, i1, i2, i3 = [c_locs[x] for x in (o0, i0, i1, i2, i3)]
def _prop_cpu(ops, c_locs, c, flip_line):
for op, o0l, i0l, i1l, i2l, i3l in ops[:,:6]:
o0, i0, i1, i2, i3 = [c_locs[x] for x in (o0l, i0l, i1l, i2l, i3l)]
if op == sim.BUF1: c[o0]=c[i0]
elif op == sim.INV1: c[o0] = ~c[i0]
elif op == sim.AND2: c[o0] = c[i0] & c[i1]
@ -335,6 +335,8 @@ def _prop_cpu(ops, c_locs, c): @@ -335,6 +335,8 @@ def _prop_cpu(ops, c_locs, c):
elif op == sim.OAI211: c[o0] = ~((c[i0] | c[i1]) & c[i2] & c[i3])
elif op == sim.MUX21: c[o0] = (c[i0] & ~c[i2]) | (c[i1] & c[i2])
else: print(f'unknown op {op}')
if flip_line >= 0 and o0l == flip_line:
c[o0] = ~c[o0]
class LogicSim6V(sim.SimOps):

Loading…
Cancel
Save