1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139
|
#!/usr/bin/env python3
import re, sys, os
def sort_bits_key(a):
if a[0] == "!": a = a[1:]
return re.sub(r"\d+", lambda m: "%02d" % int(m.group(0)), a)
def read_database(filename, tile_type):
raw_db = list()
route_to_buffer = set()
add_mux_bits = dict()
with open(filename, "r") as f:
for line in f:
line = line.strip()
m = re.match(r"\s*\((\d+)\s+(\d+)\)\s+(.*)", line)
assert m
bit = "B%d[%d]" % (int(m.group(2)), int(m.group(1)))
line = m.group(3)
line = re.sub(r"^Enable bit of Mux", "MuxEn", line)
line = re.sub(r"^IO control bit:", "IoCtrl", line)
line = re.sub(r"^Column buffer control bit:", "ColBufCtrl", line)
line = re.sub(r"^Negative Clock bit", "NegClk", line)
line = re.sub(r"^Cascade (buffer Enable )?bit:", "Cascade", line)
line = re.sub(r"^Ram config bit:", "RamConfig", line)
line = re.sub(r"^PLL config bit:", "PLL", line)
line = re.sub(r"^Icegate Enable bit:", "Icegate", line)
line = line.split()
if line[0] == "routing":
if line[3] == "wire_gbuf/in": line[3] = "fabout"
raw_db.append((bit, (line[0], line[1], line[3])))
elif line[0] == "IoCtrl":
raw_db.append((bit, (line[0], re.sub(r"^.*?_", "", line[1]).replace("_en", ""))))
elif line[0] in ("IOB_0", "IOB_1"):
if line[1] != "IO":
raw_db.append((bit, (line[0], line[1])))
elif line[0] == "PLL":
line[1] = re.sub(r"CLOCK_T_\d+_\d+_IO(LEFT|RIGHT|UP|DOWN)_", "pll_", line[1])
line[1] = re.sub(r"pll_cf_bit_", "PLLCONFIG_", line[1])
raw_db.append((bit, (line[0], line[1])))
elif line[0] == "ColBufCtrl":
line[1] = re.sub(r"B?IO(LEFT|RIGHT)_", "IO_", line[1])
line[1] = re.sub(r"IO_half_column_clock_enable_", "glb_netwk_", line[1])
line[1] = re.sub(r"(LH|MEM[BT])_colbuf_cntl_", "glb_netwk_", line[1])
if m.group(1) == "7":
line[1] = re.sub(r"glb_netwk_", "8k_glb_netwk_", line[1])
elif m.group(1) in ["1", "2"]:
line[1] = re.sub(r"glb_netwk_", "1k_glb_netwk_", line[1])
raw_db.append((bit, (line[0], line[1])))
elif line[0] == "Cascade":
match = re.match("LH_LC0(\d)_inmux02_5", line[1])
if match:
raw_db.append((bit, ("buffer", "wire_logic_cluster/lc_%d/lout" % (int(match.group(1))-1), "input_2_%s" % match.group(1))))
else:
match = re.match("MEMT_LC\d+_inmux\d+_bram_cbit_(\d+)", line[1])
if match:
raw_db.append((bit, ("RamCascade", "CBIT_%d" % int(match.group(1)))))
else:
raw_db.append((bit, (line[0], line[1])))
elif line[0] == "RamConfig":
if line[1] == "MEMB_Power_Up_Control": line[1] = "PowerUp"
line[1] = re.sub(r"MEMT_bram_cbit_", "CBIT_", line[1])
raw_db.append((bit, (line[0], line[1])))
elif line[0] == "MuxEn":
if line[4] == "wire_gbuf/in": line[4] = "fabout"
if line[3].startswith("logic_op_"):
for prefix in ["IO_L.", "IO_R.", "IO_T.", "IO_B."]:
route_to_buffer.add((prefix + line[3], line[4]))
add_mux_bits.setdefault(prefix + line[3], set()).add((bit, ("buffer", prefix + line[3], line[4])))
else:
raw_db.append((bit, ("buffer", line[3], line[4])))
route_to_buffer.add((line[3], line[4]))
elif line[0] == "NegClk" or line[0] == "Icegate" or re.match(r"LC_\d+", line[0]):
raw_db.append((bit, (line[0],)))
elif line[0] == "Carry_In_Mux":
continue
else:
print("unsupported statement: %s: %s" % (bit, line))
assert False
for i in range(len(raw_db)):
if raw_db[i][1][0] == "routing" and (raw_db[i][1][1], raw_db[i][1][2]) in route_to_buffer:
if raw_db[i][1][1] in add_mux_bits:
for entry in add_mux_bits[raw_db[i][1][1]]:
raw_db.append(entry)
raw_db[i] = (raw_db[i][0], ("buffer", raw_db[i][1][1], raw_db[i][1][2]))
func_to_bits = dict()
for entry in raw_db:
func_to_bits.setdefault(entry[1], set()).add(entry[0])
bit_groups = dict()
for func, bits in list(func_to_bits.items()):
for bit in bits:
bit_groups[bit] = bit_groups.setdefault(bit, set()).union(bits)
for func in func_to_bits:
new_bits = set()
for bit2 in func_to_bits[func]:
for bit in bit_groups[bit2]:
if bit in func_to_bits[func]:
new_bits.add(bit)
else:
new_bits.add("!" + bit)
func_to_bits[func] = new_bits
database = list()
for func in sorted(func_to_bits):
bits = func_to_bits[func]
entry = (",".join(sorted(bits, key=sort_bits_key)),) + func
database.append(entry)
return database
with open("database_io.txt", "w") as f:
for entry in read_database("bitdata_io.txt", "io"):
print("\t".join(entry), file=f)
with open("database_logic.txt", "w") as f:
for entry in read_database("bitdata_logic.txt", "logic"):
print("\t".join(entry), file=f)
with open("database_ramb.txt", "w") as f:
for entry in read_database("bitdata_ramb.txt", "ramb"):
print("\t".join(entry), file=f)
with open("database_ramt.txt", "w") as f:
for entry in read_database("bitdata_ramt.txt", "ramt"):
print("\t".join(entry), file=f)
with open("database_ramb_8k.txt", "w") as f:
for entry in read_database("bitdata_ramb_8k.txt", "ramb_8k"):
print("\t".join(entry), file=f)
with open("database_ramt_8k.txt", "w") as f:
for entry in read_database("bitdata_ramt_8k.txt", "ramt_8k"):
print("\t".join(entry), file=f)
|