Progress with chipdb refactoring
Signed-off-by: Clifford Wolf <clifford@clifford.at>
This commit is contained in:
parent
ad0df6cea8
commit
f0edb625e3
@ -153,7 +153,7 @@ BelId Chip::getBelByName(IdString name) const
|
||||
|
||||
if (bel_by_name.empty()) {
|
||||
for (int i = 0; i < chip_info.num_bels; i++)
|
||||
bel_by_name[chip_info.bel_data[i].name] = i;
|
||||
bel_by_name[chip_info.bel_data[i].name.ptr()] = i;
|
||||
}
|
||||
|
||||
auto it = bel_by_name.find(name);
|
||||
@ -190,7 +190,7 @@ WireId Chip::getWireBelPin(BelId bel, PortPin pin) const
|
||||
assert(bel != BelId());
|
||||
|
||||
int num_bel_wires = chip_info.bel_data[bel.index].num_bel_wires;
|
||||
BelWirePOD *bel_wires = chip_info.bel_data[bel.index].bel_wires;
|
||||
BelWirePOD *bel_wires = chip_info.bel_data[bel.index].bel_wires.ptr();
|
||||
|
||||
for (int i = 0; i < num_bel_wires; i++)
|
||||
if (bel_wires[i].port == pin) {
|
||||
|
45
ice40/chip.h
45
ice40/chip.h
@ -72,7 +72,6 @@ PortPin portPinFromId(IdString id);
|
||||
|
||||
// -----------------------------------------------------------------------
|
||||
|
||||
#if 0
|
||||
template <typename T>
|
||||
struct RelPtr {
|
||||
int offset;
|
||||
@ -87,16 +86,17 @@ struct RelPtr {
|
||||
T*operator->() {
|
||||
return reinterpret_cast<T*>(reinterpret_cast<char*>(this) + offset);
|
||||
}
|
||||
|
||||
T*ptr() {
|
||||
return reinterpret_cast<T*>(reinterpret_cast<char*>(this) + offset);
|
||||
}
|
||||
};
|
||||
#else
|
||||
template <typename T> using RelPtr = T *;
|
||||
#endif
|
||||
|
||||
struct BelWirePOD
|
||||
{
|
||||
int32_t wire_index;
|
||||
PortPin port;
|
||||
};
|
||||
} __attribute__((packed));
|
||||
|
||||
struct BelInfoPOD
|
||||
{
|
||||
@ -105,13 +105,14 @@ struct BelInfoPOD
|
||||
int32_t num_bel_wires;
|
||||
RelPtr<BelWirePOD> bel_wires;
|
||||
int8_t x, y, z;
|
||||
};
|
||||
int8_t filler_0;
|
||||
} __attribute__((packed));
|
||||
|
||||
struct BelPortPOD
|
||||
{
|
||||
int32_t bel_index;
|
||||
PortPin port;
|
||||
};
|
||||
} __attribute__((packed));
|
||||
|
||||
struct PipInfoPOD
|
||||
{
|
||||
@ -120,33 +121,33 @@ struct PipInfoPOD
|
||||
int8_t x, y;
|
||||
int16_t switch_mask;
|
||||
int32_t switch_index;
|
||||
};
|
||||
} __attribute__((packed));
|
||||
|
||||
struct WireInfoPOD
|
||||
{
|
||||
RelPtr<char> name;
|
||||
const char *name;
|
||||
int32_t num_uphill, num_downhill;
|
||||
RelPtr<int32_t> pips_uphill, pips_downhill;
|
||||
int32_t *pips_uphill, *pips_downhill;
|
||||
|
||||
int32_t num_bels_downhill;
|
||||
BelPortPOD bel_uphill;
|
||||
RelPtr<BelPortPOD> bels_downhill;
|
||||
BelPortPOD *bels_downhill;
|
||||
|
||||
int8_t x, y;
|
||||
};
|
||||
} __attribute__((packed));
|
||||
|
||||
struct PackagePinPOD
|
||||
{
|
||||
const char *name;
|
||||
int32_t bel_index;
|
||||
};
|
||||
} __attribute__((packed));
|
||||
|
||||
struct PackageInfoPOD
|
||||
{
|
||||
const char *name;
|
||||
int num_pins;
|
||||
PackagePinPOD *pins;
|
||||
};
|
||||
} __attribute__((packed));
|
||||
|
||||
enum TileType
|
||||
{
|
||||
@ -160,21 +161,21 @@ enum TileType
|
||||
struct ConfigBitPOD
|
||||
{
|
||||
int8_t row, col;
|
||||
};
|
||||
} __attribute__((packed));
|
||||
|
||||
struct ConfigEntryPOD
|
||||
{
|
||||
const char *name;
|
||||
int num_bits;
|
||||
ConfigBitPOD *bits;
|
||||
};
|
||||
} __attribute__((packed));
|
||||
|
||||
struct TileInfoPOD
|
||||
{
|
||||
int8_t cols, rows;
|
||||
int num_config_entries;
|
||||
ConfigEntryPOD *entries;
|
||||
};
|
||||
} __attribute__((packed));
|
||||
|
||||
static const int max_switch_bits = 5;
|
||||
|
||||
@ -183,13 +184,13 @@ struct SwitchInfoPOD
|
||||
int8_t x, y;
|
||||
int num_bits;
|
||||
ConfigBitPOD cbits[max_switch_bits];
|
||||
};
|
||||
} __attribute__((packed));
|
||||
|
||||
struct IerenInfoPOD
|
||||
{
|
||||
int8_t iox, ioy, ioz;
|
||||
int8_t ierx, iery, ierz;
|
||||
};
|
||||
} __attribute__((packed));
|
||||
|
||||
struct BitstreamInfoPOD
|
||||
{
|
||||
@ -197,7 +198,7 @@ struct BitstreamInfoPOD
|
||||
TileInfoPOD *tiles_nonrouting;
|
||||
SwitchInfoPOD *switches;
|
||||
IerenInfoPOD *ierens;
|
||||
};
|
||||
} __attribute__((packed));
|
||||
|
||||
struct ChipInfoPOD
|
||||
{
|
||||
@ -210,7 +211,7 @@ struct ChipInfoPOD
|
||||
TileType *tile_grid;
|
||||
BitstreamInfoPOD *bits_info;
|
||||
PackageInfoPOD *packages_data;
|
||||
};
|
||||
} __attribute__((packed));
|
||||
|
||||
extern ChipInfoPOD chip_info_384;
|
||||
extern ChipInfoPOD chip_info_1k;
|
||||
@ -476,7 +477,7 @@ struct Chip
|
||||
IdString getBelName(BelId bel) const
|
||||
{
|
||||
assert(bel != BelId());
|
||||
return chip_info.bel_data[bel.index].name;
|
||||
return chip_info.bel_data[bel.index].name.ptr();
|
||||
}
|
||||
|
||||
void bindBel(BelId bel, IdString cell)
|
||||
|
159
ice40/chipdb.py
159
ice40/chipdb.py
@ -4,6 +4,8 @@ import sys
|
||||
import re
|
||||
import textwrap
|
||||
|
||||
endianness = "le"
|
||||
|
||||
dev_name = None
|
||||
dev_width = None
|
||||
dev_height = None
|
||||
@ -39,6 +41,25 @@ tile_bits = [[] for _ in range(num_tile_types)]
|
||||
|
||||
cbit_re = re.compile(r'B(\d+)\[(\d+)\]')
|
||||
|
||||
portpins = dict()
|
||||
beltypes = dict()
|
||||
|
||||
with open("ice40/portpins.inc") as f:
|
||||
for line in f:
|
||||
line = line.replace("(", " ")
|
||||
line = line.replace(")", " ")
|
||||
line = line.split()
|
||||
if len(line) == 0:
|
||||
continue
|
||||
assert len(line) == 2
|
||||
assert line[0] == "X"
|
||||
idx = len(portpins) + 1
|
||||
portpins[line[1]] = idx
|
||||
|
||||
beltypes["ICESTORM_LC"] = 1
|
||||
beltypes["ICESTORM_RAM"] = 2
|
||||
beltypes["SB_IO"] = 3
|
||||
beltypes["SB_GB"] = 4
|
||||
|
||||
def maj_wire_name(name):
|
||||
if re.match(r"lutff_\d/(in|out)", name[2]):
|
||||
@ -344,24 +365,144 @@ elif dev_name == "384":
|
||||
add_bel_gb( 3, 0, 5)
|
||||
add_bel_gb( 3, 9, 4)
|
||||
|
||||
class BinaryBlobAssembler:
|
||||
def __init__(self):
|
||||
self.data = bytearray()
|
||||
self.comments = dict()
|
||||
self.labels = dict()
|
||||
self.labels_byaddr = dict()
|
||||
self.ltypes_byaddr = dict()
|
||||
self.refs = dict()
|
||||
|
||||
def l(self, name, ltype = None):
|
||||
assert name not in self.labels
|
||||
assert len(self.data) not in self.labels_byaddr
|
||||
self.labels[name] = len(self.data)
|
||||
if ltype is not None:
|
||||
self.ltypes_byaddr[len(self.data)] = ltype
|
||||
self.labels_byaddr[len(self.data)] = name
|
||||
|
||||
def r(self, name, comment):
|
||||
assert len(self.data) not in self.refs
|
||||
self.refs[len(self.data)] = (name, comment)
|
||||
self.data.append(0)
|
||||
self.data.append(0)
|
||||
self.data.append(0)
|
||||
self.data.append(0)
|
||||
|
||||
def s(self, v, comment):
|
||||
for i in range(len(v)):
|
||||
self.data.append(ord(v[i]))
|
||||
self.data.append(0)
|
||||
self.comments[len(self.data)] = comment
|
||||
|
||||
def u8(self, v, comment):
|
||||
self.data.append(v)
|
||||
self.comments[len(self.data)] = comment
|
||||
|
||||
def u16(self, v, comment):
|
||||
if endianness == "le":
|
||||
self.data.append(v & 255)
|
||||
self.data.append((v >> 8) & 255)
|
||||
elif endianness == "be":
|
||||
self.data.append((v >> 8) & 255)
|
||||
self.data.append(v & 255)
|
||||
else:
|
||||
assert 0
|
||||
self.comments[len(self.data)] = comment
|
||||
|
||||
def u32(self, v, comment):
|
||||
if endianness == "le":
|
||||
self.data.append(v & 255)
|
||||
self.data.append((v >> 8) & 255)
|
||||
self.data.append((v >> 16) & 255)
|
||||
self.data.append((v >> 24) & 255)
|
||||
elif endianness == "be":
|
||||
self.data.append((v >> 24) & 255)
|
||||
self.data.append((v >> 16) & 255)
|
||||
self.data.append((v >> 8) & 255)
|
||||
self.data.append(v & 255)
|
||||
else:
|
||||
assert 0
|
||||
self.comments[len(self.data)] = comment
|
||||
|
||||
def write_c(self, f):
|
||||
cursor = 0
|
||||
bytecnt = 0
|
||||
while cursor < len(self.data):
|
||||
if cursor in self.comments:
|
||||
if bytecnt == 0:
|
||||
print(" ", end="")
|
||||
print(" // %s" % self.comments[cursor])
|
||||
bytecnt = 0
|
||||
if cursor in self.labels_byaddr:
|
||||
if bytecnt != 0:
|
||||
print()
|
||||
if cursor in self.ltypes_byaddr:
|
||||
print("#define %s ((%s*)(binblob_%s+%d))" % (self.labels_byaddr[cursor], self.ltypes_byaddr[cursor], dev_name, cursor))
|
||||
else:
|
||||
print(" // [%d] %s" % (cursor, self.labels_byaddr[cursor]))
|
||||
bytecnt = 0
|
||||
if cursor in self.refs:
|
||||
v = self.labels[self.refs[cursor][0]] - cursor
|
||||
if bytecnt != 0:
|
||||
print()
|
||||
print(" ", end="")
|
||||
if endianness == "le":
|
||||
print(" %3d," % (v & 255), end="")
|
||||
print(" %3d," % ((v >> 8) & 255), end="")
|
||||
print(" %3d," % ((v >> 16) & 255), end="")
|
||||
print(" %3d," % ((v >> 24) & 255), end="")
|
||||
elif endianness == "be":
|
||||
print(" %3d," % (v & 255), end="")
|
||||
print(" %3d," % ((v >> 8) & 255), end="")
|
||||
print(" %3d," % ((v >> 16) & 255), end="")
|
||||
print(" %3d," % ((v >> 24) & 255), end="")
|
||||
else:
|
||||
assert 0
|
||||
print(" // [%d] %s (reference to %s)" % (cursor, self.refs[cursor][1], self.refs[cursor][0]))
|
||||
bytecnt = 0
|
||||
cursor += 4
|
||||
else:
|
||||
if bytecnt == 0:
|
||||
print(" ", end="")
|
||||
print(" %3d," % self.data[cursor], end=("" if bytecnt < 15 else "\n"))
|
||||
bytecnt = (bytecnt + 1) & 15
|
||||
cursor += 1
|
||||
if bytecnt != 0:
|
||||
print()
|
||||
|
||||
bba = BinaryBlobAssembler()
|
||||
|
||||
print('#include "nextpnr.h"')
|
||||
print('namespace {')
|
||||
print('USING_NEXTPNR_NAMESPACE')
|
||||
|
||||
index = 0
|
||||
print("static BelWirePOD bel_wires[] = {")
|
||||
for bel in range(len(bel_name)):
|
||||
print("#define bel_wires_%d (bel_wires+%d)" % (bel, index))
|
||||
bba.l("bel_wires_%d" % bel, "BelWirePOD")
|
||||
for i in range(len(bel_wires[bel])):
|
||||
print(" {%d, PIN_%s}," % bel_wires[bel][i])
|
||||
bba.u32(bel_wires[bel][i][0], "wire_index")
|
||||
bba.u32(portpins[bel_wires[bel][i][1]], "port")
|
||||
index += 1
|
||||
print("};")
|
||||
|
||||
print("static BelInfoPOD bel_data_%s[%d] = {" % (dev_name, len(bel_name)))
|
||||
for bel in range(len(bel_name)):
|
||||
print(" {\"%s\", TYPE_%s, %d, bel_wires_%d, %d, %d, %d}%s" % (bel_name[bel], bel_type[bel],
|
||||
len(bel_wires[bel]), bel, bel_pos[bel][0], bel_pos[bel][1], bel_pos[bel][2],
|
||||
"," if bel+1 < len(bel_name) else ""))
|
||||
bba.l("bel_name_%d" % bel, "char")
|
||||
bba.s(bel_name[bel], "name: %s" % bel_name[bel])
|
||||
|
||||
bba.l("bel_data", "BelInfoPOD")
|
||||
for bel in range(len(bel_name)):
|
||||
bba.r("bel_name_%d" % bel, "name")
|
||||
bba.u32(beltypes[bel_type[bel]], "type")
|
||||
bba.u32(len(bel_wires[bel]), "num_bel_wires")
|
||||
bba.r("bel_wires_%d" % bel, "bel_wires")
|
||||
bba.u8(bel_pos[bel][0], "x")
|
||||
bba.u8(bel_pos[bel][1], "y")
|
||||
bba.u8(bel_pos[bel][2], "z")
|
||||
bba.u8(0, "filler")
|
||||
|
||||
print("static uint8_t binblob_%s[] = {" % dev_name)
|
||||
bba.write_c(sys.stdout)
|
||||
print("};")
|
||||
|
||||
wireinfo = list()
|
||||
@ -540,7 +681,7 @@ print('NEXTPNR_NAMESPACE_BEGIN')
|
||||
|
||||
print("ChipInfoPOD chip_info_%s = {" % dev_name)
|
||||
print(" %d, %d, %d, %d, %d, %d, %d," % (dev_width, dev_height, len(bel_name), num_wires, len(pipinfo), len(switchinfo), len(packageinfo)))
|
||||
print(" bel_data_%s, wire_data_%s, pip_data_%s," % (dev_name, dev_name, dev_name))
|
||||
print(" bel_data, wire_data_%s, pip_data_%s," % (dev_name, dev_name))
|
||||
print(" tile_grid_%s, &bits_info_%s, package_info_%s" % (dev_name, dev_name, dev_name))
|
||||
print("};")
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user