def add_aon_read_config_data(interconnect: Interconnect): # we need to replace each read_config_data_or with more circuits # it should be in the children for (x, y) in interconnect.tile_circuits: tile = interconnect.tile_circuits[(x, y)] children = tile.children() for child in children: if isinstance(child, FromMagma) and \ child.underlying.name == "read_config_data_or": pd_feature = None # usually the tile features are the last one for feature in reversed(tile.features()): if isinstance(feature, PowerDomainConfigReg): pd_feature = feature break assert pd_feature is not None pd_or = PowerDomainOR(tile.config_data_width) replace(tile, child, pd_or) # add config input to the the module pd_or.add_port("I_not", magma.In(magma.Bits[1])) tile.wire(pd_or.ports.I_not, pd_feature.ports.ps_en_out) pd_or.wire(pd_or.ports.I_not, pd_or.not_gate.ports.I) break
def add_power_domain(interconnect: Interconnect): # add features first for (x, y) in interconnect.tile_circuits: tile = interconnect.tile_circuits[(x, y)] tile_core = tile.core if isinstance(tile_core, IOCore) or tile_core is None: continue # Add PS config register pd_feature = PowerDomainConfigReg(tile.config_addr_width, tile.config_data_width) tile.add_feature(pd_feature) # replace all the interconnect mux with aoi mux. cb mux to aoi const # mux # note that because we have an index to all mux created, it is fairly # straight-forward for (x, y) in interconnect.tile_circuits: tile = interconnect.tile_circuits[(x, y)] for bit_width, sb in tile.sbs.items(): sb_muxs = sb.sb_muxs for _, (node, old_mux) in sb_muxs.items(): assert node.width == bit_width new_mux = AOIMuxWrapper(old_mux.height, bit_width, AOIMuxType.Regular, old_mux.instance_name) # replace it! replace(sb, old_mux, new_mux) reg_mux = sb.reg_muxs for _, (node, old_mux) in reg_mux.items(): assert node.width == bit_width new_mux = AOIMuxWrapper(old_mux.height, bit_width, AOIMuxType.Regular, old_mux.instance_name) # replace it! replace(sb, old_mux, new_mux) # cb is const aoi for _, cb in tile.cbs.items(): old_mux = cb.mux new_mux = AOIMuxWrapper(old_mux.height, cb.node.width, AOIMuxType.Const, cb.instance_name) # replace it! replace(cb, old_mux, new_mux)
def add_power_domain(interconnect: Interconnect): # add features first for (x, y) in interconnect.tile_circuits: tile = interconnect.tile_circuits[(x, y)] tile_core = tile.core if isinstance(tile_core, IOCore) or tile_core is None: continue # Add PS config register pd_feature = PowerDomainConfigReg(tile.config_addr_width, tile.config_data_width) tile.add_feature(pd_feature) # replace all the interconnect mux with aoi mux. cb mux to aoi const # mux # note that because we have an index to all mux created, it is fairly # straight-forward for (x, y) in interconnect.tile_circuits: tile = interconnect.tile_circuits[(x, y)] for bit_width, sb in tile.sbs.items(): # we need more efficient implementation for a simple replacement # pass. in other words, instead of an O(n^2) implementation, we # hand-crafted an O(n) with smaller constants sb_muxs = sb.sb_muxs mux_table = {} for _, (node, old_mux) in sb_muxs.items(): assert node.width == bit_width new_mux = AOIMuxWrapper(old_mux.height, bit_width, AOIMuxType.Regular, old_mux.instance_name) mux_table[old_mux] = new_mux reg_mux = sb.reg_muxs for _, (node, old_mux) in reg_mux.items(): assert node.width == bit_width new_mux = AOIMuxWrapper(old_mux.height, bit_width, AOIMuxType.Regular, old_mux.instance_name) mux_table[old_mux] = new_mux assert len(mux_table) == len(sb_muxs) + len(reg_mux) wires = set() for conn1, conn2 in sb.wires: if conn1.owner() in mux_table or conn2.owner() in mux_table: wires.add((conn1, conn2)) for conn1, conn2 in wires: # avoid O(n) search to remove the wires. this is safe # since we directly load these connection in sorted order sb.wires.remove((conn1, conn2)) for conn1, conn2 in wires: conn1_owner = conn1.owner() conn2_owner = conn2.owner() if conn1_owner in mux_table: conn1 = conn1.get_port(mux_table[conn1_owner].ports) if conn2_owner in mux_table: conn2 = conn2.get_port(mux_table[conn2_owner].ports) sb.wire(conn1, conn2) # cb is const aoi for _, cb in tile.cbs.items(): old_mux = cb.mux new_mux = AOIMuxWrapper(old_mux.height, cb.node.width, AOIMuxType.Const, cb.instance_name) # replace it! replace(cb, old_mux, new_mux)