def popcount(w): """ Create a population count circuit. Parameters ---------- w: the width of the adder. Returns ------- a `CircuitGraph` addder. """ c = Circuit(name="popcount") ps = [[c.add(f"in_{i}", "input")] for i in range(w)] i = 0 while len(ps) > 1: # get values ns = ps.pop(0) ms = ps.pop(0) # pad aw = max(len(ns), len(ms)) while len(ms) < aw: ms += ["null"] while len(ns) < aw: ns += ["null"] # instantiate and connect adder a = adder(aw).strip_io() c.extend(a.relabel({n: f"add_{i}_{n}" for n in a.nodes()})) for j, (n, m) in enumerate(zip(ns, ms)): c.connect(n, f"add_{i}_a_{j}") c.connect(m, f"add_{i}_b_{j}") # add adder outputs ps.append([f"add_{i}_out_{j}" for j in range(aw + 1)]) i += 1 # connect outputs for i, o in enumerate(ps[0]): c.add(f"out_{i}", "buf", fanin=o, output=True) if "null" in c: c.set_type("null", "0") c.set_output("null", False) return c
def bench_to_circuit(bench, name): """ Creates a new Circuit from a bench string. Parameters ---------- bench: str bench code. name: str the module name. Returns ------- Circuit the parsed circuit. """ # create circuit c = Circuit(name=name) # get inputs in_regex = r"(?:INPUT|input)\s*\((.+?)\)" for net_str in re.findall(in_regex, bench, re.DOTALL): nets = net_str.replace(" ", "").replace("\n", "").replace("\t", "").split(",") for n in nets: c.add(n, "input") # handle gates regex = r"(\S+)\s*=\s*(NOT|OR|NOR|AND|NAND|XOR|XNOR|not|or|nor|and|nand|not|xor|xnor)\((.+?)\)" for net, gate, input_str in re.findall(regex, bench): # parse all nets inputs = (input_str.replace(" ", "").replace("\n", "").replace("\t", "").split(",")) # get outputs in_regex = r"(?:OUTPUT|output)\s*\((.+?)\)" for net_str in re.findall(in_regex, bench, re.DOTALL): nets = net_str.replace(" ", "").replace("\n", "").replace("\t", "").split(",") for n in nets: c.set_output(n) return c