Add timing information from dly files
This commit is contained in:
parent
eb77def664
commit
91eca20d10
|
|
@ -1,3 +1,5 @@
|
|||
#python
|
||||
__pycache__/
|
||||
*.pyc
|
||||
*.tar.gz
|
||||
/delay/
|
||||
|
|
@ -0,0 +1,577 @@
|
|||
import zlib
|
||||
import struct
|
||||
from dataclasses import dataclass
|
||||
from typing import List
|
||||
|
||||
@dataclass
|
||||
class T_delay_tri:
|
||||
min: int
|
||||
typ: int
|
||||
max: int
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(data: bytes) -> 'T_delay_tri':
|
||||
min_val, typ_val, max_val = struct.unpack('<3i', data)
|
||||
return T_delay_tri(min_val, typ_val, max_val)
|
||||
|
||||
@dataclass
|
||||
class T_delay:
|
||||
rise: T_delay_tri
|
||||
fall: T_delay_tri
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(data: bytes) -> 'T_delay':
|
||||
rise = T_delay_tri.from_bytes(data[:12])
|
||||
fall = T_delay_tri.from_bytes(data[12:24])
|
||||
return T_delay(rise, fall)
|
||||
|
||||
@dataclass
|
||||
class Tpin_pair:
|
||||
i: int
|
||||
o_or_clk: int # Represents either 'o' or 'clk' depending on the boolean case
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(data: bytes) -> 'Tpin_pair':
|
||||
i_val, o_or_clk_val = struct.unpack('<2h', data)
|
||||
return Tpin_pair(i_val, o_or_clk_val)
|
||||
|
||||
@dataclass
|
||||
class Tentry_rec:
|
||||
pins: Tpin_pair
|
||||
entry_no: int
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(data: bytes) -> 'Tentry_rec':
|
||||
pins = Tpin_pair.from_bytes(data[:4])
|
||||
entry_no = struct.unpack('<h', data[4:6])[0]
|
||||
return Tentry_rec(pins, entry_no)
|
||||
|
||||
@dataclass
|
||||
class Tdel_entry:
|
||||
key: int
|
||||
edge1: int
|
||||
edge2: int
|
||||
time1: T_delay_tri
|
||||
time2: T_delay_tri
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(data: bytes) -> 'Tdel_entry':
|
||||
key, edge1, edge2 = struct.unpack('<3i', data[:12])
|
||||
time1 = T_delay_tri.from_bytes(data[12:24])
|
||||
time2 = T_delay_tri.from_bytes(data[24:36])
|
||||
return Tdel_entry(key, edge1, edge2, time1, time2)
|
||||
|
||||
@dataclass
|
||||
class TRAM_del_rec:
|
||||
iopath: List[Tentry_rec]
|
||||
setuphold: List[Tentry_rec]
|
||||
width: List[Tentry_rec]
|
||||
del_entry: List[Tdel_entry]
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(data: bytes) -> 'TRAM_del_rec':
|
||||
offset = 0
|
||||
iopath = [Tentry_rec.from_bytes(data[offset + i*6:offset + (i+1)*6]) for i in range(3001)]
|
||||
offset += 3001 * 6
|
||||
setuphold = [Tentry_rec.from_bytes(data[offset + i*6:offset + (i+1)*6]) for i in range(8001)]
|
||||
offset += 8001 * 6
|
||||
width = [Tentry_rec.from_bytes(data[offset + i*6:offset + (i+1)*6]) for i in range(51)]
|
||||
offset += 51 * 6
|
||||
del_entry = [Tdel_entry.from_bytes(data[offset + i*36:offset + (i+1)*36]) for i in range(101)]
|
||||
return TRAM_del_rec(iopath, setuphold, width, del_entry)
|
||||
|
||||
@dataclass
|
||||
class Tdel_rec:
|
||||
val: T_delay
|
||||
conf_mux: int
|
||||
name: str
|
||||
x: int
|
||||
y: int
|
||||
plane: int
|
||||
dir: int
|
||||
inv: int
|
||||
cnt: int
|
||||
con_type: int
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(data: memoryview, offset: int) -> ('Tdel_rec', int):
|
||||
val = T_delay.from_bytes(data[offset:offset + 24])
|
||||
offset += 24
|
||||
|
||||
conf_mux = struct.unpack_from('<i', data, offset)[0]
|
||||
offset += 4
|
||||
strlen = data[offset]
|
||||
offset += 1
|
||||
name = data[offset:offset + strlen].decode('ascii')
|
||||
offset += 23 # alignment added as well
|
||||
|
||||
x, y, plane, dir, inv, cnt = struct.unpack_from('<6i', data, offset)
|
||||
offset += 24
|
||||
|
||||
con_type_val = data[offset]
|
||||
offset += 4
|
||||
|
||||
return Tdel_rec(val, conf_mux, name, x, y, plane, dir, inv, cnt, con_type_val), offset
|
||||
|
||||
@dataclass
|
||||
class Tdel_rec_tri:
|
||||
val: T_delay_tri
|
||||
conf_mux: int
|
||||
name: str
|
||||
x: int
|
||||
y: int
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(mv: memoryview, offset: int) -> ('Tdel_rec_tri', int):
|
||||
val = T_delay_tri.from_bytes(mv[offset:offset+12])
|
||||
offset += 12
|
||||
|
||||
conf_mux = struct.unpack_from('<i', mv, offset)[0]
|
||||
offset += 4
|
||||
|
||||
strlen = mv[offset]
|
||||
offset += 1
|
||||
name = mv[offset:offset + strlen].decode('ascii')
|
||||
offset += 23
|
||||
|
||||
x, y = struct.unpack_from('<2i', mv, offset)
|
||||
offset += 8
|
||||
|
||||
return Tdel_rec_tri(val, conf_mux, name, x, y), offset
|
||||
|
||||
|
||||
def read_SB_del_tile_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
SB_del_tile_arr = []
|
||||
|
||||
for i1 in range(4): # [1..4]
|
||||
level1 = []
|
||||
for i2 in range(8): # [1..8]
|
||||
level2 = []
|
||||
for i3 in range(4): # [1..4]
|
||||
level3 = []
|
||||
for i4 in range(12): # [1..12]
|
||||
level4 = []
|
||||
for i5 in range(5): # [0..4]
|
||||
level5 = []
|
||||
for i6 in range(8): # [0..7]
|
||||
chunk = mv[offset:offset + 24]
|
||||
if len(chunk) < 24:
|
||||
raise EOFError("Unexpected end of data")
|
||||
delay = T_delay.from_bytes(chunk)
|
||||
offset += 24
|
||||
level5.append(delay)
|
||||
level4.append(level5)
|
||||
level3.append(level4)
|
||||
level2.append(level3)
|
||||
level1.append(level2)
|
||||
SB_del_tile_arr.append(level1)
|
||||
|
||||
return SB_del_tile_arr, offset
|
||||
|
||||
@dataclass
|
||||
class ExtraTimingDelays:
|
||||
skew_report_del: int
|
||||
fix_skew_del: int
|
||||
del_rec_0: Tdel_rec
|
||||
del_min_route_SB: Tdel_rec
|
||||
del_violation_common: Tdel_rec_tri
|
||||
del_dummy: Tdel_rec
|
||||
del_Hold_D_L: Tdel_rec_tri
|
||||
del_Hold_RAM: Tdel_rec_tri
|
||||
del_Setup_D_L: Tdel_rec_tri
|
||||
del_Setup_RAM: Tdel_rec_tri
|
||||
del_Hold_SN_RN: Tdel_rec_tri
|
||||
del_Setup_SN_RN: Tdel_rec_tri
|
||||
del_Hold_RN_SN: Tdel_rec_tri
|
||||
del_Setup_RN_SN: Tdel_rec_tri
|
||||
del_bot_couty2: Tdel_rec
|
||||
del_bot_glb_couty2: Tdel_rec
|
||||
del_bot_SB_couty2: Tdel_rec
|
||||
del_bot_pouty2: Tdel_rec
|
||||
del_bot_glb_pouty2: Tdel_rec
|
||||
del_bot_SB_pouty2: Tdel_rec
|
||||
del_left_couty2: Tdel_rec
|
||||
del_left_glb_couty2: Tdel_rec
|
||||
del_left_SB_couty2: Tdel_rec
|
||||
del_left_pouty2: Tdel_rec
|
||||
del_left_glb_pouty2: Tdel_rec
|
||||
del_left_SB_pouty2: Tdel_rec
|
||||
del_inp: List[Tdel_rec]
|
||||
del_CPE_out_mux: List[Tdel_rec]
|
||||
del_CPE_CP_Q: Tdel_rec
|
||||
del_CPE_S_Q: Tdel_rec
|
||||
del_CPE_R_Q: Tdel_rec
|
||||
del_CPE_D_Q: Tdel_rec
|
||||
del_RAM_CLK_DO: Tdel_rec
|
||||
del_GLBOUT_sb_big: Tdel_rec
|
||||
del_sb_drv: Tdel_rec
|
||||
del_CP_carry_path: Tdel_rec
|
||||
del_CP_prop_path: Tdel_rec
|
||||
del_special_RAM_I: Tdel_rec
|
||||
del_RAMO_xOBF: Tdel_rec
|
||||
del_GLBOUT_IO_SEL: Tdel_rec
|
||||
del_IO_SEL_Q_out: Tdel_rec
|
||||
del_IO_SEL_Q_in: Tdel_rec
|
||||
in_delayline_per_stage: Tdel_rec
|
||||
out_delayline_per_stage: Tdel_rec
|
||||
del_IBF: Tdel_rec
|
||||
del_OBF: Tdel_rec
|
||||
del_r_OBF: Tdel_rec
|
||||
del_TOBF_ctrl: Tdel_rec
|
||||
del_LVDS_IBF: Tdel_rec
|
||||
del_LVDS_OBF: Tdel_rec
|
||||
del_LVDS_r_OBF: Tdel_rec
|
||||
del_LVDS_TOBF_ctrl: Tdel_rec
|
||||
del_CP_clkin: Tdel_rec
|
||||
del_CP_enin: Tdel_rec
|
||||
del_preplace: Tdel_rec
|
||||
del_CPE_timing_mod: List[Tdel_rec]
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(mv: memoryview, offset: int) -> ('ExtraTimingDelays', int):
|
||||
skew_report_del, fix_skew_del = struct.unpack_from('<2i', mv, offset)
|
||||
offset += 8
|
||||
|
||||
del_rec_0, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_min_route_SB, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_violation_common, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_dummy, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_Hold_D_L, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_Hold_RAM, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_Setup_D_L, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_Setup_RAM, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_Hold_SN_RN, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_Setup_SN_RN, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_Hold_RN_SN, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_Setup_RN_SN, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
|
||||
del_bot_couty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_bot_glb_couty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_bot_SB_couty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_bot_pouty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_bot_glb_pouty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_bot_SB_pouty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_left_couty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_left_glb_couty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_left_SB_couty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_left_pouty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_left_glb_pouty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_left_SB_pouty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_inp = []
|
||||
for _ in range(8):
|
||||
rec, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_inp.append(rec)
|
||||
|
||||
del_CPE_out_mux = []
|
||||
for _ in range(4):
|
||||
rec, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_CPE_out_mux.append(rec)
|
||||
|
||||
del_CPE_CP_Q, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_CPE_S_Q, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_CPE_R_Q, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_CPE_D_Q, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_RAM_CLK_DO, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_GLBOUT_sb_big, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_sb_drv, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_CP_carry_path, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_CP_prop_path, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_special_RAM_I, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_RAMO_xOBF, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_GLBOUT_IO_SEL, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_IO_SEL_Q_out, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_IO_SEL_Q_in, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
in_delayline_per_stage, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
out_delayline_per_stage, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_IBF, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_OBF, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_r_OBF, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_TOBF_ctrl, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_LVDS_IBF, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_LVDS_OBF, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_LVDS_r_OBF, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_LVDS_TOBF_ctrl, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_CP_clkin, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_CP_enin, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_preplace, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_CPE_timing_mod = []
|
||||
for _ in range(42):
|
||||
rec, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_CPE_timing_mod.append(rec)
|
||||
|
||||
return ExtraTimingDelays(
|
||||
skew_report_del, fix_skew_del,
|
||||
del_rec_0, del_min_route_SB,
|
||||
del_violation_common, del_dummy,
|
||||
del_Hold_D_L, del_Hold_RAM, del_Setup_D_L, del_Setup_RAM,
|
||||
del_Hold_SN_RN, del_Setup_SN_RN, del_Hold_RN_SN, del_Setup_RN_SN,
|
||||
del_bot_couty2, del_bot_glb_couty2, del_bot_SB_couty2,
|
||||
del_bot_pouty2, del_bot_glb_pouty2, del_bot_SB_pouty2,
|
||||
del_left_couty2, del_left_glb_couty2, del_left_SB_couty2,
|
||||
del_left_pouty2, del_left_glb_pouty2, del_left_SB_pouty2,
|
||||
del_inp, del_CPE_out_mux,
|
||||
del_CPE_CP_Q, del_CPE_S_Q, del_CPE_R_Q, del_CPE_D_Q,
|
||||
del_RAM_CLK_DO, del_GLBOUT_sb_big, del_sb_drv,
|
||||
del_CP_carry_path, del_CP_prop_path,
|
||||
del_special_RAM_I, del_RAMO_xOBF,
|
||||
del_GLBOUT_IO_SEL, del_IO_SEL_Q_out, del_IO_SEL_Q_in,
|
||||
in_delayline_per_stage, out_delayline_per_stage,
|
||||
del_IBF, del_OBF, del_r_OBF, del_TOBF_ctrl,
|
||||
del_LVDS_IBF, del_LVDS_OBF, del_LVDS_r_OBF, del_LVDS_TOBF_ctrl,
|
||||
del_CP_clkin, del_CP_enin, del_preplace,
|
||||
del_CPE_timing_mod
|
||||
), offset
|
||||
|
||||
def read_IM_del_tile_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(2): # [1..2]
|
||||
level1 = []
|
||||
for i2 in range(8): # [1..8]
|
||||
level2 = []
|
||||
for i3 in range(8): # [1..8]
|
||||
level3 = []
|
||||
for i4 in range(12): # [1..12]
|
||||
level4 = []
|
||||
for i5 in range(8): # [0..7]
|
||||
delay = T_delay.from_bytes(mv[offset:offset+24])
|
||||
offset += 24
|
||||
level4.append(delay)
|
||||
level3.append(level4)
|
||||
level2.append(level3)
|
||||
level1.append(level2)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_OM_del_tile_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(8): # [1..8]
|
||||
level1 = []
|
||||
for i2 in range(8): # [1..8]
|
||||
level2 = []
|
||||
for i3 in range(4): # [9..12]
|
||||
level3 = []
|
||||
for i4 in range(4): # [0..3]
|
||||
delay = T_delay.from_bytes(mv[offset:offset+24])
|
||||
offset += 24
|
||||
level3.append(delay)
|
||||
level2.append(level3)
|
||||
level1.append(level2)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_CPE_del_tile_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(10): # [0..9]
|
||||
level1 = []
|
||||
for i2 in range(19): # [1..19]
|
||||
level2 = []
|
||||
for i3 in range(10): # [1..10]
|
||||
rec, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
level2.append(rec)
|
||||
level1.append(level2)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_SB_del_rim_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(165): # [-2..162]
|
||||
level1 = []
|
||||
for i2 in range(4): # [1..4]
|
||||
level2 = []
|
||||
for i3 in range(12): # [1..12]
|
||||
level3 = []
|
||||
for i4 in range(5): # [0..4]
|
||||
level4 = []
|
||||
for i5 in range(8): # [0..7]
|
||||
delay = T_delay.from_bytes(mv[offset:offset+24])
|
||||
offset += 24
|
||||
level4.append(delay)
|
||||
level3.append(level4)
|
||||
level2.append(level3)
|
||||
level1.append(level2)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_Edge_del_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(165): # [-2..162]
|
||||
level1 = []
|
||||
for i2 in range(4): # [1..4]
|
||||
level2 = []
|
||||
for i3 in range(24): # [1..24]
|
||||
level3 = []
|
||||
for i4 in range(8): # [1..8]
|
||||
delay = T_delay.from_bytes(mv[offset:offset+24])
|
||||
offset += 24
|
||||
level3.append(delay)
|
||||
level2.append(level3)
|
||||
level1.append(level2)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_IO_SEL_del_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(11): # [1..11]
|
||||
level1 = []
|
||||
for i2 in range(4): # [1..4]
|
||||
delay = T_delay.from_bytes(mv[offset:offset+24])
|
||||
offset += 24
|
||||
level1.append(delay)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_CLKIN_del_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(7):
|
||||
level1 = []
|
||||
for i2 in range(4):
|
||||
delay = T_delay.from_bytes(mv[offset:offset + 24])
|
||||
offset += 24
|
||||
level1.append(delay)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_GLBOUT_del_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(28):
|
||||
level1 = []
|
||||
for i2 in range(8):
|
||||
delay = T_delay.from_bytes(mv[offset:offset + 24])
|
||||
offset += 24
|
||||
level1.append(delay)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_PLL_del_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(7):
|
||||
level1 = []
|
||||
for i2 in range(6):
|
||||
delay = T_delay.from_bytes(mv[offset:offset + 24])
|
||||
offset += 24
|
||||
level1.append(delay)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_Tentry_rec_from_bytes(data: memoryview, offset: int) -> ('Tentry_rec', int):
|
||||
pins_i, pins_val, entry_no = struct.unpack_from('<3h', data, offset)
|
||||
return Tentry_rec(Tpin_pair(pins_i, pins_val), entry_no), offset + 6
|
||||
|
||||
def read_Tdel_entry_from_bytes(data: memoryview, offset: int) -> ('Tdel_entry', int):
|
||||
key, edge1, edge2 = struct.unpack_from('<3i', data, offset)
|
||||
time1 = T_delay_tri.from_bytes(data[offset + 12:offset + 24])
|
||||
time2 = T_delay_tri.from_bytes(data[offset + 24:offset + 36])
|
||||
return Tdel_entry(key, edge1, edge2, time1, time2), offset + 36
|
||||
|
||||
def read_TRAM_del_rec_from_bytes(mv: memoryview, offset: int) -> (TRAM_del_rec, int):
|
||||
iopath = []
|
||||
for _ in range(3001):
|
||||
entry, offset = read_Tentry_rec_from_bytes(mv, offset)
|
||||
iopath.append(entry)
|
||||
|
||||
setuphold = []
|
||||
for _ in range(8001):
|
||||
entry, offset = read_Tentry_rec_from_bytes(mv, offset)
|
||||
setuphold.append(entry)
|
||||
|
||||
width = []
|
||||
for _ in range(51):
|
||||
entry, offset = read_Tentry_rec_from_bytes(mv, offset)
|
||||
width.append(entry)
|
||||
|
||||
del_entry = []
|
||||
for _ in range(101):
|
||||
entry, offset = read_Tdel_entry_from_bytes(mv, offset)
|
||||
del_entry.append(entry)
|
||||
|
||||
offset += 2 # alignment added
|
||||
return TRAM_del_rec(iopath, setuphold, width, del_entry), offset
|
||||
|
||||
def read_IO_SEL_io_coef_from_bytes(mv: memoryview, offset: int) -> (list, int):
|
||||
result = []
|
||||
for i1 in range(4): # [1..4]
|
||||
row = []
|
||||
for i2 in range(27): # [1..27]
|
||||
value = struct.unpack_from('<d', mv, offset)[0] # '<d' = little-endian double
|
||||
offset += 8
|
||||
row.append(value)
|
||||
result.append(row)
|
||||
return result, offset
|
||||
|
||||
@dataclass
|
||||
class Tdel_all_rec:
|
||||
SB_del_tile_arr: List[List[List[List[List[List[T_delay]]]]]]
|
||||
IM_del_tile_arr: List[List[List[List[List[T_delay]]]]]
|
||||
OM_del_tile_arr: List[List[List[List[T_delay]]]]
|
||||
CPE_del_tile_arr: List[List[List[Tdel_rec]]]
|
||||
SB_del_rim_arr: List[List[List[List[List[T_delay]]]]]
|
||||
Edge_del_arr: List[List[List[List[T_delay]]]]
|
||||
IO_SEL_del_arr: List[List[T_delay]]
|
||||
CLKIN_del_arr: List[List[T_delay]]
|
||||
GLBOUT_del_arr: List[List[T_delay]]
|
||||
PLL_del_arr: List[List[T_delay]]
|
||||
FPGA_ram_del_1: TRAM_del_rec
|
||||
FPGA_ram_del_2: TRAM_del_rec
|
||||
FPGA_ram_del_3: TRAM_del_rec
|
||||
IO_SEL_io_coef: list[list[float]]
|
||||
timing_delays: ExtraTimingDelays
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(data: bytes) -> 'Tdel_all_rec':
|
||||
offset = 0
|
||||
sb_del_tile_arr, offset = read_SB_del_tile_arr_from_bytes(data, offset)
|
||||
im, offset = read_IM_del_tile_arr_from_bytes(data, offset)
|
||||
om, offset = read_OM_del_tile_arr_from_bytes(data, offset)
|
||||
cpe, offset = read_CPE_del_tile_arr_from_bytes(data, offset)
|
||||
sb_del_rim, offset = read_SB_del_rim_arr_from_bytes(data, offset)
|
||||
edge, offset = read_Edge_del_arr_from_bytes(data, offset)
|
||||
io_sel, offset = read_IO_SEL_del_arr_from_bytes(data, offset)
|
||||
clkin, offset = read_CLKIN_del_arr_from_bytes(data, offset)
|
||||
glbout, offset = read_GLBOUT_del_arr_from_bytes(data, offset)
|
||||
pll_del, offset = read_PLL_del_arr_from_bytes(data, offset)
|
||||
fpga_ram_del_1, offset = read_TRAM_del_rec_from_bytes(data, offset)
|
||||
fpga_ram_del_2, offset = read_TRAM_del_rec_from_bytes(data, offset)
|
||||
fpga_ram_del_3, offset = read_TRAM_del_rec_from_bytes(data, offset)
|
||||
io_sel_coef, offset = read_IO_SEL_io_coef_from_bytes(data, offset)
|
||||
timing_delays, offset = ExtraTimingDelays.from_bytes(data, offset)
|
||||
return Tdel_all_rec(sb_del_tile_arr, im, om, cpe, sb_del_rim, edge, io_sel, clkin, glbout, pll_del, fpga_ram_del_1, fpga_ram_del_2, fpga_ram_del_3,io_sel_coef, timing_delays)
|
||||
|
||||
|
||||
def decompress_file(input_path, output_path):
|
||||
with open(input_path, 'rb') as f_in:
|
||||
compressed_data = f_in.read()
|
||||
try:
|
||||
decompressed_data = zlib.decompress(compressed_data)
|
||||
except zlib.error as e:
|
||||
print(f"Decompression failed: {e}")
|
||||
return
|
||||
|
||||
all = Tdel_all_rec.from_bytes(decompressed_data)
|
||||
#print(all.GLBOUT_del_arr)
|
||||
|
||||
with open(output_path, 'wb') as f_out:
|
||||
f_out.write(decompressed_data)
|
||||
|
||||
# Example usage
|
||||
#decompress_file("cc_best_eco_dly.dly", "cc_best_eco_dly.bin")
|
||||
#decompress_file("cc_best_lpr_dly.dly", "cc_best_lpr_dly.bin")
|
||||
#decompress_file("cc_best_spd_dly.dly", "cc_best_spd_dly.bin")
|
||||
#
|
||||
#decompress_file("cc_typ_eco_dly.dly", "cc_typ_eco_dly.bin")
|
||||
#decompress_file("cc_typ_lpr_dly.dly", "cc_typ_lpr_dly.bin")
|
||||
#decompress_file("cc_typ_spd_dly.dly", "cc_typ_spd_dly.bin")
|
||||
#
|
||||
#decompress_file("cc_worst_eco_dly.dly", "cc_worst_eco_dly.bin")
|
||||
#decompress_file("cc_worst_lpr_dly.dly", "cc_worst_lpr_dly.bin")
|
||||
decompress_file("cc_worst_spd_dly.dly", "cc_worst_spd_dly.bin")
|
||||
|
|
@ -0,0 +1,16 @@
|
|||
#!/bin/bash
|
||||
|
||||
set -e
|
||||
ARCHIVE="cc-toolchain-linux.tar.gz"
|
||||
|
||||
rm -rf delay
|
||||
mkdir -p delay
|
||||
|
||||
wget -O "$ARCHIVE" "https://colognechip.com/downloads/cc-toolchain-linux.tar.gz"
|
||||
|
||||
tar --extract \
|
||||
--file="$ARCHIVE" \
|
||||
--wildcards \
|
||||
--strip-components=3 \
|
||||
--directory=delay \
|
||||
'cc-toolchain-linux/bin/p_r/*.dly'
|
||||
298
gatemate/chip.py
298
gatemate/chip.py
|
|
@ -17,9 +17,11 @@
|
|||
#
|
||||
|
||||
import die
|
||||
import os
|
||||
from die import Die
|
||||
from dataclasses import dataclass
|
||||
from typing import List, Dict
|
||||
from timing import decompress_timing
|
||||
|
||||
@dataclass(eq=True, order=True)
|
||||
class Pad:
|
||||
|
|
@ -36,6 +38,37 @@ class Bank:
|
|||
die : str
|
||||
bank: str
|
||||
|
||||
@dataclass
|
||||
class TimingDelay:
|
||||
min : int
|
||||
typ : int
|
||||
max : int
|
||||
|
||||
def __add__(self, other):
|
||||
if not isinstance(other, TimingDelay):
|
||||
return NotImplemented
|
||||
return TimingDelay(self.min + other.min, self.typ + other.typ, self.max + other.max)
|
||||
|
||||
def __sub__(self, other):
|
||||
if not isinstance(other, TimingDelay):
|
||||
return NotImplemented
|
||||
return TimingDelay(self.min - other.min, self.typ - other.typ, self.max - other.max)
|
||||
|
||||
@dataclass
|
||||
class Timing:
|
||||
rise : TimingDelay
|
||||
fall : TimingDelay
|
||||
|
||||
def __add__(self, other):
|
||||
if not isinstance(other, Timing):
|
||||
return NotImplemented
|
||||
return Timing(self.rise + other.rise, self.fall + other.fall)
|
||||
|
||||
def __sub__(self, other):
|
||||
if not isinstance(other, Timing):
|
||||
return NotImplemented
|
||||
return Timing(self.rise - other.rise, self.fall - other.fall)
|
||||
|
||||
@dataclass
|
||||
class Chip:
|
||||
name : str
|
||||
|
|
@ -178,3 +211,268 @@ def get_all_devices():
|
|||
|
||||
def get_device(name):
|
||||
return CCGM1_DEVICES[name]
|
||||
|
||||
def convert_delay(d):
|
||||
return Timing(TimingDelay(d.rise.min, d.rise.typ, d.rise.max), TimingDelay(d.fall.min, d.fall.typ, d.fall.max))
|
||||
|
||||
def convert_delay_val(d):
|
||||
return Timing(TimingDelay(d.min, d.typ, d.max), TimingDelay(d.min, d.typ, d.max))
|
||||
|
||||
def convert_ram_delay(d):
|
||||
return Timing(TimingDelay(d.time1.min, d.time1.typ, d.time1.max), TimingDelay(d.time2.min, d.time2.typ, d.time2.max))
|
||||
|
||||
def check_dly_available():
|
||||
current_dir = os.path.dirname(os.path.abspath(__file__))
|
||||
return os.path.exists(os.path.join(current_dir, "..", "delay", "cc_worst_spd_dly.dly"))
|
||||
|
||||
def get_timings(name):
|
||||
val = dict()
|
||||
current_dir = os.path.dirname(os.path.abspath(__file__))
|
||||
timing_data = decompress_timing(os.path.join(current_dir, "..", "delay", f"cc_{name}_dly.dly"))
|
||||
|
||||
for i1 in range(4): # [1..4]
|
||||
for i2 in range(8): # [1..8]
|
||||
for i3 in range(4): # [1..4]
|
||||
for i4 in range(12): # [1..12]
|
||||
for i5 in range(5): # [0..4]
|
||||
for i6 in range(8): # [0..7]
|
||||
d = timing_data.SB_del_tile_arr[i1][i2][i3][i4][i5][i6]
|
||||
if d.rise.min == 123456: # not connected
|
||||
continue
|
||||
x = i2+1
|
||||
y = i3+1
|
||||
y = 2*y if (x % 2 == 0) else 2*y-1
|
||||
name = f"sb_del_t{i1+1}_x{x}_y{y}_p{i4+1}_d{i5}_s{i6}"
|
||||
val[name] = convert_delay(d)
|
||||
|
||||
for i1 in range(2): # [1..2]
|
||||
for i2 in range(8): # [1..8]
|
||||
for i3 in range(8): # [1..8]
|
||||
for i4 in range(12): # [1..12]
|
||||
for i5 in range(8): # [0..7]
|
||||
d = timing_data.IM_del_tile_arr[i1][i2][i3][i4][i5]
|
||||
if d.rise.min == 123456: # not connected
|
||||
continue
|
||||
name = f"im_x{i2+1}_y{i3+1}_p{i4+1}_d{i5}_path{i1+1}"
|
||||
val[name] = convert_delay(d)
|
||||
|
||||
for i1 in range(8): # [1..8]
|
||||
for i2 in range(8): # [1..8]
|
||||
for i3 in range(4): # [9..12]
|
||||
for i4 in range(4): # [0..3]
|
||||
d = timing_data.OM_del_tile_arr[i1][i2][i3][i4]
|
||||
if d.rise.min == 123456: # not connected
|
||||
continue
|
||||
name = f"om_x{i1+1}_y{i2+1}_p{i3+9}_d{i4}"
|
||||
val[name] = convert_delay(d)
|
||||
|
||||
for i1 in range(10): # [0..9]
|
||||
for i2 in range(19): # [1..19]
|
||||
for i3 in range(10): # [1..10]
|
||||
d = timing_data.CPE_del_tile_arr[i1][i2][i3]
|
||||
if d.name == "CPE": # not used
|
||||
continue
|
||||
val[d.name] = convert_delay(d.val)
|
||||
|
||||
for i1 in range(165): # [-2..162]
|
||||
for i2 in range(4): # [1..4]
|
||||
for i3 in range(12): # [1..12]
|
||||
for i4 in range(5): # [0..4]
|
||||
for i5 in range(8): # [0..7]
|
||||
d = timing_data.SB_del_rim_arr[i1][i2][i3][i4][i5]
|
||||
if d.rise.min == 123456: # not connected
|
||||
continue
|
||||
name = f"sb_rim_xy{i1-2}_s{i2+1}_p{i3+1}_d{i4}_s{i5}"
|
||||
val[name] = convert_delay(d)
|
||||
|
||||
|
||||
inputs_all = [ 'CLOCK0','CLOCK1','CLOCK2','CLOCK3',
|
||||
'SB_P1', 'SB_P2', 'SB_P3', 'SB_P4', 'SB_P5', 'SB_P6', 'SB_P7', 'SB_P8']
|
||||
inputs_left_bot = [ 'MDIE_P1', 'MDIE_P2', 'MDIE_P3', 'MDIE_P4', 'MDIE_P5', 'MDIE_P6', 'MDIE_P7', 'MDIE_P8' ]
|
||||
inputs_right_top = [ 'COUTX', 'COUTY1', 'COUTY2', 'POUTX', 'POUTY1', 'POUTY2', 'RAM_O1', 'RAM_O2' ]
|
||||
inputs_bot = [ 'P_CINY1', 'P_CINY2', 'P_PINY1', 'P_PINY2']
|
||||
outputs_right_top = [ 'MDIE_P1', 'MDIE_P2', 'MDIE_P3', 'MDIE_P4', 'MDIE_P5', 'MDIE_P6', 'MDIE_P7', 'MDIE_P8' ]
|
||||
outputs_left_bot = [ 'CINX', 'CINY1', 'CINY2', 'PINX', 'PINY1', 'PINY2', 'DUMMY', 'DUMMY']
|
||||
for i1 in range(165): # [-2..162]
|
||||
for i2 in range(4): # [1..4]
|
||||
inputs = inputs_all
|
||||
outputs = []
|
||||
match i2:
|
||||
case 0 | 1 : # right, top
|
||||
inputs += inputs_right_top
|
||||
inputs += [ 'DUMMY', 'DUMMY', 'DUMMY' ,'DUMMY']
|
||||
outputs += outputs_right_top
|
||||
case 2: # left
|
||||
inputs += inputs_left_bot
|
||||
inputs += [ 'DUMMY', 'DUMMY', 'DUMMY' ,'DUMMY']
|
||||
outputs += outputs_left_bot
|
||||
case 3: # bottom
|
||||
inputs += inputs_left_bot + inputs_bot
|
||||
outputs += outputs_left_bot
|
||||
for i3 in range(24): # [1..24]
|
||||
for i4 in range(8): # [1..8]
|
||||
d = timing_data.Edge_del_arr[i1][i2][i3][i4]
|
||||
if d.rise.min == 123456: # not connected
|
||||
continue
|
||||
name = f"edge_xy{i1-2}_s{i2+1}_{inputs[i3]}_{outputs[i4]}"
|
||||
val[name] = convert_delay(d)
|
||||
|
||||
inputs = [ 'CLOCK0','CLOCK1','CLOCK2','CLOCK3','OUT1_I','OUT2_I','OUT3_I','OUT4_I','GPIO_IN','RESET','DDR_I']
|
||||
outputs = [ 'IN1_O','IN2_O','GPIO_OUT','GPIO_EN' ]
|
||||
|
||||
for i1 in range(11): # [1..11]
|
||||
for i2 in range(4): # [1..4]
|
||||
d = timing_data.IO_SEL_del_arr[i1][i2]
|
||||
if d.rise.min == 123456: # not connected
|
||||
continue
|
||||
name = f"io_sel_{inputs[i1]}_{outputs[i2]}"
|
||||
val[name] = convert_delay(d)
|
||||
|
||||
|
||||
inputs = [ 'CLK0_I','CLK1_I','CLK2_I','CLK3_I','SERDES_CLK','SPI_CLK','JTAG_CLK']
|
||||
outputs = [ 'CLK_OUT0','CLK_OUT1','CLK_OUT2','CLK_OUT3' ]
|
||||
for i1 in range(7): # [1..7]
|
||||
for i2 in range(4): # [1..4]
|
||||
d = timing_data.CLKIN_del_arr[i1][i2]
|
||||
if d.rise.min == 123456: # not connected
|
||||
continue
|
||||
name = f"clkin_{inputs[i1]}_{outputs[i2]}"
|
||||
val[name] = convert_delay(d)
|
||||
|
||||
inputs = [ 'CLK0_0','CLK90_0','CLK180_0','CLK270_0','CLKREF_0',
|
||||
'CLK0_1','CLK90_1','CLK180_1','CLK270_1','CLKREF_1',
|
||||
'CLK0_2','CLK90_2','CLK180_2','CLK270_2','CLKREF_2',
|
||||
'CLK0_3','CLK90_3','CLK180_3','CLK270_3','CLKREF_3',
|
||||
'U_CLK0','U_CLK1','U_CLK2','U_CLK3',
|
||||
'U_FB0', 'U_FB1', 'U_FB2', 'U_FB3' ]
|
||||
outputs = [ 'CLOCK0','CLOCK1','CLOCK2','CLOCK3',
|
||||
'CLK_FB0','CLK_FB1','CLK_FB2','CLK_FB3']
|
||||
for i1 in range(28): # [1..28]
|
||||
for i2 in range(8): # [1..8]
|
||||
d = timing_data.GLBOUT_del_arr[i1][i2]
|
||||
if d.rise.min == 123456: # not connected
|
||||
continue
|
||||
name = f"glbout_{inputs[i1]}_{outputs[i2]}"
|
||||
val[name] = convert_delay(d)
|
||||
# All feedback delays calculated are same, we just take one
|
||||
val["glbout_FEEDBACK_delay"] = val["glbout_CLK0_0_CLK_FB0"] - val["glbout_CLK0_0_CLOCK0"]
|
||||
|
||||
inputs = ['clk_ref_i','clock_core0_i','adpll_enable_i','adpll_status_read_i','locked_steady_reset_i','autn_en_i','reset_n_i']
|
||||
outputs = ['clk_core0_o','clk_core90_o','clk_core180_o','clk_core270_o', 'pll_locked_o', 'pll_locked_steady_o']
|
||||
for i1 in range(7): # [1..7]
|
||||
for i2 in range(6): # [1..6]
|
||||
d = timing_data.PLL_del_arr[i1][i2]
|
||||
if d.rise.min == 123456: # not connected
|
||||
continue
|
||||
name = f"pll_{inputs[i1]}_{outputs[i2]}"
|
||||
val[name] = convert_delay(d)
|
||||
|
||||
for i in range(1,15):
|
||||
item = timing_data.FPGA_ram_del_1.del_entry[i]
|
||||
name = "RAM_NOECC_"
|
||||
match item.key:
|
||||
case 1:
|
||||
name += f"IOPATH_{i}"
|
||||
case 2:
|
||||
name += f"SETUPHOLD_{i-3}"
|
||||
case 4:
|
||||
name += "WIDTH"
|
||||
val[name] = convert_ram_delay(timing_data.FPGA_ram_del_1.del_entry[i])
|
||||
val["RAM_NOECC_IOPATH_4"] = Timing(TimingDelay(0,0,0), TimingDelay(0,0,0))
|
||||
|
||||
for i in range(1,16):
|
||||
item = timing_data.FPGA_ram_del_2.del_entry[i]
|
||||
name = "RAM_ECC_"
|
||||
match item.key:
|
||||
case 1:
|
||||
name += f"IOPATH_{i}"
|
||||
case 2:
|
||||
name += f"SETUPHOLD_{i-4}"
|
||||
case 4:
|
||||
name += "WIDTH"
|
||||
val[name] = convert_ram_delay(timing_data.FPGA_ram_del_2.del_entry[i])
|
||||
for i in range(1,16):
|
||||
item = timing_data.FPGA_ram_del_3.del_entry[i]
|
||||
name = "RAM_REG_"
|
||||
match item.key:
|
||||
case 1:
|
||||
name += f"IOPATH_{i}"
|
||||
case 2:
|
||||
name += f"SETUPHOLD_{i-4}"
|
||||
case 4:
|
||||
name += "WIDTH"
|
||||
val[name] = convert_ram_delay(timing_data.FPGA_ram_del_3.del_entry[i])
|
||||
|
||||
#val["del_rec_0"] = convert_delay(timing_data.timing_delays.del_rec_0.val)
|
||||
val["del_min_route_SB"] = convert_delay(timing_data.timing_delays.del_min_route_SB.val)
|
||||
val["del_violation_common"] = convert_delay_val(timing_data.timing_delays.del_violation_common.val)
|
||||
val["del_dummy"] = convert_delay(timing_data.timing_delays.del_dummy.val)
|
||||
val["del_Hold_D_L"] = convert_delay_val(timing_data.timing_delays.del_Hold_D_L.val)
|
||||
val["del_Setup_D_L"] = convert_delay_val(timing_data.timing_delays.del_Setup_D_L.val)
|
||||
val["del_Hold_RAM"] = convert_delay_val(timing_data.timing_delays.del_Hold_RAM.val)
|
||||
val["del_Setup_RAM"] = convert_delay_val(timing_data.timing_delays.del_Setup_RAM.val)
|
||||
|
||||
val["del_Hold_SN_RN"] = convert_delay_val(timing_data.timing_delays.del_Hold_SN_RN.val)
|
||||
val["del_Setup_SN_RN"] = convert_delay_val(timing_data.timing_delays.del_Setup_SN_RN.val)
|
||||
val["del_Hold_RN_SN"] = convert_delay_val(timing_data.timing_delays.del_Hold_RN_SN.val)
|
||||
val["del_Setup_RN_SN"] = convert_delay_val(timing_data.timing_delays.del_Setup_RN_SN.val)
|
||||
|
||||
val["del_bot_couty2"] = convert_delay(timing_data.timing_delays.del_bot_couty2.val)
|
||||
val["del_bot_glb_couty2"] = convert_delay(timing_data.timing_delays.del_bot_glb_couty2.val)
|
||||
val["del_bot_SB_couty2"] = convert_delay(timing_data.timing_delays.del_bot_SB_couty2.val)
|
||||
val["del_bot_pouty2"] = convert_delay(timing_data.timing_delays.del_bot_pouty2.val)
|
||||
val["del_bot_glb_pouty2"] = convert_delay(timing_data.timing_delays.del_bot_glb_pouty2.val)
|
||||
val["del_bot_SB_pouty2"] = convert_delay(timing_data.timing_delays.del_bot_SB_pouty2.val)
|
||||
|
||||
val["del_left_couty2"] = convert_delay(timing_data.timing_delays.del_left_couty2.val)
|
||||
val["del_left_glb_couty2"] = convert_delay(timing_data.timing_delays.del_left_glb_couty2.val)
|
||||
val["del_left_SB_couty2"] = convert_delay(timing_data.timing_delays.del_left_SB_couty2.val)
|
||||
val["del_left_pouty2"] = convert_delay(timing_data.timing_delays.del_left_pouty2.val)
|
||||
val["del_left_glb_pouty2"] = convert_delay(timing_data.timing_delays.del_left_glb_pouty2.val)
|
||||
val["del_left_SB_pouty2"] = convert_delay(timing_data.timing_delays.del_left_SB_pouty2.val)
|
||||
|
||||
val["del_CPE_CP_Q"] = convert_delay(timing_data.timing_delays.del_CPE_CP_Q.val)
|
||||
val["del_CPE_S_Q"] = convert_delay(timing_data.timing_delays.del_CPE_S_Q.val)
|
||||
val["del_CPE_R_Q"] = convert_delay(timing_data.timing_delays.del_CPE_R_Q.val)
|
||||
val["del_CPE_D_Q"] = convert_delay(timing_data.timing_delays.del_CPE_D_Q.val)
|
||||
|
||||
val["del_RAM_CLK_DO"] = convert_delay(timing_data.timing_delays.del_RAM_CLK_DO.val)
|
||||
|
||||
val["del_GLBOUT_sb_big"] = convert_delay(timing_data.timing_delays.del_GLBOUT_sb_big.val)
|
||||
|
||||
val["del_sb_drv"] = convert_delay(timing_data.timing_delays.del_sb_drv.val)
|
||||
|
||||
val["del_CP_carry_path"] = convert_delay(timing_data.timing_delays.del_CP_carry_path.val)
|
||||
val["del_CP_prop_path"] = convert_delay(timing_data.timing_delays.del_CP_prop_path.val)
|
||||
|
||||
|
||||
val["del_special_RAM_I"] = convert_delay(timing_data.timing_delays.del_special_RAM_I.val)
|
||||
val["del_RAMO_xOBF"] = convert_delay(timing_data.timing_delays.del_RAMO_xOBF.val)
|
||||
val["del_GLBOUT_IO_SEL"] = convert_delay(timing_data.timing_delays.del_GLBOUT_IO_SEL.val)
|
||||
|
||||
val["del_IO_SEL_Q_out"] = convert_delay(timing_data.timing_delays.del_IO_SEL_Q_out.val)
|
||||
val["del_IO_SEL_Q_in"] = convert_delay(timing_data.timing_delays.del_IO_SEL_Q_in.val)
|
||||
|
||||
val["in_delayline_per_stage"] = convert_delay(timing_data.timing_delays.in_delayline_per_stage.val)
|
||||
val["out_delayline_per_stage"] = convert_delay(timing_data.timing_delays.out_delayline_per_stage.val)
|
||||
|
||||
val["del_IBF"] = convert_delay(timing_data.timing_delays.del_IBF.val)
|
||||
|
||||
val["del_OBF"] = convert_delay(timing_data.timing_delays.del_OBF.val)
|
||||
val["del_r_OBF"] = convert_delay(timing_data.timing_delays.del_r_OBF.val)
|
||||
|
||||
val["del_TOBF_ctrl"] = convert_delay(timing_data.timing_delays.del_TOBF_ctrl.val)
|
||||
|
||||
val["del_LVDS_IBF"] = convert_delay(timing_data.timing_delays.del_LVDS_IBF.val)
|
||||
|
||||
val["del_LVDS_OBF"] = convert_delay(timing_data.timing_delays.del_LVDS_OBF.val)
|
||||
val["del_ddel_LVDS_r_OBFummy"] = convert_delay(timing_data.timing_delays.del_LVDS_r_OBF.val)
|
||||
|
||||
val["del_LVDS_TOBF_ctrl"] = convert_delay(timing_data.timing_delays.del_LVDS_TOBF_ctrl.val)
|
||||
|
||||
val["del_CP_clkin"] = convert_delay(timing_data.timing_delays.del_CP_clkin.val)
|
||||
val["del_CP_enin"] = convert_delay(timing_data.timing_delays.del_CP_enin.val)
|
||||
|
||||
#val["del_preplace"] = convert_delay(timing_data.timing_delays.del_preplace.val)
|
||||
|
||||
return val
|
||||
|
|
|
|||
503
gatemate/die.py
503
gatemate/die.py
|
|
@ -105,6 +105,19 @@ def is_edge_io(x,y):
|
|||
def is_ram(x,y):
|
||||
return x in [33,65,97,129] and y in [1,17,33,49,65,81,97,113]
|
||||
|
||||
def get_full_tile_loc_str(x,y):
|
||||
tile_x = ((x-1)+16) % 8 + 1
|
||||
tile_y = ((y-1)+16) % 8 + 1
|
||||
tile = ((((x+16-1) // 8)+2) % 4) + 1
|
||||
|
||||
return f"t{tile}_x{tile_x}_y{tile_y}"
|
||||
|
||||
def get_tile_loc_str(x,y):
|
||||
tile_x = ((x-1)+16) % 8 + 1
|
||||
tile_y = ((y-1)+16) % 8 + 1
|
||||
|
||||
return f"x{tile_x}_y{tile_y}"
|
||||
|
||||
@dataclass
|
||||
class IOName:
|
||||
bank : str
|
||||
|
|
@ -207,6 +220,7 @@ class MUX:
|
|||
invert: bool
|
||||
visible: bool
|
||||
config: bool
|
||||
delay: str
|
||||
|
||||
@dataclass
|
||||
class Location:
|
||||
|
|
@ -218,6 +232,7 @@ class Connection:
|
|||
x : int
|
||||
y : int
|
||||
name : str
|
||||
delay: str
|
||||
|
||||
@dataclass(eq=True, order=True)
|
||||
class TileInfo:
|
||||
|
|
@ -906,6 +921,10 @@ PRIMITIVES_PINS = {
|
|||
Pin("FRD_ADDRX[14]", PinType.OUTPUT,"RAM_WIRE"),
|
||||
Pin("FRD_ADDR[15]", PinType.OUTPUT,"RAM_WIRE"),
|
||||
Pin("FRD_ADDRX[15]", PinType.OUTPUT,"RAM_WIRE"),
|
||||
Pin("CLOCK1", PinType.INPUT,"RAM_WIRE"),
|
||||
Pin("CLOCK2", PinType.INPUT,"RAM_WIRE"),
|
||||
Pin("CLOCK3", PinType.INPUT,"RAM_WIRE"),
|
||||
Pin("CLOCK4", PinType.INPUT,"RAM_WIRE"),
|
||||
],
|
||||
"SERDES" : [
|
||||
Pin("TX_DETECT_RX_I", PinType.INPUT,"SERDES_WIRE"),
|
||||
|
|
@ -2565,9 +2584,9 @@ def get_endpoints_for_type(type):
|
|||
|
||||
def get_mux_connections_for_type(type):
|
||||
muxes = []
|
||||
def create_mux(src, dst, bits, value, invert, name = None, visible = True, config = False):
|
||||
def create_mux(src, dst, bits, value, invert, name = None, visible = True, config = False, delay = ""):
|
||||
name = dst if name is None else name
|
||||
muxes.append(MUX(src, dst, name, bits, value, invert, visible, config))
|
||||
muxes.append(MUX(src, dst, name, bits, value, invert, visible, config, delay))
|
||||
|
||||
if "CPE" in type:
|
||||
# CPE
|
||||
|
|
@ -2588,58 +2607,60 @@ def get_mux_connections_for_type(type):
|
|||
if "SB_BIG" in type:
|
||||
# SB_BIG
|
||||
for p in range(1,13):
|
||||
delay = f"sb_del_t1_x1_y1"
|
||||
plane = f"{p:02d}"
|
||||
# Per Y output mux
|
||||
for i in range(1,5):
|
||||
create_mux(f"SB_BIG.P{plane}.D0", f"SB_BIG.P{plane}.Y{i}", 3, 0, True)
|
||||
create_mux(f"SB_BIG.P{plane}.YDIAG", f"SB_BIG.P{plane}.Y{i}", 3, 1, True)
|
||||
create_mux(f"SB_BIG.P{plane}.D2_{i}", f"SB_BIG.P{plane}.Y{i}", 3, 2, True)
|
||||
create_mux(f"SB_BIG.P{plane}.D3_{i}", f"SB_BIG.P{plane}.Y{i}", 3, 3, True)
|
||||
create_mux(f"SB_BIG.P{plane}.D4_{i}", f"SB_BIG.P{plane}.Y{i}", 3, 4, True)
|
||||
create_mux(f"SB_BIG.P{plane}.D5_{i}", f"SB_BIG.P{plane}.Y{i}", 3, 5, True)
|
||||
create_mux(f"SB_BIG.P{plane}.D6_{i}", f"SB_BIG.P{plane}.Y{i}", 3, 6, True)
|
||||
create_mux(f"SB_BIG.P{plane}.D7_{i}", f"SB_BIG.P{plane}.Y{i}", 3, 7, True)
|
||||
create_mux(f"SB_BIG.P{plane}.D0", f"SB_BIG.P{plane}.Y{i}", 3, 0, True, delay="del_dummy")
|
||||
create_mux(f"SB_BIG.P{plane}.YDIAG", f"SB_BIG.P{plane}.Y{i}", 3, 1, True, delay=f"{delay}_p{p}_d1_s1")
|
||||
create_mux(f"SB_BIG.P{plane}.D2_{i}", f"SB_BIG.P{plane}.Y{i}", 3, 2, True, delay="del_dummy")
|
||||
create_mux(f"SB_BIG.P{plane}.D3_{i}", f"SB_BIG.P{plane}.Y{i}", 3, 3, True, delay="del_dummy")
|
||||
create_mux(f"SB_BIG.P{plane}.D4_{i}", f"SB_BIG.P{plane}.Y{i}", 3, 4, True, delay="del_dummy")
|
||||
create_mux(f"SB_BIG.P{plane}.D5_{i}", f"SB_BIG.P{plane}.Y{i}", 3, 5, True, delay="del_dummy")
|
||||
create_mux(f"SB_BIG.P{plane}.D6_{i}", f"SB_BIG.P{plane}.Y{i}", 3, 6, True, delay="del_dummy")
|
||||
create_mux(f"SB_BIG.P{plane}.D7_{i}", f"SB_BIG.P{plane}.Y{i}", 3, 7, True, delay="del_dummy")
|
||||
|
||||
# YDIAG output mux
|
||||
create_mux(f"SB_BIG.P{plane}.Y1", f"SB_BIG.P{plane}.YDIAG", 3, 0, True)
|
||||
create_mux(f"SB_BIG.P{plane}.Y2", f"SB_BIG.P{plane}.YDIAG", 3, 1, True)
|
||||
create_mux(f"SB_BIG.P{plane}.Y3", f"SB_BIG.P{plane}.YDIAG", 3, 2, True)
|
||||
create_mux(f"SB_BIG.P{plane}.Y4", f"SB_BIG.P{plane}.YDIAG", 3, 3, True)
|
||||
create_mux(f"SB_BIG.P{plane}.X34", f"SB_BIG.P{plane}.YDIAG", 3, 4, True)
|
||||
create_mux(f"SB_BIG.P{plane}.X14", f"SB_BIG.P{plane}.YDIAG", 3, 5, True)
|
||||
create_mux(f"SB_BIG.P{plane}.X12", f"SB_BIG.P{plane}.YDIAG", 3, 6, True)
|
||||
create_mux(f"SB_BIG.P{plane}.X23", f"SB_BIG.P{plane}.YDIAG", 3, 7, True)
|
||||
create_mux(f"SB_BIG.P{plane}.Y1", f"SB_BIG.P{plane}.YDIAG", 3, 0, True, delay=f"{delay}_p{p}_d0_s0")
|
||||
create_mux(f"SB_BIG.P{plane}.Y2", f"SB_BIG.P{plane}.YDIAG", 3, 1, True, delay=f"{delay}_p{p}_d0_s1")
|
||||
create_mux(f"SB_BIG.P{plane}.Y3", f"SB_BIG.P{plane}.YDIAG", 3, 2, True, delay=f"{delay}_p{p}_d0_s2")
|
||||
create_mux(f"SB_BIG.P{plane}.Y4", f"SB_BIG.P{plane}.YDIAG", 3, 3, True, delay=f"{delay}_p{p}_d0_s3")
|
||||
create_mux(f"SB_BIG.P{plane}.X34", f"SB_BIG.P{plane}.YDIAG", 3, 4, True, delay="del_dummy")
|
||||
create_mux(f"SB_BIG.P{plane}.X14", f"SB_BIG.P{plane}.YDIAG", 3, 5, True, delay="del_dummy")
|
||||
create_mux(f"SB_BIG.P{plane}.X12", f"SB_BIG.P{plane}.YDIAG", 3, 6, True, delay="del_dummy")
|
||||
create_mux(f"SB_BIG.P{plane}.X23", f"SB_BIG.P{plane}.YDIAG", 3, 7, True, delay="del_dummy")
|
||||
|
||||
for i in range(1,5):
|
||||
create_mux(f"SB_DRIVE.P{plane}.D{i}.IN", f"SB_DRIVE.P{plane}.D{i}.OUT", 1, 1, True, f"SB_DRIVE.P{plane}.D{i}")
|
||||
create_mux(f"SB_DRIVE.P{plane}.D{i}.IN", f"SB_DRIVE.P{plane}.D{i}.OUT_NOINV", 1, 1, False, f"SB_DRIVE.P{plane}.D{i}")
|
||||
create_mux(f"SB_DRIVE.P{plane}.D{i}.IN", f"SB_DRIVE.P{plane}.D{i}.OUT", 1, 1, True, f"SB_DRIVE.P{plane}.D{i}", delay="del_sb_drv")
|
||||
create_mux(f"SB_DRIVE.P{plane}.D{i}.IN", f"SB_DRIVE.P{plane}.D{i}.OUT_NOINV", 1, 1, False, f"SB_DRIVE.P{plane}.D{i}", delay="del_sb_drv")
|
||||
|
||||
if "SB_SML" in type:
|
||||
# SB_SML
|
||||
for p in range(1,13):
|
||||
delay = f"sb_del_t1_x1_y1"
|
||||
plane = f"{p:02d}"
|
||||
# Per Y output mux
|
||||
for i in range(1,5):
|
||||
create_mux(f"SB_SML.P{plane}.D0", f"SB_SML.P{plane}.Y{i}_int", 2, 0, False, f"SB_SML.P{plane}.Y{i}")
|
||||
create_mux(f"SB_SML.P{plane}.YDIAG_int",f"SB_SML.P{plane}.Y{i}_int", 2, 1, False, f"SB_SML.P{plane}.Y{i}")
|
||||
create_mux(f"SB_SML.P{plane}.D2_{i}", f"SB_SML.P{plane}.Y{i}_int", 2, 2, False, f"SB_SML.P{plane}.Y{i}")
|
||||
create_mux(f"SB_SML.P{plane}.D3_{i}", f"SB_SML.P{plane}.Y{i}_int", 2, 3, False, f"SB_SML.P{plane}.Y{i}")
|
||||
create_mux(f"SB_SML.P{plane}.D0", f"SB_SML.P{plane}.Y{i}_int", 2, 0, False, f"SB_SML.P{plane}.Y{i}", delay="del_dummy")
|
||||
create_mux(f"SB_SML.P{plane}.YDIAG_int",f"SB_SML.P{plane}.Y{i}_int", 2, 1, False, f"SB_SML.P{plane}.Y{i}", delay=f"{delay}_p{p}_d1_s1")
|
||||
create_mux(f"SB_SML.P{plane}.D2_{i}", f"SB_SML.P{plane}.Y{i}_int", 2, 2, False, f"SB_SML.P{plane}.Y{i}", delay="del_dummy")
|
||||
create_mux(f"SB_SML.P{plane}.D3_{i}", f"SB_SML.P{plane}.Y{i}_int", 2, 3, False, f"SB_SML.P{plane}.Y{i}", delay="del_dummy")
|
||||
|
||||
# YDIAG output mux
|
||||
create_mux(f"SB_SML.P{plane}.Y1_int", f"SB_SML.P{plane}.YDIAG_int", 3, 0, False, f"SB_SML.P{plane}.YDIAG")
|
||||
create_mux(f"SB_SML.P{plane}.Y2_int", f"SB_SML.P{plane}.YDIAG_int", 3, 1, False, f"SB_SML.P{plane}.YDIAG")
|
||||
create_mux(f"SB_SML.P{plane}.Y3_int", f"SB_SML.P{plane}.YDIAG_int", 3, 2, False, f"SB_SML.P{plane}.YDIAG")
|
||||
create_mux(f"SB_SML.P{plane}.Y4_int", f"SB_SML.P{plane}.YDIAG_int", 3, 3, False, f"SB_SML.P{plane}.YDIAG")
|
||||
create_mux(f"SB_SML.P{plane}.X34", f"SB_SML.P{plane}.YDIAG_int", 3, 4, False, f"SB_SML.P{plane}.YDIAG")
|
||||
create_mux(f"SB_SML.P{plane}.X14", f"SB_SML.P{plane}.YDIAG_int", 3, 5, False, f"SB_SML.P{plane}.YDIAG")
|
||||
create_mux(f"SB_SML.P{plane}.X12", f"SB_SML.P{plane}.YDIAG_int", 3, 6, False, f"SB_SML.P{plane}.YDIAG")
|
||||
create_mux(f"SB_SML.P{plane}.X23", f"SB_SML.P{plane}.YDIAG_int", 3, 7, False, f"SB_SML.P{plane}.YDIAG")
|
||||
create_mux(f"SB_SML.P{plane}.Y1_int", f"SB_SML.P{plane}.YDIAG_int", 3, 0, False, f"SB_SML.P{plane}.YDIAG", delay=f"{delay}_p{p}_d0_s0")
|
||||
create_mux(f"SB_SML.P{plane}.Y2_int", f"SB_SML.P{plane}.YDIAG_int", 3, 1, False, f"SB_SML.P{plane}.YDIAG", delay=f"{delay}_p{p}_d0_s1")
|
||||
create_mux(f"SB_SML.P{plane}.Y3_int", f"SB_SML.P{plane}.YDIAG_int", 3, 2, False, f"SB_SML.P{plane}.YDIAG", delay=f"{delay}_p{p}_d0_s2")
|
||||
create_mux(f"SB_SML.P{plane}.Y4_int", f"SB_SML.P{plane}.YDIAG_int", 3, 3, False, f"SB_SML.P{plane}.YDIAG", delay=f"{delay}_p{p}_d0_s3")
|
||||
create_mux(f"SB_SML.P{plane}.X34", f"SB_SML.P{plane}.YDIAG_int", 3, 4, False, f"SB_SML.P{plane}.YDIAG", delay="del_dummy")
|
||||
create_mux(f"SB_SML.P{plane}.X14", f"SB_SML.P{plane}.YDIAG_int", 3, 5, False, f"SB_SML.P{plane}.YDIAG", delay="del_dummy")
|
||||
create_mux(f"SB_SML.P{plane}.X12", f"SB_SML.P{plane}.YDIAG_int", 3, 6, False, f"SB_SML.P{plane}.YDIAG", delay="del_dummy")
|
||||
create_mux(f"SB_SML.P{plane}.X23", f"SB_SML.P{plane}.YDIAG_int", 3, 7, False, f"SB_SML.P{plane}.YDIAG", delay="del_dummy")
|
||||
|
||||
create_mux(f"SB_SML.P{plane}.Y1_int", f"SB_SML.P{plane}.Y1", 1, 1, True, f"SB_SML.P{plane}.Y1_INT", False)
|
||||
create_mux(f"SB_SML.P{plane}.Y2_int", f"SB_SML.P{plane}.Y2", 1, 1, True, f"SB_SML.P{plane}.Y2_INT", False)
|
||||
create_mux(f"SB_SML.P{plane}.Y3_int", f"SB_SML.P{plane}.Y3", 1, 1, True, f"SB_SML.P{plane}.Y3_INT", False)
|
||||
create_mux(f"SB_SML.P{plane}.Y4_int", f"SB_SML.P{plane}.Y4", 1, 1, True, f"SB_SML.P{plane}.Y4_INT", False)
|
||||
create_mux(f"SB_SML.P{plane}.YDIAG_int", f"SB_SML.P{plane}.YDIAG", 1, 1, True, f"SB_SML.P{plane}.YDIAG_INT", False)
|
||||
create_mux(f"SB_SML.P{plane}.Y1_int", f"SB_SML.P{plane}.Y1", 1, 1, True, f"SB_SML.P{plane}.Y1_INT", False, delay="del_dummy")
|
||||
create_mux(f"SB_SML.P{plane}.Y2_int", f"SB_SML.P{plane}.Y2", 1, 1, True, f"SB_SML.P{plane}.Y2_INT", False, delay="del_dummy")
|
||||
create_mux(f"SB_SML.P{plane}.Y3_int", f"SB_SML.P{plane}.Y3", 1, 1, True, f"SB_SML.P{plane}.Y3_INT", False, delay="del_dummy")
|
||||
create_mux(f"SB_SML.P{plane}.Y4_int", f"SB_SML.P{plane}.Y4", 1, 1, True, f"SB_SML.P{plane}.Y4_INT", False, delay="del_dummy")
|
||||
create_mux(f"SB_SML.P{plane}.YDIAG_int", f"SB_SML.P{plane}.YDIAG", 1, 1, True, f"SB_SML.P{plane}.YDIAG_INT", False, delay="del_dummy")
|
||||
|
||||
#if "GPIO" in type:
|
||||
# # GPIO
|
||||
|
|
@ -2653,225 +2674,225 @@ def get_mux_connections_for_type(type):
|
|||
|
||||
if "LES" in type:
|
||||
for p in range(1,9):
|
||||
create_mux(f"LES.SB_Y3.P{p}", "LES.SB_Y3_SEL1_int", 3, p-1, False, "LES.SB_Y3_SEL1")
|
||||
create_mux(f"LES.MDIE1.P{p}", "LES.MDIE1_SEL1_int", 3, p-1, False, "LES.MDIE1_SEL1")
|
||||
create_mux(f"LES.SB_Y3.P{p}", "LES.SB_Y3_SEL2_int", 3, p-1, False, "LES.SB_Y3_SEL2")
|
||||
create_mux(f"LES.MDIE1.P{p}", "LES.MDIE1_SEL2_int", 3, p-1, False, "LES.MDIE1_SEL2")
|
||||
create_mux(f"LES.SB_Y3.P{p}", "LES.SB_Y3_SEL1_int", 3, p-1, False, "LES.SB_Y3_SEL1", delay="del_dummy")
|
||||
create_mux(f"LES.MDIE1.P{p}", "LES.MDIE1_SEL1_int", 3, p-1, False, "LES.MDIE1_SEL1", delay="del_dummy")
|
||||
create_mux(f"LES.SB_Y3.P{p}", "LES.SB_Y3_SEL2_int", 3, p-1, False, "LES.SB_Y3_SEL2", delay="del_dummy")
|
||||
create_mux(f"LES.MDIE1.P{p}", "LES.MDIE1_SEL2_int", 3, p-1, False, "LES.MDIE1_SEL2", delay="del_dummy")
|
||||
for i in range(4):
|
||||
create_mux(f"LES.CLOCK{i}", "LES.CLOCK_SEL1_int", 2, i, False, "LES.CLOCK_SEL1")
|
||||
create_mux(f"LES.CLOCK{i}", "LES.CLOCK_SEL2_int", 2, i, False, "LES.CLOCK_SEL2")
|
||||
create_mux(f"LES.CLOCK{i}", "LES.CLOCK_SEL1_int", 2, i, False, "LES.CLOCK_SEL1", delay="del_dummy")
|
||||
create_mux(f"LES.CLOCK{i}", "LES.CLOCK_SEL2_int", 2, i, False, "LES.CLOCK_SEL2", delay="del_dummy")
|
||||
|
||||
create_mux("LES.SB_Y3_SEL1_int", "LES.CPE_CINX", 2, 1, False, "LES.CINX_SEL")
|
||||
create_mux("LES.MDIE1_SEL1_int", "LES.CPE_CINX", 2, 2, False, "LES.CINX_SEL")
|
||||
create_mux("LES.CLOCK_SEL1_int", "LES.CPE_CINX", 2, 3, False, "LES.CINX_SEL")
|
||||
create_mux("LES.SB_Y3_SEL1_int", "LES.CPE_CINX", 2, 1, False, "LES.CINX_SEL", delay="del_left_SB_couty2")
|
||||
create_mux("LES.MDIE1_SEL1_int", "LES.CPE_CINX", 2, 2, False, "LES.CINX_SEL", delay="del_left_couty2")
|
||||
create_mux("LES.CLOCK_SEL1_int", "LES.CPE_CINX", 2, 3, False, "LES.CINX_SEL", delay="del_left_glb_couty2")
|
||||
|
||||
create_mux("LES.SB_Y3_SEL2_int", "LES.CPE_PINX", 2, 1, False, "LES.PINX_SEL")
|
||||
create_mux("LES.MDIE1_SEL2_int", "LES.CPE_PINX", 2, 2, False, "LES.PINX_SEL")
|
||||
create_mux("LES.CLOCK_SEL2_int", "LES.CPE_PINX", 2, 3, False, "LES.PINX_SEL")
|
||||
create_mux("LES.SB_Y3_SEL2_int", "LES.CPE_PINX", 2, 1, False, "LES.PINX_SEL", delay="del_left_SB_pouty2")
|
||||
create_mux("LES.MDIE1_SEL2_int", "LES.CPE_PINX", 2, 2, False, "LES.PINX_SEL", delay="del_left_pouty2")
|
||||
create_mux("LES.CLOCK_SEL2_int", "LES.CPE_PINX", 2, 3, False, "LES.PINX_SEL", delay="del_left_glb_pouty2")
|
||||
|
||||
if "BES" in type:
|
||||
for p in range(1,9):
|
||||
create_mux(f"BES.SB_Y4.P{p}", "BES.SB_Y4_SEL1_int", 3, p-1, False, "BES.SB_Y4_SEL1")
|
||||
create_mux(f"BES.MDIE2.P{p}", "BES.MDIE2_SEL1_int", 3, p-1, False, "BES.MDIE2_SEL1")
|
||||
create_mux(f"BES.SB_Y4.P{p}", "BES.SB_Y4_SEL2_int", 3, p-1, False, "BES.SB_Y4_SEL2")
|
||||
create_mux(f"BES.MDIE2.P{p}", "BES.MDIE2_SEL2_int", 3, p-1, False, "BES.MDIE2_SEL2")
|
||||
create_mux(f"BES.SB_Y4.P{p}", "BES.SB_Y4_SEL3_int", 3, p-1, False, "BES.SB_Y4_SEL3")
|
||||
create_mux(f"BES.MDIE2.P{p}", "BES.MDIE2_SEL3_int", 3, p-1, False, "BES.MDIE2_SEL3")
|
||||
create_mux(f"BES.SB_Y4.P{p}", "BES.SB_Y4_SEL4_int", 3, p-1, False, "BES.SB_Y4_SEL4")
|
||||
create_mux(f"BES.MDIE2.P{p}", "BES.MDIE2_SEL4_int", 3, p-1, False, "BES.MDIE2_SEL4")
|
||||
create_mux(f"BES.SB_Y4.P{p}", "BES.SB_Y4_SEL1_int", 3, p-1, False, "BES.SB_Y4_SEL1", delay="del_dummy")
|
||||
create_mux(f"BES.MDIE2.P{p}", "BES.MDIE2_SEL1_int", 3, p-1, False, "BES.MDIE2_SEL1", delay="del_dummy")
|
||||
create_mux(f"BES.SB_Y4.P{p}", "BES.SB_Y4_SEL2_int", 3, p-1, False, "BES.SB_Y4_SEL2", delay="del_dummy")
|
||||
create_mux(f"BES.MDIE2.P{p}", "BES.MDIE2_SEL2_int", 3, p-1, False, "BES.MDIE2_SEL2", delay="del_dummy")
|
||||
create_mux(f"BES.SB_Y4.P{p}", "BES.SB_Y4_SEL3_int", 3, p-1, False, "BES.SB_Y4_SEL3", delay="del_dummy")
|
||||
create_mux(f"BES.MDIE2.P{p}", "BES.MDIE2_SEL3_int", 3, p-1, False, "BES.MDIE2_SEL3", delay="del_dummy")
|
||||
create_mux(f"BES.SB_Y4.P{p}", "BES.SB_Y4_SEL4_int", 3, p-1, False, "BES.SB_Y4_SEL4", delay="del_dummy")
|
||||
create_mux(f"BES.MDIE2.P{p}", "BES.MDIE2_SEL4_int", 3, p-1, False, "BES.MDIE2_SEL4", delay="del_dummy")
|
||||
for i in range(4):
|
||||
create_mux(f"BES.CLOCK{i}", "BES.CLOCK_SEL1_int", 2, i, False, "BES.CLOCK_SEL1")
|
||||
create_mux(f"BES.CLOCK{i}", "BES.CLOCK_SEL2_int", 2, i, False, "BES.CLOCK_SEL2")
|
||||
create_mux(f"BES.CLOCK{i}", "BES.CLOCK_SEL3_int", 2, i, False, "BES.CLOCK_SEL3")
|
||||
create_mux(f"BES.CLOCK{i}", "BES.CLOCK_SEL4_int", 2, i, False, "BES.CLOCK_SEL4")
|
||||
create_mux(f"BES.CLOCK{i}", "BES.CLOCK_SEL1_int", 2, i, False, "BES.CLOCK_SEL1", delay="del_dummy")
|
||||
create_mux(f"BES.CLOCK{i}", "BES.CLOCK_SEL2_int", 2, i, False, "BES.CLOCK_SEL2", delay="del_dummy")
|
||||
create_mux(f"BES.CLOCK{i}", "BES.CLOCK_SEL3_int", 2, i, False, "BES.CLOCK_SEL3", delay="del_dummy")
|
||||
create_mux(f"BES.CLOCK{i}", "BES.CLOCK_SEL4_int", 2, i, False, "BES.CLOCK_SEL4", delay="del_dummy")
|
||||
|
||||
create_mux("BES.SB_Y4_SEL1_int", "BES.CPE_CINY1_int", 2, 1, False, "BES.CINY1_SEL")
|
||||
create_mux("BES.MDIE2_SEL1_int", "BES.CPE_CINY1_int", 2, 2, False, "BES.CINY1_SEL")
|
||||
create_mux("BES.CLOCK_SEL1_int", "BES.CPE_CINY1_int", 2, 3, False, "BES.CINY1_SEL")
|
||||
create_mux("BES.SB_Y4_SEL2_int", "BES.CPE_PINY1_int", 2, 1, False, "BES.PINY1_SEL")
|
||||
create_mux("BES.MDIE2_SEL2_int", "BES.CPE_PINY1_int", 2, 2, False, "BES.PINY1_SEL")
|
||||
create_mux("BES.CLOCK_SEL2_int", "BES.CPE_PINY1_int", 2, 3, False, "BES.PINY1_SEL")
|
||||
create_mux("BES.SB_Y4_SEL3_int", "BES.CPE_CINY2_int", 2, 1, False, "BES.CINY2_SEL")
|
||||
create_mux("BES.MDIE2_SEL3_int", "BES.CPE_CINY2_int", 2, 2, False, "BES.CINY2_SEL")
|
||||
create_mux("BES.CLOCK_SEL3_int", "BES.CPE_CINY2_int", 2, 3, False, "BES.CINY2_SEL")
|
||||
create_mux("BES.SB_Y4_SEL4_int", "BES.CPE_PINY2_int", 2, 1, False, "BES.PINY2_SEL")
|
||||
create_mux("BES.MDIE2_SEL4_int", "BES.CPE_PINY2_int", 2, 2, False, "BES.PINY2_SEL")
|
||||
create_mux("BES.CLOCK_SEL4_int", "BES.CPE_PINY2_int", 2, 3, False, "BES.PINY2_SEL")
|
||||
create_mux("BES.SB_Y4_SEL1_int", "BES.CPE_CINY1_int", 2, 1, False, "BES.CINY1_SEL", delay="del_bot_SB_couty2")
|
||||
create_mux("BES.MDIE2_SEL1_int", "BES.CPE_CINY1_int", 2, 2, False, "BES.CINY1_SEL", delay="del_bot_couty2")
|
||||
create_mux("BES.CLOCK_SEL1_int", "BES.CPE_CINY1_int", 2, 3, False, "BES.CINY1_SEL", delay="del_bot_glb_couty2")
|
||||
create_mux("BES.SB_Y4_SEL2_int", "BES.CPE_PINY1_int", 2, 1, False, "BES.PINY1_SEL", delay="del_bot_SB_pouty2")
|
||||
create_mux("BES.MDIE2_SEL2_int", "BES.CPE_PINY1_int", 2, 2, False, "BES.PINY1_SEL", delay="del_bot_pouty2")
|
||||
create_mux("BES.CLOCK_SEL2_int", "BES.CPE_PINY1_int", 2, 3, False, "BES.PINY1_SEL", delay="del_bot_glb_pouty2")
|
||||
create_mux("BES.SB_Y4_SEL3_int", "BES.CPE_CINY2_int", 2, 1, False, "BES.CINY2_SEL", delay="del_bot_SB_couty2")
|
||||
create_mux("BES.MDIE2_SEL3_int", "BES.CPE_CINY2_int", 2, 2, False, "BES.CINY2_SEL", delay="del_bot_couty2")
|
||||
create_mux("BES.CLOCK_SEL3_int", "BES.CPE_CINY2_int", 2, 3, False, "BES.CINY2_SEL", delay="del_bot_glb_couty2")
|
||||
create_mux("BES.SB_Y4_SEL4_int", "BES.CPE_PINY2_int", 2, 1, False, "BES.PINY2_SEL", delay="del_bot_SB_pouty2")
|
||||
create_mux("BES.MDIE2_SEL4_int", "BES.CPE_PINY2_int", 2, 2, False, "BES.PINY2_SEL", delay="del_bot_pouty2")
|
||||
create_mux("BES.CLOCK_SEL4_int", "BES.CPE_PINY2_int", 2, 3, False, "BES.PINY2_SEL", delay="del_bot_glb_pouty2")
|
||||
|
||||
create_mux("BES.CPE_CINY1_int", "BES.CPE_CINY1", 1, 0, False, "BES.P_CINY1")
|
||||
create_mux("BES.P_CINY1", "BES.CPE_CINY1", 1, 1, False, "BES.P_CINY1")
|
||||
create_mux("BES.CPE_PINY1_int", "BES.CPE_PINY1", 1, 0, False, "BES.P_PINY1")
|
||||
create_mux("BES.P_PINY1", "BES.CPE_PINY1", 1, 1, False, "BES.P_PINY1")
|
||||
create_mux("BES.CPE_CINY2_int", "BES.CPE_CINY2", 1, 0, False, "BES.P_CINY2")
|
||||
create_mux("BES.P_CINY2", "BES.CPE_CINY2", 1, 1, False, "BES.P_CINY2")
|
||||
create_mux("BES.CPE_PINY2_int", "BES.CPE_PINY2", 1, 0, False, "BES.P_PINY2")
|
||||
create_mux("BES.P_PINY2", "BES.CPE_PINY2", 1, 1, False, "BES.P_PINY2")
|
||||
create_mux("BES.CPE_CINY1_int", "BES.CPE_CINY1", 1, 0, False, "BES.P_CINY1", delay="del_dummy")
|
||||
create_mux("BES.P_CINY1", "BES.CPE_CINY1", 1, 1, False, "BES.P_CINY1", delay="del_dummy")
|
||||
create_mux("BES.CPE_PINY1_int", "BES.CPE_PINY1", 1, 0, False, "BES.P_PINY1", delay="del_dummy")
|
||||
create_mux("BES.P_PINY1", "BES.CPE_PINY1", 1, 1, False, "BES.P_PINY1", delay="del_dummy")
|
||||
create_mux("BES.CPE_CINY2_int", "BES.CPE_CINY2", 1, 0, False, "BES.P_CINY2", delay="del_dummy")
|
||||
create_mux("BES.P_CINY2", "BES.CPE_CINY2", 1, 1, False, "BES.P_CINY2", delay="del_dummy")
|
||||
create_mux("BES.CPE_PINY2_int", "BES.CPE_PINY2", 1, 0, False, "BES.P_PINY2", delay="del_dummy")
|
||||
create_mux("BES.P_PINY2", "BES.CPE_PINY2", 1, 1, False, "BES.P_PINY2", delay="del_dummy")
|
||||
|
||||
if "RES" in type:
|
||||
for sel in range(4):
|
||||
create_mux("RES.CPE_RAM_O1", f"RES.SIG_SEL{sel+1}_int", 3, 0, False, f"RES.SIG_SEL{sel+1}")
|
||||
create_mux("RES.CPE_RAM_O2", f"RES.SIG_SEL{sel+1}_int", 3, 1, False, f"RES.SIG_SEL{sel+1}")
|
||||
create_mux("RES.CPE_COUTX", f"RES.SIG_SEL{sel+1}_int", 3, 2, False, f"RES.SIG_SEL{sel+1}")
|
||||
create_mux("RES.CPE_POUTX", f"RES.SIG_SEL{sel+1}_int", 3, 3, False, f"RES.SIG_SEL{sel+1}")
|
||||
create_mux("RES.CPE_RAM_O1", f"RES.SIG_SEL{sel+1}_int", 3, 0, False, f"RES.SIG_SEL{sel+1}", delay="del_dummy")
|
||||
create_mux("RES.CPE_RAM_O2", f"RES.SIG_SEL{sel+1}_int", 3, 1, False, f"RES.SIG_SEL{sel+1}", delay="del_dummy")
|
||||
create_mux("RES.CPE_COUTX", f"RES.SIG_SEL{sel+1}_int", 3, 2, False, f"RES.SIG_SEL{sel+1}", delay="del_dummy")
|
||||
create_mux("RES.CPE_POUTX", f"RES.SIG_SEL{sel+1}_int", 3, 3, False, f"RES.SIG_SEL{sel+1}", delay="del_dummy")
|
||||
for i in range(4):
|
||||
create_mux(f"RES.CLOCK{i}", f"RES.SIG_SEL{sel+1}_int", 3, 4 + i, False, f"RES.SIG_SEL{sel+1}")
|
||||
create_mux(f"RES.CLOCK{i}", f"RES.SIG_SEL{sel+1}_int", 3, 4 + i, False, f"RES.SIG_SEL{sel+1}", delay="del_dummy")
|
||||
|
||||
for p in range(1,9):
|
||||
create_mux(f"RES.SB_Y1.P{p}", f"RES.MDIE1.P{p}", 1, 0, False, f"RES.SEL_MDIE{p}")
|
||||
create_mux(f"RES.SB_Y1.P{p}", f"RES.MDIE1.P{p}", 1, 0, False, f"RES.SEL_MDIE{p}", delay="del_dummy")
|
||||
sel = (p - 1) // 2 + 1
|
||||
create_mux(f"RES.SIG_SEL{sel}_int", f"RES.MDIE1.P{p}", 1, 1, False, f"RES.SEL_MDIE{p}")
|
||||
create_mux(f"RES.SIG_SEL{sel}_int", f"RES.MDIE1.P{p}", 1, 1, False, f"RES.SEL_MDIE{p}", delay="del_dummy")
|
||||
|
||||
if "TES" in type:
|
||||
for sel in range(4):
|
||||
create_mux("TES.CPE_RAM_O1", f"TES.SIG_SEL{sel+1}_int", 3, 0, False, f"TES.SIG_SEL{sel+1}")
|
||||
create_mux("TES.CPE_RAM_O2", f"TES.SIG_SEL{sel+1}_int", 3, 1, False, f"TES.SIG_SEL{sel+1}")
|
||||
create_mux("TES.CPE_COUTY1", f"TES.SIG_SEL{sel+1}_int", 3, 2, False, f"TES.SIG_SEL{sel+1}")
|
||||
create_mux("TES.CPE_POUTY1", f"TES.SIG_SEL{sel+1}_int", 3, 3, False, f"TES.SIG_SEL{sel+1}")
|
||||
create_mux("TES.CPE_COUTY2", f"TES.SIG_SEL{sel+1}_int", 3, 4, False, f"TES.SIG_SEL{sel+1}")
|
||||
create_mux("TES.CPE_POUTY2", f"TES.SIG_SEL{sel+1}_int", 3, 5, False, f"TES.SIG_SEL{sel+1}")
|
||||
create_mux("TES.CPE_RAM_O1", f"TES.SIG_SEL{sel+1}_int", 3, 0, False, f"TES.SIG_SEL{sel+1}", delay="del_dummy")
|
||||
create_mux("TES.CPE_RAM_O2", f"TES.SIG_SEL{sel+1}_int", 3, 1, False, f"TES.SIG_SEL{sel+1}", delay="del_dummy")
|
||||
create_mux("TES.CPE_COUTY1", f"TES.SIG_SEL{sel+1}_int", 3, 2, False, f"TES.SIG_SEL{sel+1}", delay="del_dummy")
|
||||
create_mux("TES.CPE_POUTY1", f"TES.SIG_SEL{sel+1}_int", 3, 3, False, f"TES.SIG_SEL{sel+1}", delay="del_dummy")
|
||||
create_mux("TES.CPE_COUTY2", f"TES.SIG_SEL{sel+1}_int", 3, 4, False, f"TES.SIG_SEL{sel+1}", delay="del_dummy")
|
||||
create_mux("TES.CPE_POUTY2", f"TES.SIG_SEL{sel+1}_int", 3, 5, False, f"TES.SIG_SEL{sel+1}", delay="del_dummy")
|
||||
clk = 0 if sel < 2 else 2
|
||||
create_mux(f"TES.CLOCK{clk+0}", f"TES.SIG_SEL{sel+1}_int", 3, 6, False, f"TES.SIG_SEL{sel+1}")
|
||||
create_mux(f"TES.CLOCK{clk+1}", f"TES.SIG_SEL{sel+1}_int", 3, 7, False, f"TES.SIG_SEL{sel+1}")
|
||||
create_mux(f"TES.CLOCK{clk+0}", f"TES.SIG_SEL{sel+1}_int", 3, 6, False, f"TES.SIG_SEL{sel+1}", delay="del_dummy")
|
||||
create_mux(f"TES.CLOCK{clk+1}", f"TES.SIG_SEL{sel+1}_int", 3, 7, False, f"TES.SIG_SEL{sel+1}", delay="del_dummy")
|
||||
|
||||
for p in range(1,9):
|
||||
create_mux(f"TES.SB_Y2.P{p}", f"TES.MDIE2.P{p}", 1, 0, False, f"TES.SEL_MDIE{p}")
|
||||
create_mux(f"TES.SB_Y2.P{p}", f"TES.MDIE2.P{p}", 1, 0, False, f"TES.SEL_MDIE{p}", delay="del_dummy")
|
||||
sel = (p - 1) // 2 + 1
|
||||
create_mux(f"TES.SIG_SEL{sel}_int", f"TES.MDIE2.P{p}", 1, 1, False, f"TES.SEL_MDIE{p}")
|
||||
create_mux(f"TES.SIG_SEL{sel}_int", f"TES.MDIE2.P{p}", 1, 1, False, f"TES.SEL_MDIE{p}", delay="del_dummy")
|
||||
|
||||
if "PLL" in type:
|
||||
# CLKIN
|
||||
|
||||
create_mux("CLKIN.CLK0", "CLKIN.CLK_REF_INT0", 3, 0, False, "CLKIN.REF0", config=True)
|
||||
create_mux("CLKIN.CLK1", "CLKIN.CLK_REF_INT0", 3, 1, False, "CLKIN.REF0", config=True)
|
||||
create_mux("CLKIN.CLK2", "CLKIN.CLK_REF_INT0", 3, 2, False, "CLKIN.REF0", config=True)
|
||||
create_mux("CLKIN.CLK3", "CLKIN.CLK_REF_INT0", 3, 3, False, "CLKIN.REF0", config=True)
|
||||
create_mux("CLKIN.SER_CLK", "CLKIN.CLK_REF_INT0", 3, 4, False, "CLKIN.REF0", config=True)
|
||||
create_mux("CLKIN.CLK_REF_INT0", "CLKIN.CLK_REF_0", 1, 0, False, "CLKIN.REF0_INV", config=True)
|
||||
create_mux("CLKIN.CLK0", "CLKIN.CLK_REF_INT0", 3, 0, False, "CLKIN.REF0", config=True, delay="clkin_CLK0_I_CLK_OUT0")
|
||||
create_mux("CLKIN.CLK1", "CLKIN.CLK_REF_INT0", 3, 1, False, "CLKIN.REF0", config=True, delay="clkin_CLK1_I_CLK_OUT0")
|
||||
create_mux("CLKIN.CLK2", "CLKIN.CLK_REF_INT0", 3, 2, False, "CLKIN.REF0", config=True, delay="clkin_CLK2_I_CLK_OUT0")
|
||||
create_mux("CLKIN.CLK3", "CLKIN.CLK_REF_INT0", 3, 3, False, "CLKIN.REF0", config=True, delay="clkin_CLK3_I_CLK_OUT0")
|
||||
create_mux("CLKIN.SER_CLK", "CLKIN.CLK_REF_INT0", 3, 4, False, "CLKIN.REF0", config=True, delay="clkin_SERDES_CLK_CLK_OUT0")
|
||||
create_mux("CLKIN.CLK_REF_INT0", "CLKIN.CLK_REF_0", 1, 0, False, "CLKIN.REF0_INV", config=True, delay="del_dummy")
|
||||
|
||||
create_mux("CLKIN.CLK0", "CLKIN.CLK_REF_INT1", 3, 0, False, "CLKIN.REF1", config=True)
|
||||
create_mux("CLKIN.CLK1", "CLKIN.CLK_REF_INT1", 3, 1, False, "CLKIN.REF1", config=True)
|
||||
create_mux("CLKIN.CLK2", "CLKIN.CLK_REF_INT1", 3, 2, False, "CLKIN.REF1", config=True)
|
||||
create_mux("CLKIN.CLK3", "CLKIN.CLK_REF_INT1", 3, 3, False, "CLKIN.REF1", config=True)
|
||||
create_mux("CLKIN.SER_CLK", "CLKIN.CLK_REF_INT1", 3, 4, False, "CLKIN.REF1", config=True)
|
||||
create_mux("CLKIN.CLK_REF_INT1", "CLKIN.CLK_REF_1", 1, 0, False, "CLKIN.REF1_INV", config=True)
|
||||
create_mux("CLKIN.CLK0", "CLKIN.CLK_REF_INT1", 3, 0, False, "CLKIN.REF1", config=True, delay="clkin_CLK0_I_CLK_OUT1")
|
||||
create_mux("CLKIN.CLK1", "CLKIN.CLK_REF_INT1", 3, 1, False, "CLKIN.REF1", config=True, delay="clkin_CLK1_I_CLK_OUT1")
|
||||
create_mux("CLKIN.CLK2", "CLKIN.CLK_REF_INT1", 3, 2, False, "CLKIN.REF1", config=True, delay="clkin_CLK2_I_CLK_OUT1")
|
||||
create_mux("CLKIN.CLK3", "CLKIN.CLK_REF_INT1", 3, 3, False, "CLKIN.REF1", config=True, delay="clkin_CLK3_I_CLK_OUT1")
|
||||
create_mux("CLKIN.SER_CLK", "CLKIN.CLK_REF_INT1", 3, 4, False, "CLKIN.REF1", config=True, delay="clkin_SERDES_CLK_CLK_OUT1")
|
||||
create_mux("CLKIN.CLK_REF_INT1", "CLKIN.CLK_REF_1", 1, 0, False, "CLKIN.REF1_INV", config=True, delay="del_dummy")
|
||||
|
||||
create_mux("CLKIN.CLK0", "CLKIN.CLK_REF_INT2", 3, 0, False, "CLKIN.REF2", config=True)
|
||||
create_mux("CLKIN.CLK1", "CLKIN.CLK_REF_INT2", 3, 1, False, "CLKIN.REF2", config=True)
|
||||
create_mux("CLKIN.CLK2", "CLKIN.CLK_REF_INT2", 3, 2, False, "CLKIN.REF2", config=True)
|
||||
create_mux("CLKIN.CLK3", "CLKIN.CLK_REF_INT2", 3, 3, False, "CLKIN.REF2", config=True)
|
||||
create_mux("CLKIN.SER_CLK", "CLKIN.CLK_REF_INT2", 3, 4, False, "CLKIN.REF2", config=True)
|
||||
create_mux("CLKIN.CLK_REF_INT2", "CLKIN.CLK_REF_2", 1, 0, False, "CLKIN.REF2_INV", config=True)
|
||||
create_mux("CLKIN.CLK0", "CLKIN.CLK_REF_INT2", 3, 0, False, "CLKIN.REF2", config=True, delay="clkin_CLK0_I_CLK_OUT2")
|
||||
create_mux("CLKIN.CLK1", "CLKIN.CLK_REF_INT2", 3, 1, False, "CLKIN.REF2", config=True, delay="clkin_CLK1_I_CLK_OUT2")
|
||||
create_mux("CLKIN.CLK2", "CLKIN.CLK_REF_INT2", 3, 2, False, "CLKIN.REF2", config=True, delay="clkin_CLK2_I_CLK_OUT2")
|
||||
create_mux("CLKIN.CLK3", "CLKIN.CLK_REF_INT2", 3, 3, False, "CLKIN.REF2", config=True, delay="clkin_CLK3_I_CLK_OUT2")
|
||||
create_mux("CLKIN.SER_CLK", "CLKIN.CLK_REF_INT2", 3, 4, False, "CLKIN.REF2", config=True, delay="clkin_SERDES_CLK_CLK_OUT2")
|
||||
create_mux("CLKIN.CLK_REF_INT2", "CLKIN.CLK_REF_2", 1, 0, False, "CLKIN.REF2_INV", config=True, delay="del_dummy")
|
||||
|
||||
create_mux("CLKIN.CLK0", "CLKIN.CLK_REF_INT3", 3, 0, False, "CLKIN.REF3", config=True)
|
||||
create_mux("CLKIN.CLK1", "CLKIN.CLK_REF_INT3", 3, 1, False, "CLKIN.REF3", config=True)
|
||||
create_mux("CLKIN.CLK2", "CLKIN.CLK_REF_INT3", 3, 2, False, "CLKIN.REF3", config=True)
|
||||
create_mux("CLKIN.CLK3", "CLKIN.CLK_REF_INT3", 3, 3, False, "CLKIN.REF3", config=True)
|
||||
create_mux("CLKIN.SER_CLK", "CLKIN.CLK_REF_INT3", 3, 4, False, "CLKIN.REF3", config=True)
|
||||
create_mux("CLKIN.CLK_REF_INT3", "CLKIN.CLK_REF_3", 1, 0, False, "CLKIN.REF3_INV", config=True)
|
||||
create_mux("CLKIN.CLK0", "CLKIN.CLK_REF_INT3", 3, 0, False, "CLKIN.REF3", config=True, delay="clkin_CLK0_I_CLK_OUT3")
|
||||
create_mux("CLKIN.CLK1", "CLKIN.CLK_REF_INT3", 3, 1, False, "CLKIN.REF3", config=True, delay="clkin_CLK1_I_CLK_OUT3")
|
||||
create_mux("CLKIN.CLK2", "CLKIN.CLK_REF_INT3", 3, 2, False, "CLKIN.REF3", config=True, delay="clkin_CLK2_I_CLK_OUT3")
|
||||
create_mux("CLKIN.CLK3", "CLKIN.CLK_REF_INT3", 3, 3, False, "CLKIN.REF3", config=True, delay="clkin_CLK3_I_CLK_OUT3")
|
||||
create_mux("CLKIN.SER_CLK", "CLKIN.CLK_REF_INT3", 3, 4, False, "CLKIN.REF3", config=True, delay="clkin_SERDES_CLK_CLK_OUT3")
|
||||
create_mux("CLKIN.CLK_REF_INT3", "CLKIN.CLK_REF_3", 1, 0, False, "CLKIN.REF3_INV", config=True, delay="del_dummy")
|
||||
|
||||
# GLBOUT
|
||||
|
||||
create_mux("GLBOUT.CLK_REF_OUT0", "GLBOUT.CLK_INT_0", 3, 0, False, "GLBOUT.GLB0", config=True)
|
||||
create_mux("GLBOUT.CLK0_1", "GLBOUT.CLK_INT_0", 3, 1, False, "GLBOUT.GLB0", config=True)
|
||||
create_mux("GLBOUT.CLK0_2", "GLBOUT.CLK_INT_0", 3, 2, False, "GLBOUT.GLB0", config=True)
|
||||
create_mux("GLBOUT.CLK0_3", "GLBOUT.CLK_INT_0", 3, 3, False, "GLBOUT.GLB0", config=True)
|
||||
create_mux("GLBOUT.CLK0_0", "GLBOUT.CLK_INT_0", 3, 4, False, "GLBOUT.GLB0", config=True)
|
||||
create_mux("GLBOUT.CLK90_0", "GLBOUT.CLK_INT_0", 3, 5, False, "GLBOUT.GLB0", config=True)
|
||||
create_mux("GLBOUT.CLK180_0", "GLBOUT.CLK_INT_0", 3, 6, False, "GLBOUT.GLB0", config=True)
|
||||
create_mux("GLBOUT.CLK270_0", "GLBOUT.CLK_INT_0", 3, 7, False, "GLBOUT.GLB0", config=True)
|
||||
create_mux("GLBOUT.CLK_REF_OUT0", "GLBOUT.CLK_INT_0", 3, 0, False, "GLBOUT.GLB0", config=True, delay="glbout_CLKREF_0_CLOCK0")
|
||||
create_mux("GLBOUT.CLK0_1", "GLBOUT.CLK_INT_0", 3, 1, False, "GLBOUT.GLB0", config=True, delay="glbout_CLK0_1_CLOCK0")
|
||||
create_mux("GLBOUT.CLK0_2", "GLBOUT.CLK_INT_0", 3, 2, False, "GLBOUT.GLB0", config=True, delay="glbout_CLK0_2_CLOCK0")
|
||||
create_mux("GLBOUT.CLK0_3", "GLBOUT.CLK_INT_0", 3, 3, False, "GLBOUT.GLB0", config=True, delay="glbout_CLK0_3_CLOCK0")
|
||||
create_mux("GLBOUT.CLK0_0", "GLBOUT.CLK_INT_0", 3, 4, False, "GLBOUT.GLB0", config=True, delay="glbout_CLK0_0_CLOCK0")
|
||||
create_mux("GLBOUT.CLK90_0", "GLBOUT.CLK_INT_0", 3, 5, False, "GLBOUT.GLB0", config=True, delay="glbout_CLK90_0_CLOCK0")
|
||||
create_mux("GLBOUT.CLK180_0", "GLBOUT.CLK_INT_0", 3, 6, False, "GLBOUT.GLB0", config=True, delay="glbout_CLK180_0_CLOCK0")
|
||||
create_mux("GLBOUT.CLK270_0", "GLBOUT.CLK_INT_0", 3, 7, False, "GLBOUT.GLB0", config=True, delay="glbout_CLK270_0_CLOCK0")
|
||||
|
||||
create_mux("GLBOUT.CLK_INT_0", "GLBOUT.CLK_SEL_INT_0", 1, 0, False, "GLBOUT.USR_GLB0", config=True)
|
||||
create_mux("GLBOUT.USR_GLB0", "GLBOUT.CLK_SEL_INT_0", 1, 1, False, "GLBOUT.USR_GLB0", config=True)
|
||||
create_mux("GLBOUT.CLK_INT_0", "GLBOUT.CLK_SEL_INT_0", 1, 0, False, "GLBOUT.USR_GLB0", config=True, delay="del_dummy")
|
||||
create_mux("GLBOUT.USR_GLB0", "GLBOUT.CLK_SEL_INT_0", 1, 1, False, "GLBOUT.USR_GLB0", config=True, delay="glbout_U_CLK0_CLOCK0")
|
||||
|
||||
create_mux("GLBOUT.CLK_SEL_INT_0", "GLBOUT.GLB0", 1, 1, False, "GLBOUT.GLB0_EN", config=True)
|
||||
create_mux("GLBOUT.CLK_SEL_INT_0", "GLBOUT.GLB0", 1, 1, False, "GLBOUT.GLB0_EN", config=True, delay="del_dummy")
|
||||
|
||||
create_mux("GLBOUT.GLB0", "GLBOUT.FB_INT_0", 2, 0, False, "GLBOUT.FB0", config=True)
|
||||
create_mux("GLBOUT.GLB1", "GLBOUT.FB_INT_0", 2, 1, False, "GLBOUT.FB0", config=True)
|
||||
create_mux("GLBOUT.GLB2", "GLBOUT.FB_INT_0", 2, 2, False, "GLBOUT.FB0", config=True)
|
||||
create_mux("GLBOUT.GLB3", "GLBOUT.FB_INT_0", 2, 3, False, "GLBOUT.FB0", config=True)
|
||||
create_mux("GLBOUT.GLB0", "GLBOUT.FB_INT_0", 2, 0, False, "GLBOUT.FB0", config=True, delay="glbout_FEEDBACK_delay")
|
||||
create_mux("GLBOUT.GLB1", "GLBOUT.FB_INT_0", 2, 1, False, "GLBOUT.FB0", config=True, delay="glbout_FEEDBACK_delay")
|
||||
create_mux("GLBOUT.GLB2", "GLBOUT.FB_INT_0", 2, 2, False, "GLBOUT.FB0", config=True, delay="glbout_FEEDBACK_delay")
|
||||
create_mux("GLBOUT.GLB3", "GLBOUT.FB_INT_0", 2, 3, False, "GLBOUT.FB0", config=True, delay="glbout_FEEDBACK_delay")
|
||||
|
||||
create_mux("GLBOUT.FB_INT_0", "GLBOUT.CLK_FB0", 1, 0, False, "GLBOUT.USR_FB0", config=True)
|
||||
create_mux("GLBOUT.USR_FB0", "GLBOUT.CLK_FB0", 1, 1, False, "GLBOUT.USR_FB0", config=True)
|
||||
create_mux("GLBOUT.FB_INT_0", "GLBOUT.CLK_FB0", 1, 0, False, "GLBOUT.USR_FB0", config=True, delay="del_dummy")
|
||||
create_mux("GLBOUT.USR_FB0", "GLBOUT.CLK_FB0", 1, 1, False, "GLBOUT.USR_FB0", config=True, delay="glbout_U_FB0_CLK_FB0")
|
||||
|
||||
|
||||
create_mux("GLBOUT.CLK_REF_OUT1", "GLBOUT.CLK_INT_1", 3, 0, False, "GLBOUT.GLB1", config=True)
|
||||
create_mux("GLBOUT.CLK90_0", "GLBOUT.CLK_INT_1", 3, 1, False, "GLBOUT.GLB1", config=True)
|
||||
create_mux("GLBOUT.CLK90_2", "GLBOUT.CLK_INT_1", 3, 2, False, "GLBOUT.GLB1", config=True)
|
||||
create_mux("GLBOUT.CLK90_3", "GLBOUT.CLK_INT_1", 3, 3, False, "GLBOUT.GLB1", config=True)
|
||||
create_mux("GLBOUT.CLK0_1", "GLBOUT.CLK_INT_1", 3, 4, False, "GLBOUT.GLB1", config=True)
|
||||
create_mux("GLBOUT.CLK90_1", "GLBOUT.CLK_INT_1", 3, 5, False, "GLBOUT.GLB1", config=True)
|
||||
create_mux("GLBOUT.CLK180_1", "GLBOUT.CLK_INT_1", 3, 6, False, "GLBOUT.GLB1", config=True)
|
||||
create_mux("GLBOUT.CLK270_1", "GLBOUT.CLK_INT_1", 3, 7, False, "GLBOUT.GLB1", config=True)
|
||||
create_mux("GLBOUT.CLK_REF_OUT1", "GLBOUT.CLK_INT_1", 3, 0, False, "GLBOUT.GLB1", config=True, delay="glbout_CLKREF_1_CLOCK1")
|
||||
create_mux("GLBOUT.CLK90_0", "GLBOUT.CLK_INT_1", 3, 1, False, "GLBOUT.GLB1", config=True, delay="glbout_CLK90_0_CLOCK1")
|
||||
create_mux("GLBOUT.CLK90_2", "GLBOUT.CLK_INT_1", 3, 2, False, "GLBOUT.GLB1", config=True, delay="glbout_CLK90_2_CLOCK1")
|
||||
create_mux("GLBOUT.CLK90_3", "GLBOUT.CLK_INT_1", 3, 3, False, "GLBOUT.GLB1", config=True, delay="glbout_CLK90_3_CLOCK1")
|
||||
create_mux("GLBOUT.CLK0_1", "GLBOUT.CLK_INT_1", 3, 4, False, "GLBOUT.GLB1", config=True, delay="glbout_CLK0_1_CLOCK1")
|
||||
create_mux("GLBOUT.CLK90_1", "GLBOUT.CLK_INT_1", 3, 5, False, "GLBOUT.GLB1", config=True, delay="glbout_CLK90_1_CLOCK1")
|
||||
create_mux("GLBOUT.CLK180_1", "GLBOUT.CLK_INT_1", 3, 6, False, "GLBOUT.GLB1", config=True, delay="glbout_CLK180_1_CLOCK1")
|
||||
create_mux("GLBOUT.CLK270_1", "GLBOUT.CLK_INT_1", 3, 7, False, "GLBOUT.GLB1", config=True, delay="glbout_CLK270_1_CLOCK1")
|
||||
|
||||
create_mux("GLBOUT.CLK_INT_1", "GLBOUT.CLK_SEL_INT_1", 1, 0, False, "GLBOUT.USR_GLB1", config=True)
|
||||
create_mux("GLBOUT.USR_GLB1", "GLBOUT.CLK_SEL_INT_1", 1, 1, False, "GLBOUT.USR_GLB1", config=True)
|
||||
create_mux("GLBOUT.CLK_INT_1", "GLBOUT.CLK_SEL_INT_1", 1, 0, False, "GLBOUT.USR_GLB1", config=True, delay="del_dummy")
|
||||
create_mux("GLBOUT.USR_GLB1", "GLBOUT.CLK_SEL_INT_1", 1, 1, False, "GLBOUT.USR_GLB1", config=True, delay="glbout_U_CLK1_CLOCK1")
|
||||
|
||||
create_mux("GLBOUT.CLK_SEL_INT_1", "GLBOUT.GLB1", 1, 1, False, "GLBOUT.GLB1_EN", config=True)
|
||||
create_mux("GLBOUT.CLK_SEL_INT_1", "GLBOUT.GLB1", 1, 1, False, "GLBOUT.GLB1_EN", config=True, delay="del_dummy")
|
||||
|
||||
create_mux("GLBOUT.GLB0", "GLBOUT.FB_INT_1", 2, 0, False, "GLBOUT.FB1", config=True)
|
||||
create_mux("GLBOUT.GLB1", "GLBOUT.FB_INT_1", 2, 1, False, "GLBOUT.FB1", config=True)
|
||||
create_mux("GLBOUT.GLB2", "GLBOUT.FB_INT_1", 2, 2, False, "GLBOUT.FB1", config=True)
|
||||
create_mux("GLBOUT.GLB3", "GLBOUT.FB_INT_1", 2, 3, False, "GLBOUT.FB1", config=True)
|
||||
create_mux("GLBOUT.GLB0", "GLBOUT.FB_INT_1", 2, 0, False, "GLBOUT.FB1", config=True, delay="glbout_FEEDBACK_delay")
|
||||
create_mux("GLBOUT.GLB1", "GLBOUT.FB_INT_1", 2, 1, False, "GLBOUT.FB1", config=True, delay="glbout_FEEDBACK_delay")
|
||||
create_mux("GLBOUT.GLB2", "GLBOUT.FB_INT_1", 2, 2, False, "GLBOUT.FB1", config=True, delay="glbout_FEEDBACK_delay")
|
||||
create_mux("GLBOUT.GLB3", "GLBOUT.FB_INT_1", 2, 3, False, "GLBOUT.FB1", config=True, delay="glbout_FEEDBACK_delay")
|
||||
|
||||
create_mux("GLBOUT.FB_INT_1", "GLBOUT.CLK_FB1", 1, 0, False, "GLBOUT.USR_FB1", config=True)
|
||||
create_mux("GLBOUT.USR_FB1", "GLBOUT.CLK_FB1", 1, 1, False, "GLBOUT.USR_FB1", config=True)
|
||||
create_mux("GLBOUT.FB_INT_1", "GLBOUT.CLK_FB1", 1, 0, False, "GLBOUT.USR_FB1", config=True, delay="del_dummy")
|
||||
create_mux("GLBOUT.USR_FB1", "GLBOUT.CLK_FB1", 1, 1, False, "GLBOUT.USR_FB1", config=True, delay="glbout_U_FB1_CLK_FB1")
|
||||
|
||||
|
||||
create_mux("GLBOUT.CLK_REF_OUT2", "GLBOUT.CLK_INT_2", 3, 0, False, "GLBOUT.GLB2", config=True)
|
||||
create_mux("GLBOUT.CLK180_0", "GLBOUT.CLK_INT_2", 3, 1, False, "GLBOUT.GLB2", config=True)
|
||||
create_mux("GLBOUT.CLK180_1", "GLBOUT.CLK_INT_2", 3, 2, False, "GLBOUT.GLB2", config=True)
|
||||
create_mux("GLBOUT.CLK180_3", "GLBOUT.CLK_INT_2", 3, 3, False, "GLBOUT.GLB2", config=True)
|
||||
create_mux("GLBOUT.CLK0_2", "GLBOUT.CLK_INT_2", 3, 4, False, "GLBOUT.GLB2", config=True)
|
||||
create_mux("GLBOUT.CLK90_2", "GLBOUT.CLK_INT_2", 3, 5, False, "GLBOUT.GLB2", config=True)
|
||||
create_mux("GLBOUT.CLK180_2", "GLBOUT.CLK_INT_2", 3, 6, False, "GLBOUT.GLB2", config=True)
|
||||
create_mux("GLBOUT.CLK270_2", "GLBOUT.CLK_INT_2", 3, 7, False, "GLBOUT.GLB2", config=True)
|
||||
create_mux("GLBOUT.CLK_REF_OUT2", "GLBOUT.CLK_INT_2", 3, 0, False, "GLBOUT.GLB2", config=True, delay="glbout_CLKREF_2_CLOCK2")
|
||||
create_mux("GLBOUT.CLK180_0", "GLBOUT.CLK_INT_2", 3, 1, False, "GLBOUT.GLB2", config=True, delay="glbout_CLK180_0_CLOCK2")
|
||||
create_mux("GLBOUT.CLK180_1", "GLBOUT.CLK_INT_2", 3, 2, False, "GLBOUT.GLB2", config=True, delay="glbout_CLK180_1_CLOCK2")
|
||||
create_mux("GLBOUT.CLK180_3", "GLBOUT.CLK_INT_2", 3, 3, False, "GLBOUT.GLB2", config=True, delay="glbout_CLK180_3_CLOCK2")
|
||||
create_mux("GLBOUT.CLK0_2", "GLBOUT.CLK_INT_2", 3, 4, False, "GLBOUT.GLB2", config=True, delay="glbout_CLK0_2_CLOCK2")
|
||||
create_mux("GLBOUT.CLK90_2", "GLBOUT.CLK_INT_2", 3, 5, False, "GLBOUT.GLB2", config=True, delay="glbout_CLK90_2_CLOCK2")
|
||||
create_mux("GLBOUT.CLK180_2", "GLBOUT.CLK_INT_2", 3, 6, False, "GLBOUT.GLB2", config=True, delay="glbout_CLK180_2_CLOCK2")
|
||||
create_mux("GLBOUT.CLK270_2", "GLBOUT.CLK_INT_2", 3, 7, False, "GLBOUT.GLB2", config=True, delay="glbout_CLK270_2_CLOCK2")
|
||||
|
||||
create_mux("GLBOUT.CLK_INT_2", "GLBOUT.CLK_SEL_INT_2", 1, 0, False, "GLBOUT.USR_GLB2", config=True)
|
||||
create_mux("GLBOUT.CLK_INT_2", "GLBOUT.CLK_SEL_INT_2", 1, 0, False, "GLBOUT.USR_GLB2", config=True, delay="del_dummy")
|
||||
create_mux("GLBOUT.USR_GLB2", "GLBOUT.CLK_SEL_INT_2", 1, 1, False, "GLBOUT.USR_GLB2", config=True)
|
||||
|
||||
create_mux("GLBOUT.CLK_SEL_INT_2", "GLBOUT.GLB2", 1, 1, False, "GLBOUT.GLB2_EN", config=True)
|
||||
create_mux("GLBOUT.CLK_SEL_INT_2", "GLBOUT.GLB2", 1, 1, False, "GLBOUT.GLB2_EN", config=True, delay="del_dummy")
|
||||
|
||||
create_mux("GLBOUT.GLB0", "GLBOUT.FB_INT_2", 2, 0, False, "GLBOUT.FB2", config=True)
|
||||
create_mux("GLBOUT.GLB1", "GLBOUT.FB_INT_2", 2, 1, False, "GLBOUT.FB2", config=True)
|
||||
create_mux("GLBOUT.GLB2", "GLBOUT.FB_INT_2", 2, 2, False, "GLBOUT.FB2", config=True)
|
||||
create_mux("GLBOUT.GLB3", "GLBOUT.FB_INT_2", 2, 3, False, "GLBOUT.FB2", config=True)
|
||||
create_mux("GLBOUT.GLB0", "GLBOUT.FB_INT_2", 2, 0, False, "GLBOUT.FB2", config=True, delay="glbout_FEEDBACK_delay")
|
||||
create_mux("GLBOUT.GLB1", "GLBOUT.FB_INT_2", 2, 1, False, "GLBOUT.FB2", config=True, delay="glbout_FEEDBACK_delay")
|
||||
create_mux("GLBOUT.GLB2", "GLBOUT.FB_INT_2", 2, 2, False, "GLBOUT.FB2", config=True, delay="glbout_FEEDBACK_delay")
|
||||
create_mux("GLBOUT.GLB3", "GLBOUT.FB_INT_2", 2, 3, False, "GLBOUT.FB2", config=True, delay="glbout_FEEDBACK_delay")
|
||||
|
||||
create_mux("GLBOUT.FB_INT_2", "GLBOUT.CLK_FB2", 1, 0, False, "GLBOUT.USR_FB2", config=True)
|
||||
create_mux("GLBOUT.USR_FB2", "GLBOUT.CLK_FB2", 1, 1, False, "GLBOUT.USR_FB2", config=True)
|
||||
create_mux("GLBOUT.FB_INT_2", "GLBOUT.CLK_FB2", 1, 0, False, "GLBOUT.USR_FB2", config=True, delay="del_dummy")
|
||||
create_mux("GLBOUT.USR_FB2", "GLBOUT.CLK_FB2", 1, 1, False, "GLBOUT.USR_FB2", config=True, delay="glbout_U_FB2_CLK_FB2")
|
||||
|
||||
create_mux("GLBOUT.CLK_REF_OUT3", "GLBOUT.CLK_INT_3", 3, 0, False, "GLBOUT.GLB3", config=True)
|
||||
create_mux("GLBOUT.CLK270_0", "GLBOUT.CLK_INT_3", 3, 1, False, "GLBOUT.GLB3", config=True)
|
||||
create_mux("GLBOUT.CLK270_1", "GLBOUT.CLK_INT_3", 3, 2, False, "GLBOUT.GLB3", config=True)
|
||||
create_mux("GLBOUT.CLK270_2", "GLBOUT.CLK_INT_3", 3, 3, False, "GLBOUT.GLB3", config=True)
|
||||
create_mux("GLBOUT.CLK0_3", "GLBOUT.CLK_INT_3", 3, 4, False, "GLBOUT.GLB3", config=True)
|
||||
create_mux("GLBOUT.CLK90_3", "GLBOUT.CLK_INT_3", 3, 5, False, "GLBOUT.GLB3", config=True)
|
||||
create_mux("GLBOUT.CLK180_3", "GLBOUT.CLK_INT_3", 3, 6, False, "GLBOUT.GLB3", config=True)
|
||||
create_mux("GLBOUT.CLK270_3", "GLBOUT.CLK_INT_3", 3, 7, False, "GLBOUT.GLB3", config=True)
|
||||
create_mux("GLBOUT.CLK_REF_OUT3", "GLBOUT.CLK_INT_3", 3, 0, False, "GLBOUT.GLB3", config=True, delay="glbout_CLKREF_3_CLOCK3")
|
||||
create_mux("GLBOUT.CLK270_0", "GLBOUT.CLK_INT_3", 3, 1, False, "GLBOUT.GLB3", config=True, delay="glbout_CLK270_0_CLOCK3")
|
||||
create_mux("GLBOUT.CLK270_1", "GLBOUT.CLK_INT_3", 3, 2, False, "GLBOUT.GLB3", config=True, delay="glbout_CLK270_1_CLOCK3")
|
||||
create_mux("GLBOUT.CLK270_2", "GLBOUT.CLK_INT_3", 3, 3, False, "GLBOUT.GLB3", config=True, delay="glbout_CLK270_2_CLOCK3")
|
||||
create_mux("GLBOUT.CLK0_3", "GLBOUT.CLK_INT_3", 3, 4, False, "GLBOUT.GLB3", config=True, delay="glbout_CLK0_3_CLOCK3")
|
||||
create_mux("GLBOUT.CLK90_3", "GLBOUT.CLK_INT_3", 3, 5, False, "GLBOUT.GLB3", config=True, delay="glbout_CLK90_3_CLOCK3")
|
||||
create_mux("GLBOUT.CLK180_3", "GLBOUT.CLK_INT_3", 3, 6, False, "GLBOUT.GLB3", config=True, delay="glbout_CLK180_3_CLOCK3")
|
||||
create_mux("GLBOUT.CLK270_3", "GLBOUT.CLK_INT_3", 3, 7, False, "GLBOUT.GLB3", config=True, delay="glbout_CLK270_3_CLOCK3")
|
||||
|
||||
create_mux("GLBOUT.CLK_INT_3", "GLBOUT.CLK_SEL_INT_3", 1, 0, False, "GLBOUT.USR_GLB3", config=True)
|
||||
create_mux("GLBOUT.USR_GLB3", "GLBOUT.CLK_SEL_INT_3", 1, 1, False, "GLBOUT.USR_GLB3", config=True)
|
||||
create_mux("GLBOUT.CLK_INT_3", "GLBOUT.CLK_SEL_INT_3", 1, 0, False, "GLBOUT.USR_GLB3", config=True, delay="del_dummy")
|
||||
create_mux("GLBOUT.USR_GLB3", "GLBOUT.CLK_SEL_INT_3", 1, 1, False, "GLBOUT.USR_GLB3", config=True, delay="glbout_U_CLK3_CLOCK3")
|
||||
|
||||
create_mux("GLBOUT.CLK_SEL_INT_3", "GLBOUT.GLB3", 1, 1, False, "GLBOUT.GLB3_EN", config=True)
|
||||
create_mux("GLBOUT.CLK_SEL_INT_3", "GLBOUT.GLB3", 1, 1, False, "GLBOUT.GLB3_EN", config=True, delay="del_dummy")
|
||||
|
||||
create_mux("GLBOUT.GLB0", "GLBOUT.FB_INT_3", 2, 0, False, "GLBOUT.FB3", config=True)
|
||||
create_mux("GLBOUT.GLB1", "GLBOUT.FB_INT_3", 2, 1, False, "GLBOUT.FB3", config=True)
|
||||
create_mux("GLBOUT.GLB2", "GLBOUT.FB_INT_3", 2, 2, False, "GLBOUT.FB3", config=True)
|
||||
create_mux("GLBOUT.GLB3", "GLBOUT.FB_INT_3", 2, 3, False, "GLBOUT.FB3", config=True)
|
||||
create_mux("GLBOUT.GLB0", "GLBOUT.FB_INT_3", 2, 0, False, "GLBOUT.FB3", config=True, delay="glbout_FEEDBACK_delay")
|
||||
create_mux("GLBOUT.GLB1", "GLBOUT.FB_INT_3", 2, 1, False, "GLBOUT.FB3", config=True, delay="glbout_FEEDBACK_delay")
|
||||
create_mux("GLBOUT.GLB2", "GLBOUT.FB_INT_3", 2, 2, False, "GLBOUT.FB3", config=True, delay="glbout_FEEDBACK_delay")
|
||||
create_mux("GLBOUT.GLB3", "GLBOUT.FB_INT_3", 2, 3, False, "GLBOUT.FB3", config=True, delay="glbout_FEEDBACK_delay")
|
||||
|
||||
create_mux("GLBOUT.FB_INT_3", "GLBOUT.CLK_FB3", 1, 0, False, "GLBOUT.USR_FB3", config=True)
|
||||
create_mux("GLBOUT.USR_FB3", "GLBOUT.CLK_FB3", 1, 1, False, "GLBOUT.USR_FB3", config=True)
|
||||
create_mux("GLBOUT.FB_INT_3", "GLBOUT.CLK_FB3", 1, 0, False, "GLBOUT.USR_FB3", config=True, delay="del_dummy")
|
||||
create_mux("GLBOUT.USR_FB3", "GLBOUT.CLK_FB3", 1, 1, False, "GLBOUT.USR_FB3", config=True, delay="glbout_U_FB3_CLK_FB3")
|
||||
|
||||
# PLL
|
||||
|
||||
create_mux("CLKIN.CLK_REF_0", "GLBOUT.CLK_REF_OUT0", 1, 0, False, "PLL0.USR_CLK_OUT", config=True)
|
||||
create_mux("CLKIN.CLK_REF_1", "GLBOUT.CLK_REF_OUT1", 1, 0, False, "PLL1.USR_CLK_OUT", config=True)
|
||||
create_mux("CLKIN.CLK_REF_2", "GLBOUT.CLK_REF_OUT2", 1, 0, False, "PLL2.USR_CLK_OUT", config=True)
|
||||
create_mux("CLKIN.CLK_REF_3", "GLBOUT.CLK_REF_OUT3", 1, 0, False, "PLL3.USR_CLK_OUT", config=True)
|
||||
create_mux("CLKIN.CLK_REF_0", "GLBOUT.CLK_REF_OUT0", 1, 0, False, "PLL0.USR_CLK_OUT", config=True, delay="del_dummy")
|
||||
create_mux("CLKIN.CLK_REF_1", "GLBOUT.CLK_REF_OUT1", 1, 0, False, "PLL1.USR_CLK_OUT", config=True, delay="del_dummy")
|
||||
create_mux("CLKIN.CLK_REF_2", "GLBOUT.CLK_REF_OUT2", 1, 0, False, "PLL2.USR_CLK_OUT", config=True, delay="del_dummy")
|
||||
create_mux("CLKIN.CLK_REF_3", "GLBOUT.CLK_REF_OUT3", 1, 0, False, "PLL3.USR_CLK_OUT", config=True, delay="del_dummy")
|
||||
|
||||
create_mux("PLL0.USR_CLK_REF", "GLBOUT.CLK_REF_OUT0", 1, 1, False, "PLL0.USR_CLK_OUT", config=True)
|
||||
create_mux("PLL1.USR_CLK_REF", "GLBOUT.CLK_REF_OUT1", 1, 1, False, "PLL1.USR_CLK_OUT", config=True)
|
||||
create_mux("PLL2.USR_CLK_REF", "GLBOUT.CLK_REF_OUT2", 1, 1, False, "PLL2.USR_CLK_OUT", config=True)
|
||||
create_mux("PLL3.USR_CLK_REF", "GLBOUT.CLK_REF_OUT3", 1, 1, False, "PLL3.USR_CLK_OUT", config=True)
|
||||
create_mux("PLL0.USR_CLK_REF", "GLBOUT.CLK_REF_OUT0", 1, 1, False, "PLL0.USR_CLK_OUT", config=True, delay="del_dummy")
|
||||
create_mux("PLL1.USR_CLK_REF", "GLBOUT.CLK_REF_OUT1", 1, 1, False, "PLL1.USR_CLK_OUT", config=True, delay="del_dummy")
|
||||
create_mux("PLL2.USR_CLK_REF", "GLBOUT.CLK_REF_OUT2", 1, 1, False, "PLL2.USR_CLK_OUT", config=True, delay="del_dummy")
|
||||
create_mux("PLL3.USR_CLK_REF", "GLBOUT.CLK_REF_OUT3", 1, 1, False, "PLL3.USR_CLK_OUT", config=True, delay="del_dummy")
|
||||
|
||||
return muxes
|
||||
|
||||
|
|
@ -2986,10 +3007,10 @@ class Die:
|
|||
self.gpio_to_loc[f"GPIO_{io.bank}_{io.port}[{io.num}]"] = Location(x, y)
|
||||
self.io_pad_names[io.bank][io.port][io.num] = Location(x, y)
|
||||
|
||||
def create_conn(self, src_x,src_y, src, dst_x, dst_y, dst):
|
||||
def create_conn(self, src_x,src_y, src, dst_x, dst_y, dst, delay=""):
|
||||
key_val = f"{src_x + self.offset_x}/{src_y + self.offset_y}/{src}"
|
||||
key = Connection(src_x + self.offset_x, src_y + self.offset_y, src)
|
||||
item = Connection(dst_x + self.offset_x, dst_y + self.offset_y, dst)
|
||||
key = Connection(src_x + self.offset_x, src_y + self.offset_y, src, "")
|
||||
item = Connection(dst_x + self.offset_x, dst_y + self.offset_y, dst, delay)
|
||||
if key_val not in self.conn:
|
||||
self.conn[key_val] = list()
|
||||
self.conn[key_val].append(key)
|
||||
|
|
@ -3016,17 +3037,18 @@ class Die:
|
|||
return list()
|
||||
|
||||
def create_cpe(self, x,y):
|
||||
self.create_conn(x,y,"IM.P01.Y", x,y,"CPE.IN1")
|
||||
self.create_conn(x,y,"IM.P02.Y", x,y,"CPE.IN2")
|
||||
self.create_conn(x,y,"IM.P03.Y", x,y,"CPE.IN3")
|
||||
self.create_conn(x,y,"IM.P04.Y", x,y,"CPE.IN4")
|
||||
self.create_conn(x,y,"IM.P05.Y", x,y,"CPE.IN5")
|
||||
self.create_conn(x,y,"IM.P06.Y", x,y,"CPE.IN6")
|
||||
self.create_conn(x,y,"IM.P07.Y", x,y,"CPE.IN7")
|
||||
self.create_conn(x,y,"IM.P08.Y", x,y,"CPE.IN8")
|
||||
self.create_conn(x,y,"IM.P09.Y", x,y,"CPE.CLK")
|
||||
self.create_conn(x,y,"IM.P10.Y", x,y,"CPE.EN")
|
||||
self.create_conn(x,y,"IM.P11.Y", x,y,"CPE.SR")
|
||||
delay = f"im_{get_tile_loc_str(x,y)}"
|
||||
self.create_conn(x,y,"IM.P01.Y", x,y,"CPE.IN1", f"{delay}_p1_d0_path2") # TODO: fix, d0 used only
|
||||
self.create_conn(x,y,"IM.P02.Y", x,y,"CPE.IN2", f"{delay}_p2_d0_path2")
|
||||
self.create_conn(x,y,"IM.P03.Y", x,y,"CPE.IN3", f"{delay}_p3_d0_path2")
|
||||
self.create_conn(x,y,"IM.P04.Y", x,y,"CPE.IN4", f"{delay}_p4_d0_path2")
|
||||
self.create_conn(x,y,"IM.P05.Y", x,y,"CPE.IN5", f"{delay}_p5_d0_path2")
|
||||
self.create_conn(x,y,"IM.P06.Y", x,y,"CPE.IN6", f"{delay}_p6_d0_path2")
|
||||
self.create_conn(x,y,"IM.P07.Y", x,y,"CPE.IN7", f"{delay}_p7_d0_path2")
|
||||
self.create_conn(x,y,"IM.P08.Y", x,y,"CPE.IN8", f"{delay}_p8_d0_path2")
|
||||
self.create_conn(x,y,"IM.P09.Y", x,y,"CPE.CLK", f"{delay}_p9_d0_path2")
|
||||
self.create_conn(x,y,"IM.P10.Y", x,y,"CPE.EN", f"{delay}_p10_d0_path2")
|
||||
self.create_conn(x,y,"IM.P11.Y", x,y,"CPE.SR", f"{delay}_p11_d0_path2")
|
||||
if is_cpe(x,y-1):
|
||||
self.create_conn(x,y-1,"CPE.COUTY1", x,y,"CPE.CINY1")
|
||||
self.create_conn(x,y-1,"CPE.COUTY2", x,y,"CPE.CINY2")
|
||||
|
|
@ -3042,22 +3064,23 @@ class Die:
|
|||
|
||||
# D0 - D3 are from nearby SBs
|
||||
offset = 2 if is_sb(x,y) else 1
|
||||
self.create_conn(x-offset,y,f"{get_sb_type(x-offset,y)}.P{plane}.Y1", x,y,f"IM.P{plane}.D0")
|
||||
self.create_conn(x,y-offset,f"{get_sb_type(x,y-offset)}.P{plane}.Y2", x,y,f"IM.P{plane}.D1")
|
||||
self.create_conn(x+offset,y,f"{get_sb_type(x+offset,y)}.P{plane}.Y3", x,y,f"IM.P{plane}.D2")
|
||||
self.create_conn(x,y+offset,f"{get_sb_type(x,y+offset)}.P{plane}.Y4", x,y,f"IM.P{plane}.D3")
|
||||
delay = f"im_{get_tile_loc_str(x,y)}_p{p}"
|
||||
self.create_conn(x-offset,y,f"{get_sb_type(x-offset,y)}.P{plane}.Y1", x,y,f"IM.P{plane}.D0", f"{delay}_d0_path1")
|
||||
self.create_conn(x,y-offset,f"{get_sb_type(x,y-offset)}.P{plane}.Y2", x,y,f"IM.P{plane}.D1", f"{delay}_d1_path1")
|
||||
self.create_conn(x+offset,y,f"{get_sb_type(x+offset,y)}.P{plane}.Y3", x,y,f"IM.P{plane}.D2", f"{delay}_d2_path1")
|
||||
self.create_conn(x,y+offset,f"{get_sb_type(x,y+offset)}.P{plane}.Y4", x,y,f"IM.P{plane}.D3", f"{delay}_d3_path1")
|
||||
|
||||
# D4 and D5 are from diagonal INMUX
|
||||
if is_cpe(x-1,y-1):
|
||||
self.create_conn(x-1,y-1,f"IM.P{plane}.Y", x,y,f"IM.P{plane}.D4")
|
||||
self.create_conn(x-1,y-1,f"IM.P{plane}.Y", x,y,f"IM.P{plane}.D4", f"{delay}_d4_path1")
|
||||
if is_cpe(x+1,y+1):
|
||||
self.create_conn(x+1,y+1,f"IM.P{plane}.Y", x,y,f"IM.P{plane}.D5")
|
||||
self.create_conn(x+1,y+1,f"IM.P{plane}.Y", x,y,f"IM.P{plane}.D5", f"{delay}_d5_path1")
|
||||
|
||||
# D6 and D7 are from alternate planes
|
||||
alt = f"{alt_plane(0,p):02d}"
|
||||
self.create_conn(x,y,f"IM.P{alt}.Y", x,y,f"IM.P{plane}.D6")
|
||||
self.create_conn(x,y,f"IM.P{alt}.Y", x,y,f"IM.P{plane}.D6", f"{delay}_d6_path1")
|
||||
alt = f"{alt_plane(1,p):02d}"
|
||||
self.create_conn(x,y,f"IM.P{alt}.Y", x,y,f"IM.P{plane}.D7")
|
||||
self.create_conn(x,y,f"IM.P{alt}.Y", x,y,f"IM.P{plane}.D7", f"{delay}_d7_path1")
|
||||
|
||||
def create_sb(self, x,y):
|
||||
x_0,y_0 = base_loc(x,y)
|
||||
|
|
@ -3065,6 +3088,7 @@ class Die:
|
|||
|
||||
for p in range(1,13):
|
||||
plane = f"{p:02d}"
|
||||
delay = f"sb_del_{get_full_tile_loc_str(x,y)}"
|
||||
# Handling input D0
|
||||
if is_cpe(x,y):
|
||||
# Core section SBs are connected to CPE
|
||||
|
|
@ -3074,10 +3098,10 @@ class Die:
|
|||
y_cpe = y_0 + (1 if (p-1) & 1 else 0)
|
||||
# alternate patterns for lower-left SB(1,1) and upper-right SB(2,2)
|
||||
out = [ 2, 1, 2, 1, 1, 2, 1, 2] if x & 1 else [ 1, 2, 1, 2, 2, 1, 2, 1]
|
||||
self.create_conn(x_cpe,y_cpe,f"CPE.OUT{out[p-1]}", x,y,f"{sb_type}.P{plane}.D0")
|
||||
self.create_conn(x_cpe,y_cpe,f"CPE.OUT{out[p-1]}", x,y,f"{sb_type}.P{plane}.D0", f"{delay}_p{p}_d0_s0")
|
||||
else:
|
||||
# planes 9..12
|
||||
self.create_conn(x,y,f"OM.P{plane}.Y", x,y,f"{sb_type}.P{plane}.D0")
|
||||
self.create_conn(x,y,f"OM.P{plane}.Y", x,y,f"{sb_type}.P{plane}.D0", f"{delay}_p{p}_d0_s0")
|
||||
# Handling GPIO connections is done in create_io
|
||||
# Handling inputs D2_* till D7_*
|
||||
distances = [2, 4, 8, 12, 16, 20] if is_sb_big(x,y) else [2, 4]
|
||||
|
|
@ -3106,20 +3130,20 @@ class Die:
|
|||
src = f"SB_DRIVE.P{plane}.D{direction+1}.OUT"
|
||||
else:
|
||||
src = f"SB_DRIVE.P{plane}.D{direction+1}.OUT_NOINV"
|
||||
self.create_conn(sb_x,sb_y, src, x,y,f"{get_sb_type(x,y)}.P{plane}.D{i+2}_{direction+1}")
|
||||
self.create_conn(sb_x,sb_y, src, x,y,f"{get_sb_type(x,y)}.P{plane}.D{i+2}_{direction+1}", f"{delay}_p{p}_d{direction+1}_s{i+2}")
|
||||
|
||||
if is_sb_big(x,y):
|
||||
for direction in range(4):
|
||||
self.create_conn(x,y, f"{get_sb_type(x,y)}.P{plane}.Y{direction+1}", x,y,f"SB_DRIVE.P{plane}.D{direction+1}.IN")
|
||||
self.create_conn(x,y, f"{get_sb_type(x,y)}.P{plane}.Y{direction+1}", x,y,f"SB_DRIVE.P{plane}.D{direction+1}.IN", delay="del_dummy")
|
||||
|
||||
# Diagonal inputs
|
||||
# X12 and X34 on edges are unconnected
|
||||
if is_sb(x-1,y-1):
|
||||
self.create_conn(x-1,y-1,f"{get_sb_type(x-1,y-1)}.P{plane}.YDIAG", x,y,f"{get_sb_type(x,y)}.P{plane}.X12")
|
||||
self.create_conn(x-1,y-1,f"{get_sb_type(x-1,y-1)}.P{plane}.YDIAG", x,y,f"{get_sb_type(x,y)}.P{plane}.X12", f"{delay}_p{p}_d0_s6")
|
||||
if is_sb(x+1,y+1):
|
||||
self.create_conn(x+1,y+1,f"{get_sb_type(x+1,y+1)}.P{plane}.YDIAG", x,y,f"{get_sb_type(x,y)}.P{plane}.X34")
|
||||
self.create_conn(x,y,f"{get_sb_type(x,y)}.P{prev_plane(p):02d}.YDIAG", x,y,f"{get_sb_type(x,y)}.P{plane}.X14")
|
||||
self.create_conn(x,y,f"{get_sb_type(x,y)}.P{next_plane(p):02d}.YDIAG", x,y,f"{get_sb_type(x,y)}.P{plane}.X23")
|
||||
self.create_conn(x+1,y+1,f"{get_sb_type(x+1,y+1)}.P{plane}.YDIAG", x,y,f"{get_sb_type(x,y)}.P{plane}.X34", f"{delay}_p{p}_d0_s4")
|
||||
self.create_conn(x,y,f"{get_sb_type(x,y)}.P{prev_plane(p):02d}.YDIAG", x,y,f"{get_sb_type(x,y)}.P{plane}.X14", f"{delay}_p{p}_d0_s5")
|
||||
self.create_conn(x,y,f"{get_sb_type(x,y)}.P{next_plane(p):02d}.YDIAG", x,y,f"{get_sb_type(x,y)}.P{plane}.X23", f"{delay}_p{p}_d0_s7")
|
||||
|
||||
def create_outmux(self, x,y):
|
||||
x_0,y_0 = base_loc(x,y)
|
||||
|
|
@ -3127,10 +3151,11 @@ class Die:
|
|||
plane = f"{p:02d}"
|
||||
# alternating patters depending of plane and outmux position
|
||||
outputs = [2, 2, 1, 1] if p % 2 == x & 1 else [1, 1, 2, 2]
|
||||
self.create_conn(x_0, y_0, f"CPE.OUT{outputs[0]}", x,y, f"OM.P{plane}.D0")
|
||||
self.create_conn(x_0, y_0+1, f"CPE.OUT{outputs[1]}", x,y, f"OM.P{plane}.D1")
|
||||
self.create_conn(x_0+1, y_0, f"CPE.OUT{outputs[2]}", x,y, f"OM.P{plane}.D2")
|
||||
self.create_conn(x_0+1, y_0+1, f"CPE.OUT{outputs[3]}", x,y, f"OM.P{plane}.D3")
|
||||
delay = f"om_{get_tile_loc_str(x,y)}"
|
||||
self.create_conn(x_0, y_0, f"CPE.OUT{outputs[0]}", x,y, f"OM.P{plane}.D0", f"{delay}_p{p}_d0")
|
||||
self.create_conn(x_0, y_0+1, f"CPE.OUT{outputs[1]}", x,y, f"OM.P{plane}.D1", f"{delay}_p{p}_d1")
|
||||
self.create_conn(x_0+1, y_0, f"CPE.OUT{outputs[2]}", x,y, f"OM.P{plane}.D2", f"{delay}_p{p}_d2")
|
||||
self.create_conn(x_0+1, y_0+1, f"CPE.OUT{outputs[3]}", x,y, f"OM.P{plane}.D3", f"{delay}_p{p}_d3")
|
||||
|
||||
def get_pin_real_name(self, prim_name, pin):
|
||||
prim_type = prim_name
|
||||
|
|
@ -3149,7 +3174,7 @@ class Die:
|
|||
if c.output == RAM_OUTPUT:
|
||||
self.create_conn(loc_x + c.rel_x, loc_y + c.rel_y, f"CPE.RAM_O{c.pin_num}", loc_x, loc_y, f"{name}")
|
||||
else:
|
||||
self.create_conn(loc_x, loc_y, f"{name}", loc_x + c.rel_x, loc_y + c.rel_y, f"CPE.RAM_I{c.pin_num}")
|
||||
self.create_conn(loc_x, loc_y, f"{name}", loc_x + c.rel_x, loc_y + c.rel_y, f"CPE.RAM_I{c.pin_num}", delay="del_special_RAM_I")
|
||||
|
||||
def create_io(self, x,y):
|
||||
cpe_x, cpe_y = gpio_x, gpio_y = sb_x, sb_y = x, y
|
||||
|
|
@ -3200,10 +3225,10 @@ class Die:
|
|||
|
||||
if not alt:
|
||||
self.create_ram_io_conn("GPIO", "GPIO", x, y)
|
||||
self.create_conn(PLL_X_POS, PLL_Y_POS, "GLBOUT.GLB0", gpio_x, gpio_y, "GPIO.CLOCK1")
|
||||
self.create_conn(PLL_X_POS, PLL_Y_POS, "GLBOUT.GLB1", gpio_x, gpio_y, "GPIO.CLOCK2")
|
||||
self.create_conn(PLL_X_POS, PLL_Y_POS, "GLBOUT.GLB2", gpio_x, gpio_y, "GPIO.CLOCK3")
|
||||
self.create_conn(PLL_X_POS, PLL_Y_POS, "GLBOUT.GLB3", gpio_x, gpio_y, "GPIO.CLOCK4")
|
||||
self.create_conn(PLL_X_POS, PLL_Y_POS, "GLBOUT.GLB0", gpio_x, gpio_y, "GPIO.CLOCK1", "del_GLBOUT_IO_SEL")
|
||||
self.create_conn(PLL_X_POS, PLL_Y_POS, "GLBOUT.GLB1", gpio_x, gpio_y, "GPIO.CLOCK2", "del_GLBOUT_IO_SEL")
|
||||
self.create_conn(PLL_X_POS, PLL_Y_POS, "GLBOUT.GLB2", gpio_x, gpio_y, "GPIO.CLOCK3", "del_GLBOUT_IO_SEL")
|
||||
self.create_conn(PLL_X_POS, PLL_Y_POS, "GLBOUT.GLB3", gpio_x, gpio_y, "GPIO.CLOCK4", "del_GLBOUT_IO_SEL")
|
||||
|
||||
def create_pll(self):
|
||||
# GPIO_W2_A[8] CLK0
|
||||
|
|
@ -3248,7 +3273,7 @@ class Die:
|
|||
# Clock#2: p2, p6,p10
|
||||
# Clock#3: p3, p7,p11
|
||||
# Clock#4: p4, p8,p12
|
||||
self.create_conn(PLL_X_POS, PLL_Y_POS, f"GLBOUT.GLB{(p-1) & 3}", x,y,f"SB_BIG.P{plane}.{inp}")
|
||||
self.create_conn(PLL_X_POS, PLL_Y_POS, f"GLBOUT.GLB{(p-1) & 3}", x,y,f"SB_BIG.P{plane}.{inp}", "del_GLBOUT_sb_big")
|
||||
|
||||
# Connecting Global Mesh signals to Switch Boxes
|
||||
# Left edge
|
||||
|
|
@ -3389,6 +3414,10 @@ class Die:
|
|||
|
||||
def create_ram(self, x, y):
|
||||
self.create_ram_io_conn("RAM", "RAM", x, y)
|
||||
self.create_conn(PLL_X_POS, PLL_Y_POS, "GLBOUT.GLB0", x, y, "RAM.CLOCK1")
|
||||
self.create_conn(PLL_X_POS, PLL_Y_POS, "GLBOUT.GLB1", x, y, "RAM.CLOCK2")
|
||||
self.create_conn(PLL_X_POS, PLL_Y_POS, "GLBOUT.GLB2", x, y, "RAM.CLOCK3")
|
||||
self.create_conn(PLL_X_POS, PLL_Y_POS, "GLBOUT.GLB3", x, y, "RAM.CLOCK4")
|
||||
|
||||
def create_in_die_connections(self, conn):
|
||||
self.conn = conn
|
||||
|
|
|
|||
|
|
@ -0,0 +1,564 @@
|
|||
#
|
||||
# prjpeppercorn -- GateMate FPGAs Bitstream Documentation and Tools
|
||||
#
|
||||
# Copyright (C) 2024 The Project Peppercorn Authors.
|
||||
#
|
||||
# Permission to use, copy, modify, and/or distribute this software for any
|
||||
# purpose with or without fee is hereby granted, provided that the above
|
||||
# copyright notice and this permission notice appear in all copies.
|
||||
#
|
||||
# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||
# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||
# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
#
|
||||
|
||||
import zlib
|
||||
import struct
|
||||
from dataclasses import dataclass
|
||||
from typing import List
|
||||
|
||||
@dataclass
|
||||
class T_delay_tri:
|
||||
min: int
|
||||
typ: int
|
||||
max: int
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(data: bytes) -> 'T_delay_tri':
|
||||
min_val, typ_val, max_val = struct.unpack('<3i', data)
|
||||
return T_delay_tri(min_val, typ_val, max_val)
|
||||
|
||||
@dataclass
|
||||
class T_delay:
|
||||
rise: T_delay_tri
|
||||
fall: T_delay_tri
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(data: bytes) -> 'T_delay':
|
||||
rise = T_delay_tri.from_bytes(data[:12])
|
||||
fall = T_delay_tri.from_bytes(data[12:24])
|
||||
return T_delay(rise, fall)
|
||||
|
||||
@dataclass
|
||||
class Tpin_pair:
|
||||
i: int
|
||||
o_or_clk: int # Represents either 'o' or 'clk' depending on the boolean case
|
||||
|
||||
@dataclass
|
||||
class Tentry_rec:
|
||||
pins: Tpin_pair
|
||||
entry_no: int
|
||||
|
||||
|
||||
@dataclass
|
||||
class Tdel_entry:
|
||||
key: int
|
||||
edge1: int
|
||||
edge2: int
|
||||
time1: T_delay_tri
|
||||
time2: T_delay_tri
|
||||
|
||||
|
||||
@dataclass
|
||||
class TRAM_del_rec:
|
||||
iopath: List[Tentry_rec]
|
||||
setuphold: List[Tentry_rec]
|
||||
width: List[Tentry_rec]
|
||||
del_entry: List[Tdel_entry]
|
||||
|
||||
|
||||
@dataclass
|
||||
class Tdel_rec:
|
||||
val: T_delay
|
||||
conf_mux: int
|
||||
name: str
|
||||
x: int
|
||||
y: int
|
||||
plane: int
|
||||
dir: int
|
||||
inv: int
|
||||
cnt: int
|
||||
con_type: int
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(data: memoryview, offset: int) -> ('Tdel_rec', int):
|
||||
val = T_delay.from_bytes(data[offset:offset + 24])
|
||||
offset += 24
|
||||
|
||||
conf_mux = struct.unpack_from('<i', data, offset)[0]
|
||||
offset += 4
|
||||
strlen = data[offset]
|
||||
offset += 1
|
||||
name = data[offset:offset + strlen].decode('ascii')
|
||||
offset += 23 # alignment added as well
|
||||
|
||||
x, y, plane, dir, inv, cnt = struct.unpack_from('<6i', data, offset)
|
||||
offset += 24
|
||||
|
||||
con_type_val = data[offset]
|
||||
offset += 4
|
||||
|
||||
return Tdel_rec(val, conf_mux, name, x, y, plane, dir, inv, cnt, con_type_val), offset
|
||||
|
||||
@dataclass
|
||||
class Tdel_rec_tri:
|
||||
val: T_delay_tri
|
||||
conf_mux: int
|
||||
name: str
|
||||
x: int
|
||||
y: int
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(mv: memoryview, offset: int) -> ('Tdel_rec_tri', int):
|
||||
val = T_delay_tri.from_bytes(mv[offset:offset+12])
|
||||
offset += 12
|
||||
|
||||
conf_mux = struct.unpack_from('<i', mv, offset)[0]
|
||||
offset += 4
|
||||
|
||||
strlen = mv[offset]
|
||||
offset += 1
|
||||
name = mv[offset:offset + strlen].decode('ascii')
|
||||
offset += 23
|
||||
|
||||
x, y = struct.unpack_from('<2i', mv, offset)
|
||||
offset += 8
|
||||
|
||||
return Tdel_rec_tri(val, conf_mux, name, x, y), offset
|
||||
|
||||
|
||||
def read_SB_del_tile_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
SB_del_tile_arr = []
|
||||
|
||||
for i1 in range(4): # [1..4]
|
||||
level1 = []
|
||||
for i2 in range(8): # [1..8]
|
||||
level2 = []
|
||||
for i3 in range(4): # [1..4]
|
||||
level3 = []
|
||||
for i4 in range(12): # [1..12]
|
||||
level4 = []
|
||||
for i5 in range(5): # [0..4]
|
||||
level5 = []
|
||||
for i6 in range(8): # [0..7]
|
||||
chunk = mv[offset:offset + 24]
|
||||
if len(chunk) < 24:
|
||||
raise EOFError("Unexpected end of data")
|
||||
delay = T_delay.from_bytes(chunk)
|
||||
offset += 24
|
||||
level5.append(delay)
|
||||
level4.append(level5)
|
||||
level3.append(level4)
|
||||
level2.append(level3)
|
||||
level1.append(level2)
|
||||
SB_del_tile_arr.append(level1)
|
||||
|
||||
return SB_del_tile_arr, offset
|
||||
|
||||
@dataclass
|
||||
class ExtraTimingDelays:
|
||||
skew_report_del: int
|
||||
fix_skew_del: int
|
||||
del_rec_0: Tdel_rec
|
||||
del_min_route_SB: Tdel_rec
|
||||
del_violation_common: Tdel_rec_tri
|
||||
del_dummy: Tdel_rec
|
||||
del_Hold_D_L: Tdel_rec_tri
|
||||
del_Hold_RAM: Tdel_rec_tri
|
||||
del_Setup_D_L: Tdel_rec_tri
|
||||
del_Setup_RAM: Tdel_rec_tri
|
||||
del_Hold_SN_RN: Tdel_rec_tri
|
||||
del_Setup_SN_RN: Tdel_rec_tri
|
||||
del_Hold_RN_SN: Tdel_rec_tri
|
||||
del_Setup_RN_SN: Tdel_rec_tri
|
||||
del_bot_couty2: Tdel_rec
|
||||
del_bot_glb_couty2: Tdel_rec
|
||||
del_bot_SB_couty2: Tdel_rec
|
||||
del_bot_pouty2: Tdel_rec
|
||||
del_bot_glb_pouty2: Tdel_rec
|
||||
del_bot_SB_pouty2: Tdel_rec
|
||||
del_left_couty2: Tdel_rec
|
||||
del_left_glb_couty2: Tdel_rec
|
||||
del_left_SB_couty2: Tdel_rec
|
||||
del_left_pouty2: Tdel_rec
|
||||
del_left_glb_pouty2: Tdel_rec
|
||||
del_left_SB_pouty2: Tdel_rec
|
||||
del_inp: List[Tdel_rec]
|
||||
del_CPE_out_mux: List[Tdel_rec]
|
||||
del_CPE_CP_Q: Tdel_rec
|
||||
del_CPE_S_Q: Tdel_rec
|
||||
del_CPE_R_Q: Tdel_rec
|
||||
del_CPE_D_Q: Tdel_rec
|
||||
del_RAM_CLK_DO: Tdel_rec
|
||||
del_GLBOUT_sb_big: Tdel_rec
|
||||
del_sb_drv: Tdel_rec
|
||||
del_CP_carry_path: Tdel_rec
|
||||
del_CP_prop_path: Tdel_rec
|
||||
del_special_RAM_I: Tdel_rec
|
||||
del_RAMO_xOBF: Tdel_rec
|
||||
del_GLBOUT_IO_SEL: Tdel_rec
|
||||
del_IO_SEL_Q_out: Tdel_rec
|
||||
del_IO_SEL_Q_in: Tdel_rec
|
||||
in_delayline_per_stage: Tdel_rec
|
||||
out_delayline_per_stage: Tdel_rec
|
||||
del_IBF: Tdel_rec
|
||||
del_OBF: Tdel_rec
|
||||
del_r_OBF: Tdel_rec
|
||||
del_TOBF_ctrl: Tdel_rec
|
||||
del_LVDS_IBF: Tdel_rec
|
||||
del_LVDS_OBF: Tdel_rec
|
||||
del_LVDS_r_OBF: Tdel_rec
|
||||
del_LVDS_TOBF_ctrl: Tdel_rec
|
||||
del_CP_clkin: Tdel_rec
|
||||
del_CP_enin: Tdel_rec
|
||||
del_preplace: Tdel_rec
|
||||
del_CPE_timing_mod: List[Tdel_rec]
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(mv: memoryview, offset: int) -> ('ExtraTimingDelays', int):
|
||||
skew_report_del, fix_skew_del = struct.unpack_from('<2i', mv, offset)
|
||||
offset += 8
|
||||
|
||||
del_rec_0, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_min_route_SB, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_violation_common, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_dummy, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_Hold_D_L, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_Hold_RAM, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_Setup_D_L, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_Setup_RAM, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_Hold_SN_RN, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_Setup_SN_RN, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_Hold_RN_SN, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
del_Setup_RN_SN, offset = Tdel_rec_tri.from_bytes(mv, offset)
|
||||
|
||||
del_bot_couty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_bot_glb_couty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_bot_SB_couty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_bot_pouty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_bot_glb_pouty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_bot_SB_pouty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_left_couty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_left_glb_couty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_left_SB_couty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_left_pouty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_left_glb_pouty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_left_SB_pouty2, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_inp = []
|
||||
for _ in range(8):
|
||||
rec, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_inp.append(rec)
|
||||
|
||||
del_CPE_out_mux = []
|
||||
for _ in range(4):
|
||||
rec, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_CPE_out_mux.append(rec)
|
||||
|
||||
del_CPE_CP_Q, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_CPE_S_Q, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_CPE_R_Q, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_CPE_D_Q, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_RAM_CLK_DO, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_GLBOUT_sb_big, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_sb_drv, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_CP_carry_path, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_CP_prop_path, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_special_RAM_I, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_RAMO_xOBF, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_GLBOUT_IO_SEL, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_IO_SEL_Q_out, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_IO_SEL_Q_in, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
in_delayline_per_stage, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
out_delayline_per_stage, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_IBF, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_OBF, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_r_OBF, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_TOBF_ctrl, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_LVDS_IBF, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_LVDS_OBF, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_LVDS_r_OBF, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_LVDS_TOBF_ctrl, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_CP_clkin, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_CP_enin, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_preplace, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
|
||||
del_CPE_timing_mod = []
|
||||
for _ in range(42):
|
||||
rec, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
del_CPE_timing_mod.append(rec)
|
||||
|
||||
return ExtraTimingDelays(
|
||||
skew_report_del, fix_skew_del,
|
||||
del_rec_0, del_min_route_SB,
|
||||
del_violation_common, del_dummy,
|
||||
del_Hold_D_L, del_Hold_RAM, del_Setup_D_L, del_Setup_RAM,
|
||||
del_Hold_SN_RN, del_Setup_SN_RN, del_Hold_RN_SN, del_Setup_RN_SN,
|
||||
del_bot_couty2, del_bot_glb_couty2, del_bot_SB_couty2,
|
||||
del_bot_pouty2, del_bot_glb_pouty2, del_bot_SB_pouty2,
|
||||
del_left_couty2, del_left_glb_couty2, del_left_SB_couty2,
|
||||
del_left_pouty2, del_left_glb_pouty2, del_left_SB_pouty2,
|
||||
del_inp, del_CPE_out_mux,
|
||||
del_CPE_CP_Q, del_CPE_S_Q, del_CPE_R_Q, del_CPE_D_Q,
|
||||
del_RAM_CLK_DO, del_GLBOUT_sb_big, del_sb_drv,
|
||||
del_CP_carry_path, del_CP_prop_path,
|
||||
del_special_RAM_I, del_RAMO_xOBF,
|
||||
del_GLBOUT_IO_SEL, del_IO_SEL_Q_out, del_IO_SEL_Q_in,
|
||||
in_delayline_per_stage, out_delayline_per_stage,
|
||||
del_IBF, del_OBF, del_r_OBF, del_TOBF_ctrl,
|
||||
del_LVDS_IBF, del_LVDS_OBF, del_LVDS_r_OBF, del_LVDS_TOBF_ctrl,
|
||||
del_CP_clkin, del_CP_enin, del_preplace,
|
||||
del_CPE_timing_mod
|
||||
), offset
|
||||
|
||||
def read_IM_del_tile_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(2): # [1..2]
|
||||
level1 = []
|
||||
for i2 in range(8): # [1..8]
|
||||
level2 = []
|
||||
for i3 in range(8): # [1..8]
|
||||
level3 = []
|
||||
for i4 in range(12): # [1..12]
|
||||
level4 = []
|
||||
for i5 in range(8): # [0..7]
|
||||
delay = T_delay.from_bytes(mv[offset:offset+24])
|
||||
offset += 24
|
||||
level4.append(delay)
|
||||
level3.append(level4)
|
||||
level2.append(level3)
|
||||
level1.append(level2)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_OM_del_tile_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(8): # [1..8]
|
||||
level1 = []
|
||||
for i2 in range(8): # [1..8]
|
||||
level2 = []
|
||||
for i3 in range(4): # [9..12]
|
||||
level3 = []
|
||||
for i4 in range(4): # [0..3]
|
||||
delay = T_delay.from_bytes(mv[offset:offset+24])
|
||||
offset += 24
|
||||
level3.append(delay)
|
||||
level2.append(level3)
|
||||
level1.append(level2)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_CPE_del_tile_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(10): # [0..9]
|
||||
level1 = []
|
||||
for i2 in range(19): # [1..19]
|
||||
level2 = []
|
||||
for i3 in range(10): # [1..10]
|
||||
rec, offset = Tdel_rec.from_bytes(mv, offset)
|
||||
level2.append(rec)
|
||||
level1.append(level2)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_SB_del_rim_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(165): # [-2..162]
|
||||
level1 = []
|
||||
for i2 in range(4): # [1..4]
|
||||
level2 = []
|
||||
for i3 in range(12): # [1..12]
|
||||
level3 = []
|
||||
for i4 in range(5): # [0..4]
|
||||
level4 = []
|
||||
for i5 in range(8): # [0..7]
|
||||
delay = T_delay.from_bytes(mv[offset:offset+24])
|
||||
offset += 24
|
||||
level4.append(delay)
|
||||
level3.append(level4)
|
||||
level2.append(level3)
|
||||
level1.append(level2)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_Edge_del_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(165): # [-2..162]
|
||||
level1 = []
|
||||
for i2 in range(4): # [1..4]
|
||||
level2 = []
|
||||
for i3 in range(24): # [1..24]
|
||||
level3 = []
|
||||
for i4 in range(8): # [1..8]
|
||||
delay = T_delay.from_bytes(mv[offset:offset+24])
|
||||
offset += 24
|
||||
level3.append(delay)
|
||||
level2.append(level3)
|
||||
level1.append(level2)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_IO_SEL_del_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(11): # [1..11]
|
||||
level1 = []
|
||||
for i2 in range(4): # [1..4]
|
||||
delay = T_delay.from_bytes(mv[offset:offset+24])
|
||||
offset += 24
|
||||
level1.append(delay)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_CLKIN_del_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(7):
|
||||
level1 = []
|
||||
for i2 in range(4):
|
||||
delay = T_delay.from_bytes(mv[offset:offset + 24])
|
||||
offset += 24
|
||||
level1.append(delay)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_GLBOUT_del_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(28):
|
||||
level1 = []
|
||||
for i2 in range(8):
|
||||
delay = T_delay.from_bytes(mv[offset:offset + 24])
|
||||
offset += 24
|
||||
level1.append(delay)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_PLL_del_arr_from_bytes(mv: memoryview, offset: int) -> (List, int):
|
||||
result = []
|
||||
for i1 in range(7):
|
||||
level1 = []
|
||||
for i2 in range(6):
|
||||
delay = T_delay.from_bytes(mv[offset:offset + 24])
|
||||
offset += 24
|
||||
level1.append(delay)
|
||||
result.append(level1)
|
||||
return result, offset
|
||||
|
||||
def read_Tentry_rec_from_bytes(data: memoryview, offset: int) -> ('Tentry_rec', int):
|
||||
pins_i, pins_val, entry_no = struct.unpack_from('<3h', data, offset)
|
||||
return Tentry_rec(Tpin_pair(pins_i, pins_val), entry_no), offset + 6
|
||||
|
||||
def read_Tdel_entry_from_bytes(data: memoryview, offset: int) -> ('Tdel_entry', int):
|
||||
key, edge1, edge2 = struct.unpack_from('<3i', data, offset)
|
||||
time1 = T_delay_tri.from_bytes(data[offset + 12:offset + 24])
|
||||
time2 = T_delay_tri.from_bytes(data[offset + 24:offset + 36])
|
||||
return Tdel_entry(key, edge1, edge2, time1, time2), offset + 36
|
||||
|
||||
def read_TRAM_del_rec_from_bytes(mv: memoryview, offset: int) -> (TRAM_del_rec, int):
|
||||
iopath = []
|
||||
for _ in range(3001):
|
||||
entry, offset = read_Tentry_rec_from_bytes(mv, offset)
|
||||
iopath.append(entry)
|
||||
|
||||
setuphold = []
|
||||
for _ in range(8001):
|
||||
entry, offset = read_Tentry_rec_from_bytes(mv, offset)
|
||||
setuphold.append(entry)
|
||||
|
||||
width = []
|
||||
for _ in range(51):
|
||||
entry, offset = read_Tentry_rec_from_bytes(mv, offset)
|
||||
width.append(entry)
|
||||
|
||||
del_entry = []
|
||||
offset += 2 # alignment added
|
||||
for _ in range(101):
|
||||
entry, offset = read_Tdel_entry_from_bytes(mv, offset)
|
||||
del_entry.append(entry)
|
||||
|
||||
return TRAM_del_rec(iopath, setuphold, width, del_entry), offset
|
||||
|
||||
def read_IO_SEL_io_coef_from_bytes(mv: memoryview, offset: int) -> (list, int):
|
||||
result = []
|
||||
for i1 in range(4): # [1..4]
|
||||
row = []
|
||||
for i2 in range(27): # [1..27]
|
||||
value = struct.unpack_from('<d', mv, offset)[0] # '<d' = little-endian double
|
||||
offset += 8
|
||||
row.append(value)
|
||||
result.append(row)
|
||||
return result, offset
|
||||
|
||||
@dataclass
|
||||
class Tdel_all_rec:
|
||||
SB_del_tile_arr: List[List[List[List[List[List[T_delay]]]]]]
|
||||
IM_del_tile_arr: List[List[List[List[List[T_delay]]]]]
|
||||
OM_del_tile_arr: List[List[List[List[T_delay]]]]
|
||||
CPE_del_tile_arr: List[List[List[Tdel_rec]]]
|
||||
SB_del_rim_arr: List[List[List[List[List[T_delay]]]]]
|
||||
Edge_del_arr: List[List[List[List[T_delay]]]]
|
||||
IO_SEL_del_arr: List[List[T_delay]]
|
||||
CLKIN_del_arr: List[List[T_delay]]
|
||||
GLBOUT_del_arr: List[List[T_delay]]
|
||||
PLL_del_arr: List[List[T_delay]]
|
||||
FPGA_ram_del_1: TRAM_del_rec
|
||||
FPGA_ram_del_2: TRAM_del_rec
|
||||
FPGA_ram_del_3: TRAM_del_rec
|
||||
IO_SEL_io_coef: list[list[float]]
|
||||
timing_delays: ExtraTimingDelays
|
||||
|
||||
@staticmethod
|
||||
def from_bytes(data: bytes) -> 'Tdel_all_rec':
|
||||
offset = 0
|
||||
sb_del_tile_arr, offset = read_SB_del_tile_arr_from_bytes(data, offset)
|
||||
im, offset = read_IM_del_tile_arr_from_bytes(data, offset)
|
||||
om, offset = read_OM_del_tile_arr_from_bytes(data, offset)
|
||||
cpe, offset = read_CPE_del_tile_arr_from_bytes(data, offset)
|
||||
sb_del_rim, offset = read_SB_del_rim_arr_from_bytes(data, offset)
|
||||
edge, offset = read_Edge_del_arr_from_bytes(data, offset)
|
||||
io_sel, offset = read_IO_SEL_del_arr_from_bytes(data, offset)
|
||||
clkin, offset = read_CLKIN_del_arr_from_bytes(data, offset)
|
||||
glbout, offset = read_GLBOUT_del_arr_from_bytes(data, offset)
|
||||
pll_del, offset = read_PLL_del_arr_from_bytes(data, offset)
|
||||
fpga_ram_del_1, offset = read_TRAM_del_rec_from_bytes(data, offset)
|
||||
fpga_ram_del_2, offset = read_TRAM_del_rec_from_bytes(data, offset)
|
||||
fpga_ram_del_3, offset = read_TRAM_del_rec_from_bytes(data, offset)
|
||||
io_sel_coef, offset = read_IO_SEL_io_coef_from_bytes(data, offset)
|
||||
timing_delays, offset = ExtraTimingDelays.from_bytes(data, offset)
|
||||
return Tdel_all_rec(sb_del_tile_arr, im, om, cpe, sb_del_rim, edge, io_sel, clkin, glbout, pll_del, fpga_ram_del_1, fpga_ram_del_2, fpga_ram_del_3,io_sel_coef, timing_delays)
|
||||
|
||||
|
||||
def decompress_timing(input_path) -> 'Tdel_all_rec':
|
||||
with open(input_path, 'rb') as f_in:
|
||||
compressed_data = f_in.read()
|
||||
try:
|
||||
decompressed_data = zlib.decompress(compressed_data)
|
||||
except zlib.error as e:
|
||||
print(f"Decompression failed: {e}")
|
||||
return
|
||||
|
||||
return Tdel_all_rec.from_bytes(decompressed_data)
|
||||
|
||||
# Example usage
|
||||
#decompress_timing("cc_best_eco_dly.dly")
|
||||
#decompress_timing("cc_best_lpr_dly.dly")
|
||||
#decompress_timing("cc_best_spd_dly.dly")
|
||||
#
|
||||
#decompress_timing("cc_typ_eco_dly.dly")
|
||||
#decompress_timing("cc_typ_lpr_dly.dly")
|
||||
#decompress_timing("cc_typ_spd_dly.dly")
|
||||
#
|
||||
#decompress_timing("cc_worst_eco_dly.dly")
|
||||
#decompress_timing("cc_worst_lpr_dly.dly")
|
||||
#decompress_timing("cc_worst_spd_dly.dly")
|
||||
Loading…
Reference in New Issue