Skip to content

Commit

Permalink
nexus: Promote CE/LSR globals
Browse files Browse the repository at this point in the history
Signed-off-by: gatecat <[email protected]>
  • Loading branch information
gatecat committed May 6, 2021
1 parent ae8a910 commit 31387db
Show file tree
Hide file tree
Showing 2 changed files with 24 additions and 6 deletions.
9 changes: 5 additions & 4 deletions nexus/arch.h
Original file line number Diff line number Diff line change
Expand Up @@ -785,9 +785,10 @@ enum CellPinStyle

PINDEF_MASK = 0x30,

PINGLB_CLK = 0x100, // pin is a 'clock' for global purposes
PINGLB_CLK = 0x100, // pin is a 'clock' for global purposes
PINGLB_CE_LSR = 0x200, // pin is CE/LSR for global purposes

PINGLB_MASK = 0x100,
PINGLB_MASK = 0x300,

PINBIT_GATED = 0x1000, // pin must be enabled in bitstream if used
PINBIT_1 = 0x2000, // pin has an explicit bit that must be set if tied to 1
Expand All @@ -796,8 +797,8 @@ enum CellPinStyle
PINSTYLE_NONE = 0x0000, // default
PINSTYLE_CIB = 0x4012, // 'CIB' signal, floats high but explicitly zeroed if not used
PINSTYLE_CLK = 0x0107, // CLK type signal, invertible and defaults to disconnected
PINSTYLE_CE = 0x0027, // CE type signal, invertible and defaults to enabled
PINSTYLE_LSR = 0x0017, // LSR type signal, invertible and defaults to not reset
PINSTYLE_CE = 0x0227, // CE type signal, invertible and defaults to enabled
PINSTYLE_LSR = 0x0217, // LSR type signal, invertible and defaults to not reset
PINSTYLE_DEDI = 0x0000, // dedicated signals, leave alone
PINSTYLE_PU = 0x4022, // signals that float high and default high
PINSTYLE_PU_NONCIB = 0x0022, // signals that float high and default high
Expand Down
21 changes: 19 additions & 2 deletions nexus/pack.cc
Original file line number Diff line number Diff line change
Expand Up @@ -853,7 +853,9 @@ struct NexusPacker
void promote_globals()
{
std::vector<std::pair<int, IdString>> clk_fanout;
int available_globals = 16;
std::vector<std::pair<int, IdString>> ce_lsr_fanout;
// TODO: if we are more cunning about placement, the real limits are 16 per device half and 8 per row segment
int available_globals = 8;
for (auto net : sorted(ctx->nets)) {
NetInfo *ni = net.second;
// Skip undriven nets; and nets that are already global
Expand All @@ -864,26 +866,41 @@ struct NexusPacker
continue;
}
// Count the number of clock ports
int clk_count = 0;
int clk_count = 0, ce_lsr_count = 0;
for (const auto &usr : ni->users) {
auto port_style = ctx->get_cell_pin_style(usr.cell, usr.port);
if (port_style & PINGLB_CLK)
++clk_count;
if (port_style & PINGLB_CE_LSR)
++ce_lsr_count;
}
if (clk_count > 0)
clk_fanout.emplace_back(clk_count, ni->name);
if (ce_lsr_count > 150)
ce_lsr_fanout.emplace_back(ce_lsr_count, ni->name);
}
if (available_globals <= 0)
return;
// Sort clocks by max fanout
std::sort(clk_fanout.begin(), clk_fanout.end(), std::greater<std::pair<int, IdString>>());
std::sort(ce_lsr_fanout.begin(), ce_lsr_fanout.end(), std::greater<std::pair<int, IdString>>());

log_info("Promoting globals...\n");
// Promote the N highest fanout clocks
for (size_t i = 0; i < std::min<size_t>(clk_fanout.size(), available_globals); i++) {
NetInfo *net = ctx->nets.at(clk_fanout.at(i).second).get();
log_info(" promoting clock net '%s'\n", ctx->nameOf(net));
insert_buffer(net, id_DCC, "glb_clk", id_CLKI, id_CLKO, [](const PortRef &port) { return true; });
}
// Limit to 6 LSR/CE to avoid routeability issues
int available_ce_lsr_globals = std::min<int>(available_globals, 6);
for (size_t i = 0; i < std::min<size_t>(clk_fanout.size(), available_ce_lsr_globals); i++) {
NetInfo *net = ctx->nets.at(ce_lsr_fanout.at(i).second).get();
log_info(" promoting CE/LSR net '%s'\n", ctx->nameOf(net));
insert_buffer(net, id_DCC, "glb_ce_lsr", id_CLKI, id_CLKO, [this](const PortRef &port) {
return ctx->get_cell_pin_style(port.cell, port.port) & PINGLB_CE_LSR;
});
}
}

// Place certain global cells
Expand Down

0 comments on commit 31387db

Please sign in to comment.