aboutsummaryrefslogtreecommitdiffstats
path: root/ecp5/globals.cc
diff options
context:
space:
mode:
authorgatecat <gatecat@ds0.me>2022-02-26 15:17:46 +0000
committergatecat <gatecat@ds0.me>2022-02-27 13:47:05 +0000
commit86699b42f619960bfefd4d0b479dd44a90527ea4 (patch)
tree06997246ae104b75ce472215fcee3ba37ee5c50c /ecp5/globals.cc
parent434a9737bb459189b463c8768454ea6c0e151406 (diff)
downloadnextpnr-86699b42f619960bfefd4d0b479dd44a90527ea4.tar.gz
nextpnr-86699b42f619960bfefd4d0b479dd44a90527ea4.tar.bz2
nextpnr-86699b42f619960bfefd4d0b479dd44a90527ea4.zip
Switch to potentially-sparse net users array
This uses a new data structure for net.users that allows gaps, so removing a port from a net is no longer an O(n) operation on the number of users the net has. Signed-off-by: gatecat <gatecat@ds0.me>
Diffstat (limited to 'ecp5/globals.cc')
-rw-r--r--ecp5/globals.cc22
1 files changed, 12 insertions, 10 deletions
diff --git a/ecp5/globals.cc b/ecp5/globals.cc
index 7b48e693..71188aa0 100644
--- a/ecp5/globals.cc
+++ b/ecp5/globals.cc
@@ -472,17 +472,15 @@ class Ecp5GlobalRouter
} else if (is_logic_port(user)) {
keep_users.push_back(user);
} else {
- glbptr->users.push_back(user);
user.cell->ports.at(user.port).net = glbptr;
+ user.cell->ports.at(user.port).user_idx = glbptr->users.add(user);
}
}
- net->users = keep_users;
+ net->users.clear();
+ for (auto &usr : keep_users)
+ usr.cell->ports.at(usr.port).user_idx = net->users.add(usr);
- dcc->ports[id_CLKI].net = net;
- PortRef clki_pr;
- clki_pr.port = id_CLKI;
- clki_pr.cell = dcc.get();
- net->users.push_back(clki_pr);
+ dcc->connectPort(id_CLKI, net);
if (net->clkconstr) {
glbptr->clkconstr = std::unique_ptr<ClockConstraint>(new ClockConstraint());
glbptr->clkconstr->low = net->clkconstr->low;
@@ -556,9 +554,13 @@ class Ecp5GlobalRouter
if (ci->type == id_DCCA || ci->type == id_DCSC) {
NetInfo *clock = ci->ports.at((ci->type == id_DCSC) ? id_DCSOUT : id_CLKO).net;
NPNR_ASSERT(clock != nullptr);
- bool drives_fabric = std::any_of(clock->users.begin(), clock->users.end(),
- [this](const PortRef &port) { return !is_clock_port(port); });
-
+ bool drives_fabric = false;
+ for (auto &usr : clock->users) {
+ if (!is_clock_port(usr)) {
+ drives_fabric = true;
+ break;
+ }
+ }
int glbid;
if (drives_fabric) {
if (fab_globals.empty())