From 002c4c41d206a505d24fa65a84ff12cd32b433cc Mon Sep 17 00:00:00 2001 From: James Cherry Date: Fri, 21 Nov 2025 07:46:05 -0700 Subject: [PATCH 1/6] power cell seq has precedence over test_cell resolves #331 Signed-off-by: James Cherry --- power/Power.cc | 37 +++++++++++++++++++++++++++---------- power/Power.hh | 4 ++++ 2 files changed, 31 insertions(+), 10 deletions(-) diff --git a/power/Power.cc b/power/Power.cc index 48692dea..f50fb67d 100644 --- a/power/Power.cc +++ b/power/Power.cc @@ -489,13 +489,16 @@ PropActivityVisitor::visit(Vertex *vertex) } if (network_->isDriver(pin)) { LibertyPort *port = network_->libertyPort(pin); - if (port) { - LibertyCell *test_cell = port->libertyCell()->testCell(); - if (test_cell) - port = test_cell->findLibertyPort(port->name()); - } if (port) { FuncExpr *func = port->function(); + if (func == nullptr) { + LibertyCell *test_cell = port->libertyCell()->testCell(); + if (test_cell) { + port = test_cell->findLibertyPort(port->name()); + if (port) + func = port->function(); + } + } if (func) { PwrActivity activity = power_->evalActivity(func, inst); changed = setActivityCheck(pin, activity); @@ -777,10 +780,24 @@ Power::seedRegOutputActivities(const Instance *inst, BfsFwdIterator &bfs) { LibertyCell *cell = network_->libertyCell(inst); - LibertyCell *test_cell = cell->testCell(); - const SequentialSeq &seqs = test_cell - ? test_cell->sequentials() - : cell->sequentials(); + const SequentialSeq &seqs = cell->sequentials(); + if (!seqs.empty()) + seedRegOutputActivities(inst, nullptr, seqs, bfs); + else { + LibertyCell *test_cell = cell->testCell(); + if (test_cell) { + const SequentialSeq &seqs = test_cell->sequentials(); + seedRegOutputActivities(inst, test_cell, seqs, bfs); + } + } +} + +void +Power::seedRegOutputActivities(const Instance *inst, + const LibertyCell *test_cell, + const SequentialSeq &seqs, + BfsFwdIterator &bfs) +{ for (Sequential *seq : seqs) { seedRegOutputActivities(inst, seq, seq->output(), false); seedRegOutputActivities(inst, seq, seq->outputInv(), true); @@ -791,7 +808,7 @@ Power::seedRegOutputActivities(const Instance *inst, Pin *pin = pin_iter->next(); LibertyPort *port = network_->libertyPort(pin); if (test_cell) - port = test_cell->findLibertyPort(port->name()); + port = test_cell->findLibertyPort(port->name()); if (port) { FuncExpr *func = port->function(); Vertex *vertex = graph_->pinDrvrVertex(pin); diff --git a/power/Power.hh b/power/Power.hh index 55f8a252..5c45fd60 100644 --- a/power/Power.hh +++ b/power/Power.hh @@ -191,6 +191,10 @@ protected: bool invert); void seedRegOutputActivities(const Instance *inst, BfsFwdIterator &bfs); + void seedRegOutputActivities(const Instance *inst, + const LibertyCell *test_cell, + const SequentialSeq &seqs, + BfsFwdIterator &bfs); PwrActivity evalActivity(FuncExpr *expr, const Instance *inst); PwrActivity evalActivity(FuncExpr *expr, From 5a26929be5b71e8df975b65638e3385d1c5af98a Mon Sep 17 00:00:00 2001 From: James Cherry Date: Fri, 21 Nov 2025 07:48:44 -0700 Subject: [PATCH 2/6] clang format from PR #317 Signed-off-by: James Cherry --- .clang-format | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/.clang-format b/.clang-format index cd7dc197..d50ce987 100644 --- a/.clang-format +++ b/.clang-format @@ -12,18 +12,20 @@ AllowShortLoopsOnASingleLine: false AlwaysBreakAfterReturnType: TopLevel BinPackArguments: false # fails -BinPackParameters: false +BinPackParameters: AlwaysOnePerLine BraceWrapping: AfterClass: true AfterStruct: true AfterFunction: true BeforeElse: true +BreakBeforeBinaryOperators: NonAssignment BreakBeforeBraces: Custom # fails if all initializers fit on one line BreakConstructorInitializers: AfterColon -ColumnLimit: 0 +ColumnLimit: 90 # fails -ConstructorInitializerAllOnOneLineOrOnePerLine: false ConstructorInitializerIndentWidth: 2 IncludeBlocks: Preserve +PackConstructorInitializers: Never PointerAlignment: Right +SortIncludes: Never From cabc1424e02e322ec3fcfcb24b3b0694924cf549 Mon Sep 17 00:00:00 2001 From: James Cherry Date: Fri, 21 Nov 2025 07:56:39 -0700 Subject: [PATCH 3/6] tclArgError Signed-off-by: James Cherry --- tcl/TclTypeHelpers.cc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tcl/TclTypeHelpers.cc b/tcl/TclTypeHelpers.cc index e3cabbb6..f5d73442 100644 --- a/tcl/TclTypeHelpers.cc +++ b/tcl/TclTypeHelpers.cc @@ -101,7 +101,7 @@ tclArgError(Tcl_Interp *interp, try { Sta::sta()->report()->error(id, msg, arg); } catch (const std::exception &e) { - Tcl_SetResult(interp, const_cast(e.what()), TCL_STATIC); + Tcl_SetResult(interp, const_cast(e.what()), TCL_VOLATILE); } } From 574379eb32df438b1467078e325994dc93aaa5e8 Mon Sep 17 00:00:00 2001 From: Matt Liberty Date: Fri, 21 Nov 2025 07:01:39 -0800 Subject: [PATCH 4/6] rm stray semicolon (#338) Signed-off-by: Matt Liberty --- liberty/LibertyReader.cc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/liberty/LibertyReader.cc b/liberty/LibertyReader.cc index 3fc2ffdf..bb24b5fe 100644 --- a/liberty/LibertyReader.cc +++ b/liberty/LibertyReader.cc @@ -5690,7 +5690,7 @@ LibertyReader::visitPgType(LibertyAttr *attr) PwrGndType type = findPwrGndType(type_name); PortDirection *dir = PortDirection::unknown(); switch (type) { - case PwrGndType::primary_ground:; + case PwrGndType::primary_ground: case PwrGndType::backup_ground: case PwrGndType::internal_ground: dir = PortDirection::ground(); From 4475f89024070dec335e4405ff9db63054c389c0 Mon Sep 17 00:00:00 2001 From: Matt Liberty Date: Fri, 21 Nov 2025 07:02:35 -0800 Subject: [PATCH 5/6] Fix C++20 warning (#337) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit warning: implicit capture of ‘this’ via ‘[=]’ is deprecated in C++20 [-Wdeprecated] Signed-off-by: Matt Liberty --- search/Sta.cc | 4 ++-- spice/WriteSpice.cc | 12 ++++++------ verilog/VerilogReader.cc | 4 ++-- 3 files changed, 10 insertions(+), 10 deletions(-) diff --git a/search/Sta.cc b/search/Sta.cc index 3957f3d5..99675388 100644 --- a/search/Sta.cc +++ b/search/Sta.cc @@ -5241,8 +5241,8 @@ Sta::slowDrivers(int count) { findDelays(); InstanceSeq insts = network_->leafInstances(); - sort(insts, [=] (const Instance *inst1, - const Instance *inst2) { + sort(insts, [this] (const Instance *inst1, + const Instance *inst2) { return delayGreater(instMaxSlew(inst1, this), instMaxSlew(inst2, this), this); diff --git a/spice/WriteSpice.cc b/spice/WriteSpice.cc index 2d4296e7..a0623c53 100644 --- a/spice/WriteSpice.cc +++ b/spice/WriteSpice.cc @@ -533,8 +533,8 @@ WriteSpice::writeParasiticNetwork(const Pin *drvr_pin, // Sort resistors for consistent regression results. ParasiticResistorSeq resistors = parasitics_->resistors(parasitic); sort(resistors.begin(), resistors.end(), - [=] (const ParasiticResistor *r1, - const ParasiticResistor *r2) { + [this] (const ParasiticResistor *r1, + const ParasiticResistor *r2) { return parasitics_->id(r1) < parasitics_->id(r2); }); for (ParasiticResistor *resistor : resistors) { @@ -577,8 +577,8 @@ WriteSpice::writeParasiticNetwork(const Pin *drvr_pin, // Sort nodes for consistent regression results. ParasiticNodeSeq nodes = parasitics_->nodes(parasitic); sort(nodes.begin(), nodes.end(), - [=] (const ParasiticNode *node1, - const ParasiticNode *node2) { + [this] (const ParasiticNode *node1, + const ParasiticNode *node2) { const char *name1 = parasitics_->name(node1); const char *name2 = parasitics_->name(node2); return stringLess(name1, name2); @@ -598,8 +598,8 @@ WriteSpice::writeParasiticNetwork(const Pin *drvr_pin, // Sort coupling capacitors for consistent regression results. ParasiticCapacitorSeq capacitors = parasitics_->capacitors(parasitic); sort(capacitors.begin(), capacitors.end(), - [=] (const ParasiticCapacitor *c1, - const ParasiticCapacitor *c2) { + [this] (const ParasiticCapacitor *c1, + const ParasiticCapacitor *c2) { return parasitics_->id(c1) < parasitics_->id(c2); }); const Net *net = pinNet(drvr_pin, network_); diff --git a/verilog/VerilogReader.cc b/verilog/VerilogReader.cc index 166021e6..26ed54d8 100644 --- a/verilog/VerilogReader.cc +++ b/verilog/VerilogReader.cc @@ -146,8 +146,8 @@ VerilogReader::VerilogReader(NetworkReader *network) : zero_net_name_("zero_"), one_net_name_("one_") { - network->setLinkFunc([=] (const char *top_cell_name, - bool make_black_boxes) -> Instance* { + network->setLinkFunc([this] (const char *top_cell_name, + bool make_black_boxes) -> Instance* { return linkNetwork(top_cell_name, make_black_boxes, true); }); constant10_max_ = stdstrPrint("%llu", std::numeric_limits::max()); From f79f442f1d63d24b7929bac77fccd31a9b5c2c5c Mon Sep 17 00:00:00 2001 From: James Cherry Date: Mon, 24 Nov 2025 14:15:53 -0700 Subject: [PATCH 6/6] path enum latch resolves orfs #1229 --- search/PathEnum.cc | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/search/PathEnum.cc b/search/PathEnum.cc index e3d6ac85..9650aff0 100644 --- a/search/PathEnum.cc +++ b/search/PathEnum.cc @@ -636,7 +636,8 @@ PathEnum::makeDivertedPath(Path *path, after_div_copy = copy; if (first) div_path = copy; - else if (network_->isLatchData(p->pin(this))) + else if (found_div + && network_->isLatchData(p->pin(this))) break; if (p == before_div) { // Replaced on next pass.