Implement GCK limitations
This commit is contained in:
parent
e1837b781b
commit
9baf87e2a6
@ -20,7 +20,15 @@ NPNR_PACKED_STRUCT(struct NGUltraPipExtraDataPOD {
|
|||||||
});
|
});
|
||||||
|
|
||||||
NPNR_PACKED_STRUCT(struct NGUltraBelExtraDataPOD { int32_t flags; });
|
NPNR_PACKED_STRUCT(struct NGUltraBelExtraDataPOD { int32_t flags; });
|
||||||
|
|
||||||
|
struct GckConfig {
|
||||||
|
explicit GckConfig(BelId belid) { bel = belid; si1 = IdString(); si2 = IdString(); used = false; }
|
||||||
|
BelId bel;
|
||||||
|
IdString si1;
|
||||||
|
IdString si2;
|
||||||
|
bool used;
|
||||||
|
};
|
||||||
|
|
||||||
enum TILETypeZ
|
enum TILETypeZ
|
||||||
{
|
{
|
||||||
BEL_LUT_Z = 0,
|
BEL_LUT_Z = 0,
|
||||||
|
@ -52,6 +52,8 @@ void NgUltraImpl::init_database(Arch *arch)
|
|||||||
void NgUltraImpl::init(Context *ctx)
|
void NgUltraImpl::init(Context *ctx)
|
||||||
{
|
{
|
||||||
HimbaechelAPI::init(ctx);
|
HimbaechelAPI::init(ctx);
|
||||||
|
for (int i=1;i<=8;i++)
|
||||||
|
gck_per_lobe[i].reserve(20);
|
||||||
for (auto bel : ctx->getBels()) {
|
for (auto bel : ctx->getBels()) {
|
||||||
if (ctx->getBelType(bel) == id_IOM) {
|
if (ctx->getBelType(bel) == id_IOM) {
|
||||||
std::set<IdString> ckg;
|
std::set<IdString> ckg;
|
||||||
@ -81,8 +83,10 @@ void NgUltraImpl::init(Context *ctx)
|
|||||||
global_capable_bels.emplace(bel,id_P19RI);
|
global_capable_bels.emplace(bel,id_P19RI);
|
||||||
}
|
}
|
||||||
} else if (ctx->getBelType(bel) == id_GCK) {
|
} else if (ctx->getBelType(bel) == id_GCK) {
|
||||||
int lobe = ctx->getBelName(bel)[1].c_str(ctx)[1] - '0';
|
std::string name = ctx->getBelName(bel)[1].c_str(ctx);
|
||||||
gck_per_lobe[lobe].emplace(bel);
|
int lobe = name[1] - '0';
|
||||||
|
int num = atoi(name.substr(4,2).c_str());
|
||||||
|
gck_per_lobe[lobe].insert(gck_per_lobe[lobe].begin()+num-1, GckConfig(bel));
|
||||||
}
|
}
|
||||||
locations.emplace(stringf("%s:%s",tile_name(bel.tile).c_str(), ctx->getBelName(bel)[1].c_str(ctx)),bel);
|
locations.emplace(stringf("%s:%s",tile_name(bel.tile).c_str(), ctx->getBelName(bel)[1].c_str(ctx)),bel);
|
||||||
}
|
}
|
||||||
|
@ -71,7 +71,7 @@ public:
|
|||||||
dict<std::string, std::string> bank_voltage;
|
dict<std::string, std::string> bank_voltage;
|
||||||
dict<BelId,IdString> global_capable_bels;
|
dict<BelId,IdString> global_capable_bels;
|
||||||
dict<std::string,BelId> locations;
|
dict<std::string,BelId> locations;
|
||||||
dict<int,pool<BelId>> gck_per_lobe;
|
dict<int,std::vector<GckConfig>> gck_per_lobe;
|
||||||
|
|
||||||
pool<PipId> blocked_pips;
|
pool<PipId> blocked_pips;
|
||||||
dict<IdString, std::pair<IdString,IdString>> bank_to_ckg;
|
dict<IdString, std::pair<IdString,IdString>> bank_to_ckg;
|
||||||
|
@ -527,12 +527,21 @@ void NgUltraPacker::pack_iobs(void)
|
|||||||
NetInfo *c_net = cell->getPort(id_C);
|
NetInfo *c_net = cell->getPort(id_C);
|
||||||
if (!c_net)
|
if (!c_net)
|
||||||
log_error("C input of IO primitive %s must be connected.\n", cell->name.c_str(ctx));
|
log_error("C input of IO primitive %s must be connected.\n", cell->name.c_str(ctx));
|
||||||
if (c_net->name == ctx->id("$PACKER_GND") && !cell->getPort(id_O))
|
if (c_net->name == ctx->id("$PACKER_GND") && !cell->getPort(id_O)) {
|
||||||
log_error("O port of IO primitive %s must be connected.\n", cell->name.c_str(ctx));
|
log_warning("O port of IO primitive %s must be connected. Removing cell.\n", cell->name.c_str(ctx));
|
||||||
if (c_net->name == ctx->id("$PACKER_VCC") && !cell->getPort(id_I))
|
packed_cells.emplace(cell->name);
|
||||||
log_error("I port of IO primitive %s must be connected.\n", cell->name.c_str(ctx));
|
continue;
|
||||||
if (!cell->getPort(id_I) && !cell->getPort(id_O))
|
}
|
||||||
log_error("I or O port of IO primitive %s must be connected.\n", cell->name.c_str(ctx));
|
if (c_net->name == ctx->id("$PACKER_VCC") && !cell->getPort(id_I)) {
|
||||||
|
log_warning("I port of IO primitive %s must be connected. Removing cell.\n", cell->name.c_str(ctx));
|
||||||
|
packed_cells.emplace(cell->name);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (!cell->getPort(id_I) && !cell->getPort(id_O)) {
|
||||||
|
log_warning("I or O port of IO primitive %s must be connected. Removing cell.\n", cell->name.c_str(ctx));
|
||||||
|
packed_cells.emplace(cell->name);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
{
|
{
|
||||||
CellInfo *iod = net_driven_by(ctx, c_net, is_dfr, id_O);
|
CellInfo *iod = net_driven_by(ctx, c_net, is_dfr, id_O);
|
||||||
@ -633,6 +642,7 @@ void NgUltraPacker::pack_iobs(void)
|
|||||||
}
|
}
|
||||||
if (bfr_added)
|
if (bfr_added)
|
||||||
log_info(" %6d DFRs/DDFRs used as BFR\n", bfr_added);
|
log_info(" %6d DFRs/DDFRs used as BFR\n", bfr_added);
|
||||||
|
flush_cells();
|
||||||
}
|
}
|
||||||
|
|
||||||
void NgUltraPacker::pack_ioms(void)
|
void NgUltraPacker::pack_ioms(void)
|
||||||
@ -2035,6 +2045,27 @@ void NgUltraImpl::postPlace()
|
|||||||
ctx->assignArchInfo();
|
ctx->assignArchInfo();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
BelId NgUltraPacker::get_available_gck(int lobe, NetInfo *si1, NetInfo *si2)
|
||||||
|
{
|
||||||
|
auto &gcks = uarch->gck_per_lobe[lobe];
|
||||||
|
for(int i=0;i<20;i++) {
|
||||||
|
auto &g = gcks.at(i);
|
||||||
|
if (g.used) continue;
|
||||||
|
if (si1 && g.si1!=IdString() && g.si1!=si1->name) continue;
|
||||||
|
if (si2 && g.si2!=IdString() && g.si2!=si2->name) continue;
|
||||||
|
if (si1) g.si1 = si1->name;
|
||||||
|
if (si2) g.si2 = si2->name;
|
||||||
|
g.used = true;
|
||||||
|
if (i%2==0) {
|
||||||
|
// next GCK share inputs in reverse order
|
||||||
|
if (si2) gcks.at(i+1).si1 = si2->name;
|
||||||
|
if (si1) gcks.at(i+1).si2 = si1->name;
|
||||||
|
}
|
||||||
|
return g.bel;
|
||||||
|
}
|
||||||
|
log_error("No GCK left to promote global signal.\n");
|
||||||
|
return BelId();
|
||||||
|
}
|
||||||
void NgUltraPacker::duplicate_gck()
|
void NgUltraPacker::duplicate_gck()
|
||||||
{
|
{
|
||||||
// Unbind all GCKs that are inserted
|
// Unbind all GCKs that are inserted
|
||||||
@ -2115,11 +2146,7 @@ void NgUltraPacker::duplicate_gck()
|
|||||||
NetInfo *si2 = driver->getPort(id_SI2);
|
NetInfo *si2 = driver->getPort(id_SI2);
|
||||||
NetInfo *cmd = driver->getPort(id_CMD);
|
NetInfo *cmd = driver->getPort(id_CMD);
|
||||||
for (auto &conn : connections) {
|
for (auto &conn : connections) {
|
||||||
pool<BelId>& gck = uarch->gck_per_lobe[conn.first];
|
BelId bel = get_available_gck(conn.first, si1, si2);
|
||||||
if (gck.size()==0)
|
|
||||||
log_error("No GCK left to promote global signal.\n");
|
|
||||||
|
|
||||||
BelId bel = gck.pop();
|
|
||||||
CellInfo *gck_cell = nullptr;
|
CellInfo *gck_cell = nullptr;
|
||||||
if (cnt==0) {
|
if (cnt==0) {
|
||||||
gck_cell = driver;
|
gck_cell = driver;
|
||||||
@ -2218,11 +2245,7 @@ void NgUltraPacker::insert_bypass_gck()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
for (auto &conn : connections) {
|
for (auto &conn : connections) {
|
||||||
pool<BelId>& gck = uarch->gck_per_lobe[conn.first];
|
BelId bel = get_available_gck(conn.first, glb_net, nullptr);
|
||||||
if (gck.size()==0)
|
|
||||||
log_error("No GCK left to promote global signal.\n");
|
|
||||||
|
|
||||||
BelId bel = gck.pop();
|
|
||||||
|
|
||||||
log_info(" Create GCK for lobe %d\n",conn.first);
|
log_info(" Create GCK for lobe %d\n",conn.first);
|
||||||
CellInfo *gck_cell = create_cell_ptr(id_GCK, ctx->id(glb_net->name.str(ctx) + "$gck_"+ std::to_string(conn.first)));
|
CellInfo *gck_cell = create_cell_ptr(id_GCK, ctx->id(glb_net->name.str(ctx) + "$gck_"+ std::to_string(conn.first)));
|
||||||
|
@ -93,6 +93,7 @@ private:
|
|||||||
void mandatory_param(CellInfo *cell, IdString param);
|
void mandatory_param(CellInfo *cell, IdString param);
|
||||||
void disconnect_unused(CellInfo *cell, IdString port);
|
void disconnect_unused(CellInfo *cell, IdString port);
|
||||||
void bind_attr_loc(CellInfo *cell, dict<IdString, Property> *attrs);
|
void bind_attr_loc(CellInfo *cell, dict<IdString, Property> *attrs);
|
||||||
|
BelId get_available_gck(int lobe, NetInfo *si1, NetInfo *si2);
|
||||||
// General helper functions
|
// General helper functions
|
||||||
void flush_cells();
|
void flush_cells();
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user