rm tmp string uses

commit 2d0a4f8e9a8b46faa2ba91e1be636c3c3ad95a7f
Author: James Cherry <cherry@parallaxsw.com>
Date:   Sat Mar 25 21:25:37 2023 -0700

    leaks

    Signed-off-by: James Cherry <cherry@parallaxsw.com>

commit 5514910a91707d615bac0bbed3a29f579eca8de2
Author: James Cherry <cherry@parallaxsw.com>
Date:   Sat Mar 25 18:21:54 2023 -0700

    foo

    Signed-off-by: James Cherry <cherry@parallaxsw.com>

commit 076a51d5816444e883232933c2ded7309291d0bc
Author: James Cherry <cherry@parallaxsw.com>
Date:   Sat Mar 25 16:38:42 2023 -0700

    parse bus string

    Signed-off-by: James Cherry <cherry@parallaxsw.com>

commit 2b80e563cbbb6563a6b716431f391bbb6639f816
Author: James Cherry <cherry@parallaxsw.com>
Date:   Sat Mar 25 15:57:05 2023 -0700

    rm tmp string

    Signed-off-by: James Cherry <cherry@parallaxsw.com>

commit 9e4f2308658232d0b1ee9efcd948bb19ae5dd30f
Author: James Cherry <cherry@parallaxsw.com>
Date:   Sat Mar 25 14:37:35 2023 -0700

    rm tmp string

    Signed-off-by: James Cherry <cherry@parallaxsw.com>

commit ebad3afd49b08e7194452dd082c3c7c05767f875
Author: James Cherry <cherry@parallaxsw.com>
Date:   Sat Mar 25 10:59:11 2023 -0700

    rm tmp string

    Signed-off-by: James Cherry <cherry@parallaxsw.com>

commit 69647913932312a04ca06e7a04cca17ed50d4daf
Author: James Cherry <cherry@parallaxsw.com>
Date:   Fri Mar 24 21:02:20 2023 -0700

    rm tmp string

    Signed-off-by: James Cherry <cherry@parallaxsw.com>

commit 55e67996a7b0651dbb5ee06cb89fe0410648c3c1
Author: James Cherry <cherry@parallaxsw.com>
Date:   Sat Mar 25 10:42:43 2023 -0700

    rm tmp string

    Signed-off-by: James Cherry <cherry@parallaxsw.com>

commit 73cee43925c0d32940989c616440b4da18640121
Author: James Cherry <cherry@parallaxsw.com>
Date:   Sat Mar 25 09:55:17 2023 -0700

    rm tmp string

    Signed-off-by: James Cherry <cherry@parallaxsw.com>

commit eba6d1413b8d87a64a90141e5263a56eede1df51
Author: James Cherry <cherry@parallaxsw.com>
Date:   Sat Mar 25 09:40:16 2023 -0700

    rm tmp string

    Signed-off-by: James Cherry <cherry@parallaxsw.com>

commit 95d6ed78144512a37fd7c1d3d8a62fc4c8965818
Author: James Cherry <cherry@parallaxsw.com>
Date:   Sat Mar 25 08:18:46 2023 -0700

    rm tmp string

    Signed-off-by: James Cherry <cherry@parallaxsw.com>

commit faf82464d7be7fd6c958a21d401fa48ece4ac341
Author: James Cherry <cherry@parallaxsw.com>
Date:   Sat Mar 25 07:49:11 2023 -0700

    rm tmp string

    Signed-off-by: James Cherry <cherry@parallaxsw.com>

commit cfc9064496cb6f46ec562b104bc7fff2fbc1b32e
Author: James Cherry <cherry@parallaxsw.com>
Date:   Sat Mar 25 07:37:12 2023 -0700

    rm tmp string

    Signed-off-by: James Cherry <cherry@parallaxsw.com>

commit 057933a6ac356a7541883aa64b5109c7a0e8b8d1
Author: James Cherry <cherry@parallaxsw.com>
Date:   Fri Mar 24 21:02:20 2023 -0700

    rm tmp string

    Signed-off-by: James Cherry <cherry@parallaxsw.com>

commit fdeb6436a72413356a627dd1de1d8cec7fca4c4a
Author: James Cherry <cherry@parallaxsw.com>
Date:   Fri Mar 24 19:53:44 2023 -0700

    rm TmpString uses

    Signed-off-by: James Cherry <cherry@parallaxsw.com>

Signed-off-by: James Cherry <cherry@parallaxsw.com>
This commit is contained in:
James Cherry 2023-03-26 06:34:36 -07:00
parent 2b8fd17ca7
commit 94a93bd4ae
24 changed files with 621 additions and 588 deletions

View File

@ -1106,7 +1106,7 @@ private:
LibertyCell *cell_;
};
const char *
string
portLibertyToSta(const char *port_name);
} // namespace

View File

@ -16,8 +16,12 @@
#pragma once
#include <string>
namespace sta {
using std::string;
// Return true if name is a bus.
bool
isBusName(const char *name,
@ -38,7 +42,8 @@ parseBusName(const char *name,
const char brkt_right,
char escape,
// Return values.
char *&bus_name,
bool &is_bus,
string &bus_name,
int &index);
// Allow multiple different left/right bus brackets.
void
@ -47,7 +52,8 @@ parseBusName(const char *name,
const char *brkts_right,
char escape,
// Return values.
char *&bus_name,
bool &is_bus,
string &bus_name,
int &index);
// Parse a bus range, such as BUS[4:0].
@ -59,7 +65,8 @@ parseBusRange(const char *name,
const char brkt_right,
char escape,
// Return values.
char *&bus_name,
bool &is_bus,
string &bus_name,
int &from,
int &to);
// brkt_lefts and brkt_rights are corresponding strings of legal
@ -70,12 +77,13 @@ parseBusRange(const char *name,
const char *brkts_right,
const char escape,
// Return values.
char *&bus_name,
bool &is_bus,
string &bus_name,
int &from,
int &to);
// Insert escapes before ch1 and ch2 in token.
const char *
string
escapeChars(const char *token,
const char ch1,
const char ch2,

View File

@ -44,7 +44,10 @@ public:
PatternMatch(const char *pattern);
PatternMatch(const char *pattern,
const PatternMatch *inherit_from);
PatternMatch(string pattern,
const PatternMatch *inherit_from);
bool match(const char *str) const;
bool match(const string &str) const;
bool matchNoCase(const char *str) const;
const char *pattern() const { return pattern_; }
bool isRegexp() const { return is_regexp_; }

View File

@ -16,25 +16,29 @@
#pragma once
#include <string>
namespace sta {
const char *
using std::string;
string
instanceVerilogName(const char *sta_name,
const char escape);
const char *
string
netVerilogName(const char *sta_name,
const char escape);
const char *
string
portVerilogName(const char *sta_name,
const char escape);
const char *
string
moduleVerilogToSta(const char *sta_name);
const char *
string
instanceVerilogToSta(const char *sta_name);
const char *
string
netVerilogToSta(const char *sta_name);
const char *
string
portVerilogToSta(const char *sta_name);
} // namespace

View File

@ -2520,23 +2520,20 @@ LibertyPort::setReceiverModel(ReceiverModelPtr receiver_model)
receiver_model_ = receiver_model;
}
const char *
string
portLibertyToSta(const char *port_name)
{
constexpr char bus_brkt_left = '[';
constexpr char bus_brkt_right = ']';
size_t name_length = strlen(port_name);
char *sta_name = makeTmpString(name_length * 2);
//char *sta_name = new char[name_length * 2];//makeTmpString(name_length * 2);
char *p = sta_name;
string sta_name;
for (size_t i = 0; i < name_length; i++) {
char ch = port_name[i];
if (ch == bus_brkt_left
|| ch == bus_brkt_right)
*p++ = '\\';
*p++ = ch;
sta_name += '\\';
sta_name += ch;
}
*p++ = '\0';
return sta_name;
}

View File

@ -41,8 +41,8 @@ LibertyPort *
LibertyBuilder::makePort(LibertyCell *cell,
const char *port_name)
{
const char *sta_name = portLibertyToSta(port_name);
LibertyPort *port = new LibertyPort(cell, sta_name, false, nullptr,
string sta_name = portLibertyToSta(port_name);
LibertyPort *port = new LibertyPort(cell, sta_name.c_str(), false, nullptr,
-1, -1, false, nullptr);
cell->addPort(port);
return port;
@ -89,12 +89,13 @@ LibertyBuilder::makeBusPortBit(ConcreteLibrary *library,
const char *bus_name,
int bit_index)
{
char *bit_name = stringPrintTmp("%s%c%d%c",
bus_name,
library->busBrktLeft(),
bit_index,
library->busBrktRight());
LibertyPort *port = makePort(cell, bit_name, bit_index);
string bit_name;
stringPrint(bit_name, "%s%c%d%c",
bus_name,
library->busBrktLeft(),
bit_index,
library->busBrktRight());
LibertyPort *port = makePort(cell, bit_name.c_str(), bit_index);
bus_port->addPortBit(port);
cell->addPortBit(port);
}

View File

@ -523,38 +523,42 @@ LibertyReader::defineScalingFactorVisitors()
if (scaleFactorTypeRiseFallSuffix(type)) {
for (auto tr : RiseFall::range()) {
const char *tr_name = (tr == RiseFall::rise()) ? "rise":"fall";
const char *attr_name = stringPrintTmp("k_%s_%s_%s",
pvt_name,
type_name,
tr_name);
defineAttrVisitor(attr_name,&LibertyReader::visitScaleFactorSuffix);
string attr_name;
stringPrint(attr_name, "k_%s_%s_%s",
pvt_name,
type_name,
tr_name);
defineAttrVisitor(attr_name.c_str() ,&LibertyReader::visitScaleFactorSuffix);
}
}
else if (scaleFactorTypeRiseFallPrefix(type)) {
for (auto tr : RiseFall::range()) {
const char *tr_name = (tr == RiseFall::rise()) ? "rise":"fall";
const char *attr_name = stringPrintTmp("k_%s_%s_%s",
pvt_name,
tr_name,
type_name);
defineAttrVisitor(attr_name,&LibertyReader::visitScaleFactorPrefix);
string attr_name;
stringPrint(attr_name, "k_%s_%s_%s",
pvt_name,
tr_name,
type_name);
defineAttrVisitor(attr_name.c_str(),&LibertyReader::visitScaleFactorPrefix);
}
}
else if (scaleFactorTypeLowHighSuffix(type)) {
for (auto tr : RiseFall::range()) {
const char *tr_name = (tr == RiseFall::rise()) ? "high":"low";
const char *attr_name = stringPrintTmp("k_%s_%s_%s",
pvt_name,
tr_name,
type_name);
defineAttrVisitor(attr_name,&LibertyReader::visitScaleFactorHiLow);
string attr_name;
stringPrint(attr_name, "k_%s_%s_%s",
pvt_name,
tr_name,
type_name);
defineAttrVisitor(attr_name.c_str(),&LibertyReader::visitScaleFactorHiLow);
}
}
else {
const char *attr_name = stringPrintTmp("k_%s_%s",
pvt_name,
type_name);
defineAttrVisitor(attr_name,&LibertyReader::visitScaleFactor);
string attr_name;
stringPrint(attr_name, "k_%s_%s",
pvt_name,
type_name);
defineAttrVisitor(attr_name.c_str(),&LibertyReader::visitScaleFactor);
}
}
}
@ -770,39 +774,32 @@ LibertyReader::parseUnits(LibertyAttr *attr,
float &scale_var,
Unit *unit)
{
const char *unit_str = getAttrString(attr);
if (unit_str) {
unsigned unit_str_length = strlen(unit_str);
string units = getAttrString(attr);
if (!units.empty()) {
// Unit format is <multipler_digits><scale_suffix_char><unit_suffix>.
// Find the multiplier digits.
char *mult_str = makeTmpString(unit_str_length);
const char *s = unit_str;
char *m = mult_str;
for (; *s; s++) {
char ch = *s;
if (isdigit(ch))
*m++ = ch;
else
break;
}
*m = '\0';
string units = getAttrString(attr);
size_t mult_end = units.find_first_not_of("01234567890");
float mult = 1.0F;
if (*mult_str != '\0') {
if (stringEq(mult_str, "1"))
string scale_suffix;
if (mult_end != units.npos) {
string unit_mult = units.substr(0, mult_end);
scale_suffix = units.substr(mult_end);
if (unit_mult == "1")
mult = 1.0F;
else if (stringEq(mult_str, "10"))
else if (unit_mult == "10")
mult = 10.0F;
else if (stringEq(mult_str, "100"))
else if (unit_mult == "100")
mult = 100.0F;
else
libWarn(38, attr, "unknown unit multiplier %s.", mult_str);
libWarn(38, attr, "unknown unit multiplier %s.", unit_mult.c_str());
}
else
scale_suffix = units;
float scale_mult = 1.0F;
if (*s && stringEqual(s + 1, unit_suffix)) {
char scale_char = tolower(*s);
if (scale_suffix.size() >= 2 && scale_suffix.substr(1) == unit_suffix) {
char scale_char = tolower(scale_suffix[0]);
if (scale_char == 'k')
scale_mult = 1E+3F;
else if (scale_char == 'm')
@ -818,8 +815,8 @@ LibertyReader::parseUnits(LibertyAttr *attr,
else
libWarn(39, attr, "unknown unit scale %c.", scale_char);
}
else if (!stringEqual(s, unit_suffix))
libWarn(40, attr, "unknown unit suffix %s.", s + 1);
else if (!stringEqual(scale_suffix.c_str(), unit_suffix))
libWarn(40, attr, "unknown unit suffix %s.", scale_suffix.c_str());
scale_var = scale_mult * mult;
unit->setScale(scale_var);
@ -3192,8 +3189,8 @@ libertyReaderFindPort(LibertyCell *cell,
char brkt_right = library->busBrktRight();
const char escape = '\\';
// Pins at top level with bus names have escaped brackets.
port_name = escapeChars(port_name, brkt_left, brkt_right, escape);
port = cell->findLibertyPort(port_name);
string escaped_port_name = escapeChars(port_name, brkt_left, brkt_right, escape);
port = cell->findLibertyPort(escaped_port_name.c_str());
}
return port;
}
@ -4771,11 +4768,12 @@ LibertyReader::parseFunc(const char *func,
const char *attr_name,
int line)
{
const char *error_msg = stringPrintTmp("%s, line %d %s",
filename_,
line,
attr_name);
return parseFuncExpr(func, cell_, error_msg, report_);
string error_msg;
stringPrint(error_msg, "%s, line %d %s",
filename_,
line,
attr_name);
return parseFuncExpr(func, cell_, error_msg.c_str(), report_);
}
EarlyLateAll *
@ -5628,7 +5626,6 @@ PortNameBitIterator::PortNameBitIterator(LibertyCell *cell,
port_(nullptr),
bit_iterator_(nullptr),
range_bus_port_(nullptr),
range_bus_name_(nullptr),
range_name_next_(nullptr),
size_(0)
{
@ -5649,11 +5646,13 @@ PortNameBitIterator::init(const char *port_name)
else {
// Check for bus range.
LibertyLibrary *library = visitor_->library();
bool is_bus;
string bus_name;
int from, to;
char *bus_name;
parseBusRange(port_name, library->busBrktLeft(), library->busBrktRight(),
'\\', bus_name, from, to);
if (bus_name) {
parseBusRange(port_name, library->busBrktLeft(),
library->busBrktRight(), '\\',
is_bus, bus_name, from, to);
if (is_bus) {
port = visitor_->findPort(port_name);
if (port) {
if (port->isBus()) {
@ -5663,7 +5662,6 @@ PortNameBitIterator::init(const char *port_name)
range_from_ = from;
range_to_ = to;
range_bit_ = from;
delete [] bus_name;
}
else
visitor_->libWarn(156, line_, "port %s subscript out of range.",
@ -5672,7 +5670,7 @@ PortNameBitIterator::init(const char *port_name)
else
visitor_->libWarn(157, line_, "port range %s of non-bus port %s.",
port_name,
bus_name);
bus_name.c_str());
}
else {
range_bus_name_ = bus_name;
@ -5690,7 +5688,6 @@ PortNameBitIterator::init(const char *port_name)
PortNameBitIterator::~PortNameBitIterator()
{
stringDelete(range_bus_name_);
delete bit_iterator_;
}
@ -5703,7 +5700,7 @@ PortNameBitIterator::hasNext()
&& ((range_from_ > range_to_)
? range_bit_ >= range_to_
: range_bit_ <= range_from_))
|| (range_bus_name_
|| (!range_bus_name_.empty()
&& range_name_next_);
}
@ -5725,7 +5722,7 @@ PortNameBitIterator::next()
range_bit_++;
return next;
}
else if (range_bus_name_) {
else if (!range_bus_name_.empty()) {
LibertyPort *next = range_name_next_;
findRangeBusNameNext();
return next;
@ -5741,12 +5738,13 @@ PortNameBitIterator::findRangeBusNameNext()
? range_bit_ >= range_to_
: range_bit_ <= range_to_) {
LibertyLibrary *library = visitor_->library();
const char *bus_bit_name = stringPrintTmp("%s%c%d%c",
range_bus_name_,
library->busBrktLeft(),
range_bit_,
library->busBrktRight());
range_name_next_ = visitor_->findPort(bus_bit_name);
string bus_bit_name;
stringPrint(bus_bit_name, "%s%c%d%c",
range_bus_name_.c_str(),
library->busBrktLeft(),
range_bit_,
library->busBrktRight());
range_name_next_ = visitor_->findPort(bus_bit_name.c_str());
if (range_name_next_) {
if (range_from_ > range_to_)
range_bit_--;
@ -5754,7 +5752,7 @@ PortNameBitIterator::findRangeBusNameNext()
range_bit_++;
}
else
visitor_->libWarn(159, line_, "port %s not found.", bus_bit_name);
visitor_->libWarn(159, line_, "port %s not found.", bus_bit_name.c_str());
}
else
range_name_next_ = nullptr;

View File

@ -861,7 +861,7 @@ protected:
LibertyPort *port_;
LibertyPortMemberIterator *bit_iterator_;
LibertyPort *range_bus_port_;
const char *range_bus_name_;
string range_bus_name_;
LibertyPort *range_name_next_;
int range_from_;
int range_to_;

View File

@ -25,6 +25,8 @@
namespace sta {
using std::map;
static constexpr char escape_ = '\\';
ConcreteLibrary::ConcreteLibrary(const char *name,
@ -381,7 +383,7 @@ ConcreteCell::groupBusPorts(const char bus_brkt_left,
{
const char bus_brkts_left[2]{bus_brkt_left, '\0'};
const char bus_brkts_right[2]{bus_brkt_right, '\0'};
BusPortMap port_map;
map<string, BusPort*> port_map;
// Find ungrouped bus ports.
// Remove bus bit ports from the ports_ vector during the scan by
// keeping an index to the next insertion index and skipping over
@ -390,19 +392,21 @@ ConcreteCell::groupBusPorts(const char bus_brkt_left,
ports_.clear();
for (ConcretePort *port : ports) {
const char *port_name = port->name();
char *bus_name;
bool is_bus;
string bus_name;
int index;
parseBusName(port_name, bus_brkts_left, bus_brkts_right, escape_,
bus_name, index);
if (bus_name) {
is_bus, bus_name, index);
if (is_bus) {
if (!port->isBusBit()) {
BusPort *bus_port = port_map.findKey(bus_name);
if (bus_port)
stringDelete(bus_name);
else {
bus_port = new BusPort(bus_name, index, port->direction());
auto name_bus_port = port_map.find(bus_name);
BusPort *bus_port;
if (name_bus_port == port_map.end()) {
bus_port = new BusPort(bus_name.c_str(), index, port->direction());
port_map[bus_name] = bus_port;
}
else
bus_port = name_bus_port->second;
bus_port->pushMember(port);
}
else
@ -413,47 +417,45 @@ ConcreteCell::groupBusPorts(const char bus_brkt_left,
}
// Make the bus ports.
BusPortMap::Iterator bus_iter(port_map);
while (bus_iter.hasNext()) {
BusPort *bus_port = bus_iter.next();
const char *bus_name = bus_port->name();
bool msb_first = port_msb_first(bus_name);
for (auto name_bus : port_map) {
const string &bus_name = name_bus.first;
BusPort *bus_port = name_bus.second;
bool msb_first = port_msb_first(bus_name.c_str());
ConcretePortSeq *members = bus_port->members();
sort(members, [&](ConcretePort *port1,
ConcretePort *port2) {
char *bus_name;
int index1, index2;
parseBusName(port1->name(), bus_brkts_left, bus_brkts_right, escape_,
bus_name, index1);
stringDelete(bus_name);
parseBusName(port2->name(), bus_brkts_left, bus_brkts_right, escape_,
bus_name, index2);
stringDelete(bus_name);
return msb_first ? index1 > index2 : index1 < index2;
});
bool is_bus;
string bus_name;
int index1, index2;
parseBusName(port1->name(), bus_brkts_left, bus_brkts_right, escape_,
is_bus, bus_name, index1);
parseBusName(port2->name(), bus_brkts_left, bus_brkts_right, escape_,
is_bus, bus_name, index2);
return msb_first ? index1 > index2 : index1 < index2;
});
char *bus_name1;
bool is_bus1;
string bus_name1;
int from_index, to_index;
parseBusName((*members)[0]->name(),
bus_brkts_left, bus_brkts_right, escape_,
bus_name1, from_index);
stringDelete(bus_name1);
is_bus1, bus_name1, from_index);
parseBusName((*members)[members->size() - 1]->name(),
bus_brkts_left, bus_brkts_right, escape_,
bus_name1, to_index);
stringDelete(bus_name1);
is_bus1, bus_name1, to_index);
ConcretePort *port = makeBusPort(bus_name, from_index, to_index, members);
ConcretePort *port = makeBusPort(bus_name.c_str(), from_index,
to_index, members);
port->setDirection(bus_port->direction());
delete bus_port;
for (ConcretePort *port : *members) {
char *bus_name;
bool is_bus;
string bus_name;
int index;
parseBusName(port->name(), bus_brkts_left, bus_brkts_right, escape_,
bus_name, index);
is_bus, bus_name, index);
port->setBusBitIndex(index);
stringDelete(bus_name);
}
}
}

View File

@ -51,12 +51,14 @@ parseBusName(const char *name,
const char brkt_right,
const char escape,
// Return values.
char *&bus_name,
bool &is_bus,
string &bus_name,
int &index)
{
const char brkts_left[2] = {brkt_left, '\0'};
const char brkts_right[2] = {brkt_right, '\0'};
parseBusName(name, brkts_left, brkts_right, escape, bus_name, index);
parseBusName(name, brkts_left, brkts_right, escape,
is_bus, bus_name, index);
}
void
@ -65,10 +67,11 @@ parseBusName(const char *name,
const char *brkts_right,
char escape,
// Return values.
char *&bus_name,
bool &is_bus,
string &bus_name,
int &index)
{
bus_name = nullptr;
is_bus = false;
size_t len = strlen(name);
// Shortest bus name is a[0].
if (len >= 4
@ -81,10 +84,9 @@ parseBusName(const char *name,
char brkt_left = brkts_left[brkt_index];
const char *left = strrchr(name, brkt_left);
if (left) {
is_bus = true;
size_t bus_name_len = left - name;
bus_name = new char[bus_name_len + 1];
strncpy(bus_name, name, bus_name_len);
bus_name[bus_name_len] = '\0';
bus_name.append(name, bus_name_len);
// Simple bus subscript.
index = atoi(left + 1);
}
@ -98,13 +100,15 @@ parseBusRange(const char *name,
const char brkt_right,
char escape,
// Return values.
char *&bus_name,
bool &is_bus,
string &bus_name,
int &from,
int &to)
{
const char brkts_left[2] = {brkt_left, '\0'};
const char brkts_right[2] = {brkt_right, '\0'};
parseBusRange(name, brkts_left, brkts_right, escape, bus_name, from, to);
parseBusRange(name, brkts_left, brkts_right, escape,
is_bus, bus_name, from, to);
}
void
@ -113,11 +117,12 @@ parseBusRange(const char *name,
const char *brkts_right,
char escape,
// Return values.
char *&bus_name,
bool &is_bus,
string &bus_name,
int &from,
int &to)
{
bus_name = nullptr;
is_bus = false;
size_t len = strlen(name);
// Shortest bus range is a[1:0].
if (len >= 6
@ -134,10 +139,8 @@ parseBusRange(const char *name,
const char range_sep = ':';
const char *range = strchr(name, range_sep);
if (range) {
size_t bus_name_len = left - name;
bus_name = new char[bus_name_len + 1];
strncpy(bus_name, name, bus_name_len);
bus_name[bus_name_len] = '\0';
is_bus = true;
bus_name.append(name, left - name);
// No need to terminate bus subscript because atoi stops
// scanning at first non-digit character.
from = atoi(left + 1);
@ -148,54 +151,32 @@ parseBusRange(const char *name,
}
}
const char *
string
escapeChars(const char *token,
const char ch1,
const char ch2,
const char escape)
{
int result_length = 0;
bool need_escapes = false;
string escaped;
for (const char *s = token; *s; s++) {
char ch = *s;
if (ch == escape) {
char next_ch = s[1];
// Make sure we don't skip the null if escape is the last char.
if (next_ch != '\0')
result_length++;
if (next_ch != '\0') {
escaped += ch;
escaped += next_ch;
s++;
}
}
else if (ch == ch1 || ch == ch2) {
result_length++;
need_escapes = true;
escaped += escape;
escaped += ch;
}
result_length++;
else
escaped += ch;
}
if (need_escapes) {
char *result = makeTmpString(result_length + 1);
char *r = result;
for (const char *s = token; *s; s++) {
char ch = *s;
if (ch == escape) {
char next_ch = s[1];
// Make sure we don't skip the null if escape is the last char.
if (next_ch != '\0') {
*r++ = ch;
*r++ = next_ch;
s++;
}
}
else if (ch == ch1 || ch == ch2) {
*r++ = escape;
*r++ = ch;
}
else
*r++ = ch;
}
*r++ = '\0';
return result;
}
else
return token;
return escaped;
}
} // namespace

View File

@ -22,10 +22,10 @@
namespace sta {
static const char *
static string
escapeDividers(const char *token,
const Network *network);
static const char *
static string
escapeBrackets(const char *token,
const Network *network);
@ -631,21 +631,22 @@ SdcNetwork::findPort(const Cell *cell,
Port *port = network_->findPort(cell, name);
if (port == nullptr) {
// Look for matches after escaping brackets.
char *bus_name;
bool is_bus;
string bus_name;
int index;
parseBusName(name, '[', ']', pathEscape(), bus_name, index);
if (bus_name) {
const char *escaped1 = escapeBrackets(name, this);
port = network_->findPort(cell, escaped1);
if (port == nullptr
&& bus_name[strlen(bus_name) - 1] == ']') {
parseBusName(name, '[', ']', pathEscape(), is_bus, bus_name, index);
if (is_bus) {
string escaped1 = escapeBrackets(name, this);
port = network_->findPort(cell, escaped1.c_str());
if (port == nullptr) {
// Try escaping base foo\[0\][1]
const char *escaped2 = stringPrintTmp("%s[%d]",
escapeBrackets(bus_name, this),
index);
port = network_->findPort(cell, escaped2);
string escaped2;
string escaped_bus_name = escapeBrackets(bus_name.c_str(), this);
stringPrint(escaped2, "%s[%d]",
escaped_bus_name.c_str(),
index);
port = network_->findPort(cell, escaped2.c_str());
}
stringDelete(bus_name);
}
}
return port;
@ -658,23 +659,25 @@ SdcNetwork::findPortsMatching(const Cell *cell,
PortSeq matches = network_->findPortsMatching(cell, pattern);
if (matches.empty()) {
// Look for matches after escaping brackets.
char *bus_name;
bool is_bus;
string bus_name;
int index;
parseBusName(pattern->pattern(), '[', ']', pathEscape(), bus_name, index);
if (bus_name) {
const char *escaped1 = escapeBrackets(pattern->pattern(), this);
PatternMatch escaped_pattern1(escaped1, pattern);
parseBusName(pattern->pattern(), '[', ']', pathEscape(),
is_bus, bus_name, index);
if (is_bus) {
string escaped1 = escapeBrackets(pattern->pattern(), this);
PatternMatch escaped_pattern1(escaped1.c_str(), pattern);
matches = network_->findPortsMatching(cell, &escaped_pattern1);
if (matches.empty()
&& bus_name[strlen(bus_name) - 1] == ']') {
if (matches.empty()) {
// Try escaping base foo\[0\][1]
const char *escaped2 = stringPrintTmp("%s[%d]",
escapeBrackets(bus_name, this),
index);
PatternMatch escaped_pattern2(escaped2, pattern);
string escaped2;
string escaped_bus_name = escapeBrackets(bus_name.c_str(), this);
stringPrint(escaped2, "%s[%d]",
escaped_bus_name.c_str(),
index);
PatternMatch escaped_pattern2(escaped2.c_str(), pattern);
matches = network_->findPortsMatching(cell, &escaped_pattern2);
}
stringDelete(bus_name);
}
}
return matches;
@ -739,8 +742,10 @@ SdcNetwork::findInstance(const char *path_name) const
if (parent == nullptr)
parent = network_->topInstance();
Instance *child = findChild(parent, child_name);
if (child == nullptr)
child = findChild(parent, escapeDividers(child_name, this));
if (child == nullptr) {
string escaped_name = escapeDividers(child_name, this);
child = findChild(parent, escaped_name.c_str());
}
return child;
}
@ -774,8 +779,8 @@ SdcNetwork::findChild(const Instance *parent,
{
Instance *child = network_->findChild(parent, name);
if (child == nullptr) {
const char *escaped = escapeBrackets(name, this);
child = network_->findChild(parent, escaped);
string escaped = escapeBrackets(name, this);
child = network_->findChild(parent, escaped.c_str());
}
return child;
}
@ -799,8 +804,8 @@ SdcNetwork::findNet(const Instance *instance,
{
Net *net = network_->findNet(instance, net_name);
if (net == nullptr) {
const char *net_name_ = escapeBrackets(net_name, this);
net = network_->findNet(instance, net_name_);
string net_name1 = escapeBrackets(net_name, this);
net = network_->findNet(instance, net_name1.c_str());
}
return net;
}
@ -829,14 +834,13 @@ SdcNetwork::findInstNetsMatching(const Instance *instance,
network_->findInstNetsMatching(instance, pattern, matches);
if (matches.empty()) {
// Look for matches after escaping path dividers.
const PatternMatch escaped_dividers(escapeDividers(pattern->pattern(),
this),
pattern);
string escaped_pattern = escapeDividers(pattern->pattern(), this);
const PatternMatch escaped_dividers(escaped_pattern.c_str(), pattern);
network_->findInstNetsMatching(instance, &escaped_dividers, matches);
if (matches.empty()) {
// Look for matches after escaping brackets.
const PatternMatch escaped_brkts(escapeBrackets(pattern->pattern(),this),
pattern);
string escaped_pattern2 = escapeBrackets(pattern->pattern(),this);
const PatternMatch escaped_brkts(escaped_pattern2.c_str(), pattern);
network_->findInstNetsMatching(instance, &escaped_brkts, matches);
}
}
@ -862,21 +866,21 @@ SdcNetwork::findPin(const Instance *instance,
Pin *pin = network_->findPin(instance, port_name);
if (pin == nullptr) {
// Look for match after escaping brackets.
char *bus_name;
bool is_bus;
string bus_name;
int index;
parseBusName(port_name, '[', ']', pathEscape(), bus_name, index);
if (bus_name) {
const char *escaped1 = escapeBrackets(port_name, this);
pin = network_->findPin(instance, escaped1);
if (pin == nullptr
&& bus_name[strlen(bus_name) - 1] == ']') {
parseBusName(port_name, '[', ']', pathEscape(),
is_bus, bus_name, index);
if (is_bus) {
string escaped1 = escapeBrackets(port_name, this);
pin = network_->findPin(instance, escaped1.c_str());
if (pin == nullptr) {
// Try escaping base foo\[0\][1]
const char *escaped2 = stringPrintTmp("%s[%d]",
escapeBrackets(bus_name, this),
index);
pin = network_->findPin(instance, escaped2);
string escaped_bus_name = escapeBrackets(bus_name.c_str(), this);
string escaped2;
stringPrint(escaped2, "%s[%d]", escaped_bus_name.c_str(), index);
pin = network_->findPin(instance, escaped2.c_str());
}
stringDelete(bus_name);
}
}
return pin;
@ -967,16 +971,16 @@ SdcNetwork::makeInstance(LibertyCell *cell,
const char *name,
Instance *parent)
{
const char *escaped_name = escapeDividers(name, this);
return network_edit_->makeInstance(cell, escaped_name, parent);
string escaped_name = escapeDividers(name, this);
return network_edit_->makeInstance(cell, escaped_name.c_str(), parent);
}
Net *
SdcNetwork::makeNet(const char *name,
Instance *parent)
{
const char *escaped_name = escapeDividers(name, this);
return network_edit_->makeNet(escaped_name, parent);
string escaped_name = escapeDividers(name, this);
return network_edit_->makeNet(escaped_name.c_str(), parent);
}
////////////////////////////////////////////////////////////////
@ -1154,10 +1158,9 @@ SdcNetwork::visitMatches(const Instance *parent,
found_match |= visit_tail(parent, &tail_pattern);
if (!found_match && has_brkts) {
// Look for matches after escaping brackets.
char *escaped_path = stringCopy(escapeBrackets(inst_path, this));
string escaped_path = escapeBrackets(inst_path, this);
const PatternMatch escaped_tail(escaped_path, pattern);
found_match |= visit_tail(parent, &escaped_tail);
stringDelete(escaped_path);
}
}
stringDelete(inst_path);
@ -1166,7 +1169,7 @@ SdcNetwork::visitMatches(const Instance *parent,
////////////////////////////////////////////////////////////////
static const char *
static string
escapeDividers(const char *token,
const Network *network)
{
@ -1174,7 +1177,7 @@ escapeDividers(const char *token,
network->pathEscape());
}
static const char *
static string
escapeBrackets(const char *token,
const Network *network)
{

View File

@ -23,72 +23,63 @@
namespace sta {
static const char *
static string
staToVerilog(const char *sta_name,
const char escape);
static const char *
static string
staToVerilog2(const char *sta_name,
const char escape);
static const char *
static string
verilogToSta(const char *verilog_name);
static inline void
vstringAppend(char *&str,
char *&str_end,
char *&insert,
char ch);
const char *
string
instanceVerilogName(const char *sta_name,
const char escape)
{
return staToVerilog(sta_name, escape);
}
const char *
string
netVerilogName(const char *sta_name,
const char escape)
{
char *bus_name;
bool is_bus;
string bus_name;
int index;
parseBusName(sta_name, '[', ']', escape, bus_name, index);
if (bus_name) {
const char *vname = stringPrintTmp("%s[%d]",
staToVerilog(bus_name, escape),
index);
stringDelete(bus_name);
parseBusName(sta_name, '[', ']', escape, is_bus, bus_name, index);
if (is_bus) {
string bus_vname = staToVerilog(bus_name.c_str(), escape);
string vname;
stringPrint(vname, "%s[%d]", bus_vname.c_str(), index);
return vname;
}
else
return staToVerilog2(sta_name, escape);
}
const char *
string
portVerilogName(const char *sta_name,
const char escape)
{
return staToVerilog2(sta_name, escape);
}
static const char *
static string
staToVerilog(const char *sta_name,
const char escape)
{
// Leave room for leading escape and trailing space if the name
// needs to be escaped.
size_t verilog_name_length = strlen(sta_name) + 3;
char *verilog_name = makeTmpString(verilog_name_length);
char *verilog_name_end = &verilog_name[verilog_name_length];
char *v = verilog_name;
// Assume the name has to be escaped and start copying while scanning.
string escaped_name = "\\";
bool escaped = false;
*v++ = '\\';
for (const char *s = sta_name; *s ; s++) {
char ch = s[0];
if (ch == escape) {
char next_ch = s[1];
if (next_ch == escape) {
vstringAppend(verilog_name, verilog_name_end, v, ch);
vstringAppend(verilog_name, verilog_name_end, v, next_ch);
escaped_name += ch;
escaped_name += next_ch;
s++;
}
else
@ -98,20 +89,19 @@ staToVerilog(const char *sta_name,
else {
if ((!(isalnum(ch) || ch == '_')))
escaped = true;
vstringAppend(verilog_name, verilog_name_end, v, ch);
escaped_name += ch;
}
}
if (escaped) {
// Add a terminating space.
vstringAppend(verilog_name, verilog_name_end, v, ' ');
vstringAppend(verilog_name, verilog_name_end, v, '\0');
return verilog_name;
escaped_name += ' ';
return escaped_name;
}
else
return sta_name;
return string(sta_name);
}
static const char *
static string
staToVerilog2(const char *sta_name,
const char escape)
{
@ -119,20 +109,16 @@ staToVerilog2(const char *sta_name,
constexpr char bus_brkt_right = ']';
// Leave room for leading escape and trailing space if the name
// needs to be escaped.
size_t verilog_name_length = strlen(sta_name) + 3;
char *verilog_name = makeTmpString(verilog_name_length);
char *verilog_name_end = &verilog_name[verilog_name_length];
char *v = verilog_name;
string escaped_name = "\\";
// Assume the name has to be escaped and start copying while scanning.
bool escaped = false;
*v++ = '\\';
for (const char *s = sta_name; *s ; s++) {
char ch = s[0];
if (ch == escape) {
char next_ch = s[1];
if (next_ch == escape) {
vstringAppend(verilog_name, verilog_name_end, v, ch);
vstringAppend(verilog_name, verilog_name_end, v, next_ch);
escaped_name += ch;
escaped_name += next_ch;
s++;
}
else
@ -144,46 +130,45 @@ staToVerilog2(const char *sta_name,
if ((!(isalnum(ch) || ch == '_') && !is_brkt)
|| is_brkt)
escaped = true;
vstringAppend(verilog_name, verilog_name_end, v, ch);
escaped_name += ch;
}
}
if (escaped) {
// Add a terminating space.
vstringAppend(verilog_name, verilog_name_end, v, ' ');
vstringAppend(verilog_name, verilog_name_end, v, '\0');
return verilog_name;
escaped_name += ' ';
return escaped_name;
}
else
return sta_name;
return string(sta_name);
}
////////////////////////////////////////////////////////////////
const char *
string
moduleVerilogToSta(const char *module_name)
{
return verilogToSta(module_name);
}
const char *
string
instanceVerilogToSta(const char *inst_name)
{
return verilogToSta(inst_name);
}
const char *
string
netVerilogToSta(const char *net_name)
{
return verilogToSta(net_name);
}
const char *
string
portVerilogToSta(const char *port_name)
{
return verilogToSta(port_name);
}
static const char *
static string
verilogToSta(const char *verilog_name)
{
if (verilog_name && verilog_name[0] == '\\') {
@ -197,11 +182,7 @@ verilogToSta(const char *verilog_name)
size_t verilog_name_length = strlen(verilog_name);
if (verilog_name[verilog_name_length - 1] == ' ')
verilog_name_length--;
// +1 for \0, +2 for escaping brackets.
size_t sta_name_length = verilog_name_length + 1;
char *sta_name = makeTmpString(sta_name_length);
char *sta_name_end = &sta_name[sta_name_length];
char *s = sta_name;
string sta_name;
for (size_t i = 0; i < verilog_name_length; i++) {
char ch = verilog_name[i];
if (ch == bus_brkt_left
@ -209,33 +190,13 @@ verilogToSta(const char *verilog_name)
|| ch == divider
|| ch == escape)
// Escape bus brackets, dividers and escapes.
vstringAppend(sta_name, sta_name_end, s, escape);
vstringAppend(sta_name, sta_name_end, s, ch);
sta_name += escape;
sta_name += ch;
}
vstringAppend(sta_name, sta_name_end, s, '\0');
return sta_name;
}
else
return verilog_name;
}
// Append ch to str at insert. Resize str if necessary.
static inline void
vstringAppend(char *&str,
char *&str_end,
char *&insert,
char ch)
{
if (insert == str_end) {
size_t length = str_end - str;
size_t length2 = length * 2;
char *new_str = makeTmpString(length2);
strncpy(new_str, str, length);
str = new_str;
str_end = &str[length2];
insert = &str[length];
}
*insert++ = ch;
return string(verilog_name);
}
} // namespace

View File

@ -131,14 +131,15 @@ ReadVcdActivities::setVarActivity(VcdVar *var,
string &var_name,
const VcdValues &var_values)
{
const char *sta_name = netVerilogToSta(var_name.c_str());
string sta_name = netVerilogToSta(var_name.c_str());
if (var->width() == 1)
setVarActivity(sta_name, var_values, 0);
setVarActivity(sta_name.c_str(), var_values, 0);
else {
char *bus_name;
bool is_bus;
string bus_name;
int from, to;
parseBusRange(sta_name, '[', ']', '\\',
bus_name, from, to);
parseBusRange(sta_name.c_str(), '[', ']', '\\',
is_bus, bus_name, from, to);
int value_bit = 0;
if (to < from) {
for (int bus_bit = to; bus_bit <= from; bus_bit++) {
@ -160,7 +161,6 @@ ReadVcdActivities::setVarActivity(VcdVar *var,
value_bit++;
}
}
stringDelete(bus_name);
}
}

View File

@ -128,8 +128,10 @@ celltype:
;
cell_instance:
'(' INSTANCE ')' { sta::sdf_reader->setInstance(NULL); }
| '(' INSTANCE '*' ')' { sta::sdf_reader->setInstanceWildcard(); }
'(' INSTANCE ')'
{ sta::sdf_reader->setInstance(NULL); }
| '(' INSTANCE '*' ')'
{ sta::sdf_reader->setInstanceWildcard(); }
| '(' INSTANCE path ')'
{ sta::sdf_reader->setInstance($3); }
;
@ -266,7 +268,10 @@ port:
ID
{ $$ = sta::sdf_reader->unescaped($1); }
| ID '[' DNUMBER ']'
{ $$ = sta::stringPrint("%s[%d]", sta::sdf_reader->unescaped($1), $3); }
{ const char *bus_name = sta::sdf_reader->unescaped($1);
$$ = sta::stringPrint("%s[%d]", bus_name, $3);
sta::stringDelete(bus_name);
}
;
port_instance:
@ -292,7 +297,7 @@ port_tchk:
| '(' COND EXPR_ID_CLOSE
{ $$ = sta::sdf_reader->makeCondPortSpec($3); }
| '(' COND EXPR_OPEN port_transition port_instance ')' ')'
{ $$ = sta::sdf_reader->makePortSpec($4, $5, $3); sta::stringDelete($3); }
{ $$ = sta::sdf_reader->makePortSpec($4, $5, $3); }
;
value:

View File

@ -210,6 +210,8 @@ SdfReader::interconnect(const char *from_pin_name,
sdfWarn(186, "pin %s not found.", to_pin_name);
}
}
stringDelete(from_pin_name);
stringDelete(to_pin_name);
deleteTripleSeq(triples);
}
@ -234,6 +236,7 @@ SdfReader::port(const char *to_pin_name,
}
}
}
stringDelete(to_pin_name);
deleteTripleSeq(triples);
}
@ -312,6 +315,7 @@ SdfReader::setInstance(const char *instance_name)
}
else
instance_ = nullptr;
stringDelete(instance_name);
}
void
@ -399,6 +403,7 @@ SdfReader::iopath(SdfPortSpec *from_edge,
}
}
}
stringDelete(to_port_name);
deletePortSpec(from_edge);
deleteTripleSeq(triples);
stringDelete(cond);
@ -688,6 +693,7 @@ SdfReader::device(const char *to_port_name,
setDevicePinDelays(to_pin, triples);
}
}
stringDelete(to_port_name);
deleteTripleSeq(triples);
}
@ -822,7 +828,10 @@ SdfReader::makePortSpec(Transition *tr,
const char *port,
const char *cond)
{
return new SdfPortSpec(tr, port, cond);
SdfPortSpec *port_spec = new SdfPortSpec(tr, port, cond);
stringDelete(port);
stringDelete(cond);
return port_spec;
}
SdfPortSpec *
@ -837,9 +846,9 @@ SdfReader::makeCondPortSpec(const char *cond_port)
auto cond_end = cond_port1.find_last_not_of(" ", port_idx);
if (cond_end != cond_port1.npos) {
string cond1 = cond_port1.substr(0, cond_end + 1);
SdfPortSpec *port_spec = makePortSpec(Transition::riseFall(),
port1.c_str(),
cond1.c_str());
SdfPortSpec *port_spec = new SdfPortSpec(Transition::riseFall(),
port1.c_str(),
cond1.c_str());
stringDelete(cond_port);
return port_spec;
}
@ -919,7 +928,7 @@ SdfReader::unescaped(const char *token)
{
char path_escape = network_->pathEscape();
char path_divider = network_->pathDivider();
char *unescaped = makeTmpString(strlen(token) + 1);
char *unescaped = new char[strlen(token) + 1];
char *u = unescaped;
size_t token_length = strlen(token);
@ -962,10 +971,12 @@ char *
SdfReader::makePath(const char *head,
const char *tail)
{
char *path = stringPrintTmp("%s%c%s",
head,
network_->pathDivider(),
tail);
char *path = stringPrint("%s%c%s",
head,
network_->pathDivider(),
tail);
sta::stringDelete(head);
sta::stringDelete(tail);
return path;
}

View File

@ -100,10 +100,10 @@ protected:
void writeSdfTriple(float min,
float max);
void writeSdfDelay(double delay);
char *sdfPortName(const Pin *pin);
char *sdfPathName(const Pin *pin);
char *sdfPathName(const Instance *inst);
char *sdfName(const Instance *inst);
string sdfPortName(const Pin *pin);
string sdfPathName(const Pin *pin);
string sdfPathName(const Instance *inst);
string sdfName(const Instance *inst);
private:
char sdf_divider_;
@ -310,9 +310,11 @@ SdfWriter::writeInterconnectFromPin(Pin *drvr_pin)
Edge *edge = edge_iter.next();
if (edge->isWire()) {
Pin *load_pin = edge->to(graph_)->pin();
string drvr_pin_name = sdfPathName(drvr_pin);
string load_pin_name = sdfPathName(load_pin);
gzprintf(stream_, " (INTERCONNECT %s %s ",
sdfPathName(drvr_pin),
sdfPathName(load_pin));
drvr_pin_name.c_str(),
load_pin_name.c_str());
writeArcDelays(edge);
gzprintf(stream_, ")\n");
}
@ -340,7 +342,8 @@ SdfWriter::writeInstHeader(const Instance *inst)
{
gzprintf(stream_, " (CELL\n");
gzprintf(stream_, " (CELLTYPE \"%s\")\n", network_->cellName(inst));
gzprintf(stream_, " (INSTANCE %s)\n", sdfPathName(inst));
string inst_name = sdfPathName(inst);
gzprintf(stream_, " (INSTANCE %s)\n", inst_name.c_str());
}
void
@ -384,9 +387,11 @@ SdfWriter::writeIopaths(const Instance *inst,
gzprintf(stream_, " (COND %s\n", sdf_cond);
gzprintf(stream_, " ");
}
gzprintf(stream_, " (IOPATH %s %s ",
sdfPortName(from_pin),
sdfPortName(to_pin));
string from_pin_name = sdfPortName(from_pin);
string to_pin_name = sdfPortName(to_pin);
gzprintf(stream_, " (IOPATH %s %s ",
from_pin_name.c_str(),
to_pin_name.c_str());
writeArcDelays(edge);
if (sdf_cond)
gzprintf(stream_, ")");
@ -651,12 +656,14 @@ SdfWriter::writeCheck(Edge *edge,
if (sdf_cond_start)
gzprintf(stream_, "(COND %s ", sdf_cond_start);
if (use_data_edge)
string to_pin_name = sdfPortName(to_pin);
if (use_data_edge) {
gzprintf(stream_, "(%s %s)",
sdfEdge(arc->toEdge()),
sdfPortName(to_pin));
to_pin_name.c_str());
}
else
gzprintf(stream_, "%s", sdfPortName(to_pin));
gzprintf(stream_, "%s", to_pin_name.c_str());
if (sdf_cond_start)
gzprintf(stream_, ")");
@ -666,12 +673,13 @@ SdfWriter::writeCheck(Edge *edge,
if (sdf_cond_end)
gzprintf(stream_, "(COND %s ", sdf_cond_end);
string from_pin_name = sdfPortName(from_pin);
if (use_clk_edge)
gzprintf(stream_, "(%s %s)",
sdfEdge(arc->fromEdge()),
sdfPortName(from_pin));
from_pin_name.c_str());
else
gzprintf(stream_, "%s", sdfPortName(from_pin));
gzprintf(stream_, "%s", from_pin_name.c_str());
if (sdf_cond_end)
gzprintf(stream_, ")");
@ -691,9 +699,10 @@ SdfWriter::writeWidthCheck(const Pin *pin,
float min_width,
float max_width)
{
string pin_name = sdfPortName(pin);
gzprintf(stream_, " (WIDTH (%s %s) ",
sdfEdge(hi_low->asTransition()),
sdfPortName(pin));
pin_name.c_str());
writeSdfTriple(min_width, max_width);
gzprintf(stream_, ")\n");
}
@ -702,8 +711,8 @@ void
SdfWriter::writePeriodCheck(const Pin *pin,
float min_period)
{
gzprintf(stream_, " (PERIOD %s ",
sdfPortName(pin));
string pin_name = sdfPortName(pin);
gzprintf(stream_, " (PERIOD %s ", pin_name.c_str());
writeSdfTriple(min_period, min_period);
gzprintf(stream_, ")\n");
}
@ -720,81 +729,68 @@ SdfWriter::sdfEdge(const Transition *tr)
////////////////////////////////////////////////////////////////
char *
string
SdfWriter::sdfPathName(const Pin *pin)
{
Instance *inst = network_->instance(pin);
if (network_->isTopInstance(inst))
return sdfPortName(pin);
else {
char *inst_path = sdfPathName(inst);
const char *port_name = sdfPortName(pin);
size_t length = strlen(inst_path) + 1 + strlen(port_name) + 1;
char *sdf_name = makeTmpString(length);
snprintf(sdf_name, length, "%s%c%s", inst_path, sdf_divider_, port_name);
string inst_path = sdfPathName(inst);
string port_name = sdfPortName(pin);
string sdf_name = inst_path;
sdf_name += sdf_divider_;
sdf_name += port_name;
return sdf_name;
}
}
// Based on Network::pathName.
char *
string
SdfWriter::sdfPathName(const Instance *instance)
{
InstanceSeq inst_path;
network_->path(instance, inst_path);
size_t name_length = 0;
InstanceSeq::Iterator path_iter1(inst_path);
while (path_iter1.hasNext()) {
const Instance *inst = path_iter1.next();
name_length += strlen(sdfName(inst)) + 1;
}
char *path_name = makeTmpString(name_length);
char *path_ptr = path_name;
// Top instance has null string name, so terminate the string here.
*path_name = '\0';
while (inst_path.size()) {
string path_name;
while (!inst_path.empty()) {
const Instance *inst = inst_path.back();
const char *inst_name = sdfName(inst);
strcpy(path_ptr, inst_name);
path_ptr += strlen(inst_name);
string inst_name = sdfName(inst);
path_name += inst_name;
inst_path.pop_back();
if (inst_path.size())
*path_ptr++ = sdf_divider_;
*path_ptr = '\0';
if (!inst_path.empty())
path_name += sdf_divider_;
}
return path_name;
}
// Escape for non-alpha numeric characters.
char *
string
SdfWriter::sdfName(const Instance *inst)
{
const char *name = network_->name(inst);
char *sdf_name = makeTmpString(strlen(name) * 2 + 1);
string sdf_name;
const char *p = name;
char *s = sdf_name;
while (*p) {
char ch = *p;
// Ignore sta escapes.
if (ch != network_escape_) {
if (!(isalnum(ch) || ch == '_'))
// Insert escape.
*s++ = sdf_escape_;
*s++ = ch;
sdf_name += sdf_escape_;
sdf_name += ch;
}
p++;
}
*s = '\0';
return sdf_name;
}
char *
string
SdfWriter::sdfPortName(const Pin *pin)
{
const char *name = network_->portName(pin);
size_t name_length = strlen(name);
char *sdf_name = makeTmpString(name_length * 2 + 1);
char *s = sdf_name;
string sdf_name;
constexpr char bus_brkt_left = '[';
constexpr char bus_brkt_right = ']';
@ -809,18 +805,17 @@ SdfWriter::sdfPortName(const Pin *pin)
char ch = name[i];
if (ch == network_escape_) {
// Copy escape and escaped char.
*s++ = sdf_escape_;
*s++ = name[++i];
sdf_name += sdf_escape_;
sdf_name += name[++i];
}
else {
if (!(isalnum(ch) || ch == '_')
&& !(i >= bus_index && (ch == bus_brkt_right || ch == bus_brkt_left)))
// Insert escape.
*s++ = sdf_escape_;
*s++ = ch;
sdf_name += sdf_escape_;
sdf_name += ch;
}
}
*s = '\0';
return sdf_name;
}

View File

@ -113,34 +113,35 @@ ClkInfo::asString(const StaState *sta) const
{
Network *network = sta->network();
Corners *corners = sta->corners();
string str;
string result;
PathAnalysisPt *path_ap = corners->findPathAnalysisPt(path_ap_index_);
str += stringPrintTmp("%s/%d ",
path_ap->pathMinMax()->asString(),
path_ap_index_);
result += path_ap->pathMinMax()->asString();
result += "/";
result += std::to_string(path_ap_index_);
if (clk_edge_)
str += clk_edge_->name();
result += clk_edge_->name();
else
str += "unclocked";
result += "unclocked";
if (clk_src_) {
str += " clk_src ";
str += network->pathName(clk_src_);
result += " clk_src ";
result += network->pathName(clk_src_);
}
if (!crpr_clk_path_.isNull()) {
const Pin *crpr_clk_pin = crpr_clk_path_.vertex(sta)->pin();
str += " crpr_pin ";
str += network->pathName(crpr_clk_pin);
result += " crpr_pin ";
result += network->pathName(crpr_clk_pin);
}
if (is_gen_clk_src_path_)
str += " genclk";
result += " genclk";
char *result = makeTmpString(str.size() + 1);
strcpy(result, str.c_str());
return result;
char *tmp = makeTmpString(result.size() + 1);
strcpy(tmp, result.c_str());
return tmp;
}
const Clock *

View File

@ -1028,7 +1028,9 @@ getProperty(Edge *edge,
auto graph = sta->graph();
const char *from = edge->from(graph)->name(network);
const char *to = edge->to(graph)->name(network);
return PropertyValue(stringPrintTmp("%s -> %s", from, to));
string full_name;
stringPrint(full_name, "%s -> %s", from, to);
return PropertyValue(full_name);
}
if (stringEqual(property, "delay_min_fall"))
return edgeDelayProperty(edge, RiseFall::fall(), MinMax::min(), sta);

View File

@ -94,83 +94,84 @@ Tag::asString(bool report_index,
{
const Network *network = sta->network();
const Corners *corners = sta->corners();
string str;
string result;
if (report_index)
str += stringPrintTmp("%4d ", index_);
result += std::to_string(index_);
if (report_rf_min_max) {
const RiseFall *rf = transition();
PathAnalysisPt *path_ap = corners->findPathAnalysisPt(path_ap_index_);
str += stringPrintTmp("%s %s/%d ",
rf->asString(),
path_ap->pathMinMax()->asString(),
path_ap_index_);
result += rf->asString();
result += " ";
result += path_ap->pathMinMax()->asString();
result += "/";
result += std::to_string(path_ap_index_);
}
const ClockEdge *clk_edge = clkEdge();
if (clk_edge)
str += clk_edge->name();
result += clk_edge->name();
else
str += "unclocked";
result += "unclocked";
bool is_genclk_src = clk_info_->isGenClkSrcPath();
if (is_clk_ || is_genclk_src) {
str += " (";
result += " (";
if (is_clk_) {
str += "clock";
result += "clock";
if (clk_info_->isPropagated())
str += " prop";
result += " prop";
else
str += " ideal";
result += " ideal";
if (is_genclk_src)
str += " ";
result += " ";
}
if (clk_info_->isGenClkSrcPath())
str += "genclk";
str += ")";
result += "genclk";
result += ")";
}
const Pin *clk_src = clkSrc();
if (clk_src) {
str += " clk_src ";
str += network->pathName(clk_src);
result += " clk_src ";
result += network->pathName(clk_src);
}
const PathVertex crpr_clk_path(clk_info_->crprClkPath(), sta);
if (!crpr_clk_path.isNull()) {
str += " crpr_pin ";
str += network->pathName(crpr_clk_path.pin(sta));
result += " crpr_pin ";
result += network->pathName(crpr_clk_path.pin(sta));
}
if (input_delay_) {
str += " input ";
str += network->pathName(input_delay_->pin());
result += " input ";
result += network->pathName(input_delay_->pin());
}
if (is_segment_start_)
str += " segment_start";
result += " segment_start";
if (states_) {
for (ExceptionState *state : *states_) {
ExceptionPath *exception = state->exception();
str += " ";
str += exception->asString(network);
result += " ";
result += exception->asString(network);
if (state->nextThru()) {
str += " (next thru ";
str += state->nextThru()->asString(network);
str += ")";
result += " (next thru ";
result += state->nextThru()->asString(network);
result += ")";
}
else {
if (exception->thrus() != nullptr)
str += " (thrus complete)";
result += " (thrus complete)";
}
}
}
char *result = makeTmpString(str.size() + 1);
strcpy(result, str.c_str());
return result;
char *tmp = makeTmpString(result.size() + 1);
strcpy(tmp, result.c_str());
return tmp;
}
const RiseFall *

View File

@ -57,6 +57,18 @@ PatternMatch::PatternMatch(const char *pattern,
compileRegexp();
}
PatternMatch::PatternMatch(string pattern,
const PatternMatch *inherit_from) :
pattern_(pattern.c_str()),
is_regexp_(inherit_from->is_regexp_),
nocase_(inherit_from->nocase_),
interp_(inherit_from->interp_),
regexp_(nullptr)
{
if (is_regexp_)
compileRegexp();
}
void
PatternMatch::compileRegexp()
{
@ -89,6 +101,12 @@ PatternMatch::hasWildcards() const
return patternWildcards(pattern_);
}
bool
PatternMatch::match(const string &str) const
{
return match(str.c_str());
}
bool
PatternMatch::match(const char *str) const
{

View File

@ -394,7 +394,7 @@ inst_named_pins:
inst_named_pin:
// Scalar port.
'.' ID '(' ')'
{ $$ = sta::verilog_reader->makeNetNamedPortRefScalarNet($2, NULL); }
{ $$ = sta::verilog_reader->makeNetNamedPortRefScalarNet($2); }
| '.' ID '(' ID ')'
{ $$ = sta::verilog_reader->makeNetNamedPortRefScalarNet($2, $4); }
| '.' ID '(' ID '[' INT ']' ')'

View File

@ -36,9 +36,9 @@ namespace sta {
VerilogReader *verilog_reader;
static const char *unconnected_net_name = reinterpret_cast<const char*>(1);
static const char *
verilogBusBitNameTmp(const char *bus_name,
int index);
static string
verilogBusBitName(const char *bus_name,
int index);
static int
hierarchyLevel(Net *net,
Network *network);
@ -255,17 +255,18 @@ VerilogReader::makeModule(const char *module_vname,
VerilogStmtSeq *stmts,
int line)
{
const char *module_name = moduleVerilogToSta(module_vname);
Cell *cell = network_->findCell(library_, module_name);
string module_name = moduleVerilogToSta(module_vname);
Cell *cell = network_->findCell(library_, module_name.c_str());
if (cell) {
VerilogModule *module = module_map_[cell];
delete module;
module_map_.erase(cell);
network_->deleteCell(cell);
}
VerilogModule *module = new VerilogModule(module_name, ports, stmts,
VerilogModule *module = new VerilogModule(module_name.c_str(),
ports, stmts,
filename_, line, this);
cell = network_->makeCell(library_, module_name, false, filename_);
cell = network_->makeCell(library_, module_name.c_str(), false, filename_);
module_map_[cell] = module;
makeCellPorts(cell, module, ports);
module_count_++;
@ -300,26 +301,25 @@ VerilogReader::makeCellPorts(Cell *cell,
VerilogModule *module,
VerilogNetSeq *ports)
{
StringSet port_names;
set<string> port_names;
for (VerilogNet *mod_port : *ports) {
const char *port_name = mod_port->name();
if (port_names.findKey(port_name) == nullptr) {
port_names.insert(stringCopy(port_name));
const string &port_name = mod_port->name();
if (port_names.find(port_name) == port_names.end()) {
port_names.insert(port_name);
if (mod_port->isNamed()) {
if (mod_port->isNamedPortRef())
makeNamedPortRefCellPorts(cell, module, mod_port, port_names);
else
makeCellPort(cell, module, mod_port->name());
makeCellPort(cell, module, mod_port->name().c_str());
}
}
else
warn(165, module->filename(), module->line(),
"module %s repeated port name %s.",
module->name(),
port_name);
port_name.c_str());
}
checkModuleDcls(module, port_names);
deleteContents(&port_names);
}
Port *
@ -351,25 +351,25 @@ void
VerilogReader::makeNamedPortRefCellPorts(Cell *cell,
VerilogModule *module,
VerilogNet *mod_port,
StringSet &port_names)
set<string> &port_names)
{
PortSeq *member_ports = new PortSeq;
VerilogNetNameIterator *net_name_iter = mod_port->nameIterator(module,this);
while (net_name_iter->hasNext()) {
const char *net_name = net_name_iter->next();
port_names.insert(stringCopy(net_name));
port_names.insert(net_name);
Port *port = makeCellPort(cell, module, net_name);
member_ports->push_back(port);
}
delete net_name_iter;
// Note that the bundle does NOT have a port declaration.
network_->makeBundlePort(cell, mod_port->name(), member_ports);
network_->makeBundlePort(cell, mod_port->name().c_str(), member_ports);
}
// Make sure each declaration appears in the module port list.
void
VerilogReader::checkModuleDcls(VerilogModule *module,
StringSet &port_names)
set<string> &port_names)
{
VerilogDclMap::ConstIterator dcl_iter(module->declarationMap());
while (dcl_iter.hasNext()) {
@ -380,7 +380,7 @@ VerilogReader::checkModuleDcls(VerilogModule *module,
if (dir->isInput()
|| dir->isOutput()
|| dir->isBidirect()) {
if (port_names.findKey(port_name) == nullptr)
if (port_names.find(port_name) == port_names.end())
linkWarn(197, module->filename(), module->line(),
"module %s declared signal %s is not in the port list.",
module->name(),
@ -457,10 +457,10 @@ VerilogDclArg *
VerilogReader::makeDclArg(const char *net_vname)
{
dcl_arg_count_++;
const char *net_name = netVerilogToSta(net_vname);
VerilogDclArg *dcl =new VerilogDclArg(net_name);
stringDelete(net_vname);
return dcl;
string net_name = netVerilogToSta(net_vname);
VerilogDclArg *dcl =new VerilogDclArg(net_name.c_str());
stringDelete(net_vname);
return dcl;
}
VerilogDclArg *
@ -478,8 +478,9 @@ VerilogReader::makeNetPartSelect(const char *net_vname,
net_part_select_count_++;
if (report_stmt_stats_)
net_bus_names_ += strlen(net_vname) + 1;
const char *net_name = netVerilogToSta(net_vname);
VerilogNetPartSelect *select = new VerilogNetPartSelect(net_name, from_index,
string net_name = netVerilogToSta(net_vname);
VerilogNetPartSelect *select = new VerilogNetPartSelect(net_name.c_str(),
from_index,
to_index);
stringDelete(net_vname);
return select;
@ -498,8 +499,8 @@ VerilogReader::makeNetScalar(const char *net_vname)
net_scalar_count_++;
if (report_stmt_stats_)
net_scalar_names_ += strlen(net_vname) + 1;
const char *net_name = netVerilogToSta(net_vname);
VerilogNetScalar *scalar = new VerilogNetScalar(net_name);
string net_name = netVerilogToSta(net_vname);
VerilogNetScalar *scalar = new VerilogNetScalar(net_name.c_str());
stringDelete(net_vname);
return scalar;
}
@ -511,8 +512,8 @@ VerilogReader::makeNetBitSelect(const char *net_vname,
net_bit_select_count_++;
if (report_stmt_stats_)
net_bus_names_ += strlen(net_vname) + 1;
const char *net_name = netVerilogToSta(net_vname);
VerilogNetBitSelect *select = new VerilogNetBitSelect(net_name, index);
string net_name = netVerilogToSta(net_vname);
VerilogNetBitSelect *select = new VerilogNetBitSelect(net_name.c_str(), index);
stringDelete(net_vname);
return select;
}
@ -532,9 +533,9 @@ VerilogReader::makeModuleInst(const char *module_vname,
VerilogNetSeq *pins,
const int line)
{
const char *module_name = moduleVerilogToSta(module_vname);
const char *inst_name = instanceVerilogToSta(inst_vname);
Cell *cell = network_->findAnyCell(module_name);
string module_name = moduleVerilogToSta(module_vname);
string inst_name = instanceVerilogToSta(inst_vname);
Cell *cell = network_->findAnyCell(module_name.c_str());
LibertyCell *liberty_cell = nullptr;
if (cell)
liberty_cell = network_->libertyCell(cell);
@ -549,7 +550,7 @@ VerilogReader::makeModuleInst(const char *module_vname,
for (VerilogNet *vnet : *pins) {
VerilogNetPortRefScalarNet *vpin =
dynamic_cast<VerilogNetPortRefScalarNet*>(vnet);
const char *port_name = vpin->name();
const char *port_name = vpin->name().c_str();
const char *net_name = vpin->netName();
// Steal the net name string.
vpin->setNetName(nullptr);
@ -569,11 +570,11 @@ VerilogReader::makeModuleInst(const char *module_vname,
delete vpin;
net_port_ref_scalar_net_count_--;
}
VerilogInst *inst = new VerilogLibertyInst(liberty_cell, inst_name,
VerilogInst *inst = new VerilogLibertyInst(liberty_cell, inst_name.c_str(),
net_names, line);
delete pins;
if (report_stmt_stats_) {
inst_names_ += strlen(inst_name) + 1;
inst_names_ += inst_name.size() + 1;
inst_lib_count_++;
inst_lib_net_arrays_ += port_count;
}
@ -582,10 +583,12 @@ VerilogReader::makeModuleInst(const char *module_vname,
return inst;
}
else {
VerilogInst *inst = new VerilogModuleInst(module_name, inst_name, pins, line);
VerilogInst *inst = new VerilogModuleInst(module_name.c_str(),
inst_name.c_str(),
pins, line);
if (report_stmt_stats_) {
inst_module_names_ += strlen(module_name) + 1;
inst_names_ += strlen(inst_name) + 1;
inst_module_names_ += module_name.size() + 1;
inst_names_ += inst_name.size() + 1;
inst_mod_count_++;
}
stringDelete(module_vname);
@ -602,7 +605,7 @@ VerilogReader::hasScalarNamedPortRefs(LibertyCell *liberty_cell,
&& pins->size() > 0
&& (*pins)[0]->isNamedPortRef()) {
for (VerilogNet *vpin : *pins) {
const char *port_name = vpin->name();
const char *port_name = vpin->name().c_str();
LibertyPort *port = liberty_cell->findLibertyPort(port_name);
if (port) {
if (!(port->size() == 1
@ -618,6 +621,18 @@ VerilogReader::hasScalarNamedPortRefs(LibertyCell *liberty_cell,
return false;
}
VerilogNetPortRef *
VerilogReader::makeNetNamedPortRefScalarNet(const char *port_vname)
{
net_port_ref_scalar_net_count_++;
if (report_stmt_stats_)
port_names_ += strlen(port_vname) + 1;
string port_name = portVerilogToSta(port_vname);
VerilogNetPortRef *ref = new VerilogNetPortRefScalarNet(port_name.c_str());
stringDelete(port_vname);
return ref;
}
VerilogNetPortRef *
VerilogReader::makeNetNamedPortRefScalarNet(const char *port_vname,
const char *net_vname)
@ -628,9 +643,10 @@ VerilogReader::makeNetNamedPortRefScalarNet(const char *port_vname,
net_scalar_names_ += strlen(net_vname) + 1;
port_names_ += strlen(port_vname) + 1;
}
const char *port_name = portVerilogToSta(port_vname);
const char *net_name = netVerilogToSta(net_vname);
VerilogNetPortRef *ref = new VerilogNetPortRefScalarNet(port_name, net_name);
string port_name = portVerilogToSta(port_vname);
string net_name = netVerilogToSta(net_vname);
VerilogNetPortRef *ref = new VerilogNetPortRefScalarNet(port_name.c_str(),
net_name.c_str());
stringDelete(port_vname);
stringDelete(net_vname);
return ref;
@ -642,14 +658,15 @@ VerilogReader::makeNetNamedPortRefBitSelect(const char *port_vname,
int index)
{
net_port_ref_scalar_net_count_++;
const char *bus_name = portVerilogToSta(bus_vname);
const char *net_name = verilogBusBitNameTmp(bus_name, index);
string bus_name = portVerilogToSta(bus_vname);
string net_name = verilogBusBitName(bus_name.c_str(), index);
if (report_stmt_stats_) {
net_scalar_names_ += strlen(net_name) + 1;
net_scalar_names_ += net_name.length() + 1;
port_names_ += strlen(port_vname) + 1;
}
const char *port_name = portVerilogToSta(port_vname);
VerilogNetPortRef *ref = new VerilogNetPortRefScalarNet(port_name, net_name);
string port_name = portVerilogToSta(port_vname);
VerilogNetPortRef *ref = new VerilogNetPortRefScalarNet(port_name.c_str(),
net_name.c_str());
stringDelete(port_vname);
stringDelete(bus_vname);
return ref;
@ -662,8 +679,8 @@ VerilogReader::makeNetNamedPortRefScalar(const char *port_vname,
net_port_ref_scalar_count_++;
if (report_stmt_stats_)
port_names_ += strlen(port_vname) + 1;
const char *port_name = portVerilogToSta(port_vname);
VerilogNetPortRef *ref = new VerilogNetPortRefScalar(port_name, net);
string port_name = portVerilogToSta(port_vname);
VerilogNetPortRef *ref = new VerilogNetPortRefScalar(port_name.c_str(), net);
stringDelete(port_vname);
return ref;
}
@ -674,8 +691,9 @@ VerilogReader::makeNetNamedPortRefBit(const char *port_vname,
VerilogNet *net)
{
net_port_ref_bit_count_++;
const char *port_name = portVerilogToSta(port_vname);
VerilogNetPortRef *ref = new VerilogNetPortRefBit(port_name, index, net);
string port_name = portVerilogToSta(port_vname);
VerilogNetPortRef *ref = new VerilogNetPortRefBit(port_name.c_str(),
index, net);
stringDelete(port_vname);
return ref;
}
@ -687,8 +705,9 @@ VerilogReader::makeNetNamedPortRefPart(const char *port_vname,
VerilogNet *net)
{
net_port_ref_part_count_++;
const char *port_name = portVerilogToSta(port_vname);
VerilogNetPortRef *ref = new VerilogNetPortRefPart(port_name, from_index,
string port_name = portVerilogToSta(port_vname);
VerilogNetPortRef *ref = new VerilogNetPortRefPart(port_name.c_str(),
from_index,
to_index, net);
stringDelete(port_vname);
return ref;
@ -776,20 +795,20 @@ VerilogReader::warn(int id,
va_end(args);
}
const char *
string
VerilogReader::verilogName(VerilogModuleInst *mod_inst)
{
return sta::instanceVerilogName(mod_inst->instanceName(),
network_->pathEscape());
}
const char *
string
VerilogReader::instanceVerilogName(const char *inst_name)
{
return sta::netVerilogName(inst_name, network_->pathEscape());
}
const char *
string
VerilogReader::netVerilogName(const char *net_name)
{
return sta::netVerilogName(net_name, network_->pathEscape());
@ -862,11 +881,13 @@ VerilogModule::parseDcl(VerilogDcl *dcl,
// supply0/supply1 dcl can be used as modifier for
// input/output/inout dcls.
dcl_map_[net_name] = dcl;
else if (!dcl->direction()->isInternal())
else if (!dcl->direction()->isInternal()) {
string net_vname = reader->netVerilogName(net_name);
reader->warn(18, filename_, dcl->line(),
"signal %s previously declared on line %d.",
reader->netVerilogName(net_name),
net_vname.c_str(),
existing_dcl->line());
}
}
else
dcl_map_[net_name] = dcl;
@ -890,9 +911,10 @@ VerilogModule::checkInstanceName(VerilogInst *inst,
stringDelete(replacement_name);
replacement_name = stringPrint("%s_%d", inst_name, i);
} while (inst_names.findKey(replacement_name));
string inst_vname = reader->instanceVerilogName(inst_name);
reader->warn(19, filename_, inst->line(),
"instance name %s duplicated - renamed to %s.",
reader->instanceVerilogName(inst_name),
inst_vname.c_str(),
replacement_name);
inst_name = replacement_name;
inst->setInstanceName(inst_name);
@ -1078,7 +1100,7 @@ VerilogDclArg::netName()
if (net_name_)
return net_name_;
else if (assign_)
return assign_->lhs()->name();
return assign_->lhs()->name().c_str();
else
return nullptr;
}
@ -1112,6 +1134,7 @@ class VerilogOneNetNameIterator : public VerilogNetNameIterator
{
public:
explicit VerilogOneNetNameIterator(const char *name);
explicit VerilogOneNetNameIterator(string name);
virtual bool hasNext();
virtual const char *next();
@ -1152,6 +1175,7 @@ protected:
int from_index_;
int to_index_;
int index_;
string bit_name_;
};
VerilogBusNetNameIterator::VerilogBusNetNameIterator(const char *bus_name,
@ -1176,19 +1200,21 @@ VerilogBusNetNameIterator::hasNext()
const char *
VerilogBusNetNameIterator::next()
{
const char *bit_name = verilogBusBitNameTmp(bus_name_, index_);
bit_name_ = verilogBusBitName(bus_name_, index_);
if (to_index_ > from_index_)
index_++;
else
index_--;
return bit_name;
return bit_name_.c_str();
}
static const char *
verilogBusBitNameTmp(const char *bus_name,
int index)
static string
verilogBusBitName(const char *bus_name,
int index)
{
return stringPrintTmp("%s[%d]", bus_name, index);
string bus_bit_name;
stringPrint(bus_bit_name, "%s[%d]", bus_name, index);
return bus_bit_name;
}
class VerilogConstantNetNameIterator : public VerilogNetNameIterator
@ -1291,21 +1317,27 @@ VerilogNetConcatNameIterator::next()
////////////////////////////////////////////////////////////////
const string VerilogNetUnnamed::null_;
VerilogNetNamed::VerilogNetNamed(const char *name) :
VerilogNet(),
name_(stringCopy(name))
name_(name)
{
}
VerilogNetNamed::VerilogNetNamed(const string &name) :
VerilogNet(),
name_(name)
{
}
VerilogNetNamed::~VerilogNetNamed()
{
stringDelete(name_);
}
void
VerilogNetNamed::setName(const char *name)
{
stringDelete(name_);
name_ = name;
}
@ -1329,7 +1361,7 @@ verilogNetScalarSize(const char *name,
int
VerilogNetScalar::size(VerilogModule *module)
{
return verilogNetScalarSize(name_, module);
return verilogNetScalarSize(name_.c_str(), module);
}
static VerilogNetNameIterator *
@ -1354,22 +1386,16 @@ VerilogNetNameIterator *
VerilogNetScalar::nameIterator(VerilogModule *module,
VerilogReader *)
{
return verilogNetScalarNameIterator(name_, module);
return verilogNetScalarNameIterator(name_.c_str(), module);
}
VerilogNetBitSelect::VerilogNetBitSelect(const char *name,
int index) :
VerilogNetNamed(name),
VerilogNetNamed(verilogBusBitName(name, index)),
index_(index)
{
}
const char *
VerilogNetBitSelect::name()
{
return verilogBusBitNameTmp(name_, index_);
}
int
VerilogNetBitSelect::size(VerilogModule *)
{
@ -1380,7 +1406,7 @@ VerilogNetNameIterator *
VerilogNetBitSelect::nameIterator(VerilogModule *,
VerilogReader *)
{
return new VerilogOneNetNameIterator(verilogBusBitNameTmp(name_, index_));
return new VerilogOneNetNameIterator(name_.c_str());
}
VerilogNetPartSelect::VerilogNetPartSelect(const char *name,
@ -1405,7 +1431,7 @@ VerilogNetNameIterator *
VerilogNetPartSelect::nameIterator(VerilogModule *,
VerilogReader *)
{
return new VerilogBusNetNameIterator(name_, from_index_, to_index_);
return new VerilogBusNetNameIterator(name_.c_str(), from_index_, to_index_);
}
VerilogNetConstant::VerilogNetConstant(const char *constant,
@ -1583,6 +1609,12 @@ VerilogNetPortRef::VerilogNetPortRef(const char *name) :
{
}
VerilogNetPortRefScalarNet::VerilogNetPortRefScalarNet(const char *name) :
VerilogNetPortRef(name),
net_name_(nullptr)
{
}
VerilogNetPortRefScalarNet::VerilogNetPortRefScalarNet(const char *name,
const char *net_name) :
VerilogNetPortRef(name),
@ -1651,16 +1683,10 @@ VerilogNetPortRefBit::VerilogNetPortRefBit(const char *name,
int index,
VerilogNet *net) :
VerilogNetPortRefScalar(name, net),
index_(index)
bit_name_(verilogBusBitName(name, index))
{
}
const char *
VerilogNetPortRefBit::name()
{
return verilogBusBitNameTmp(name_, index_);
}
VerilogNetPortRefPart::VerilogNetPortRefPart(const char *name,
int from_index,
int to_index,
@ -1670,8 +1696,8 @@ VerilogNetPortRefPart::VerilogNetPortRefPart(const char *name,
{
}
const char *
VerilogNetPortRefPart::name()
const string &
VerilogNetPortRefPart::name() const
{
return name_;
}
@ -1813,18 +1839,19 @@ VerilogReader::makeModuleInstNetwork(VerilogModuleInst *mod_inst,
const char *module_name = mod_inst->moduleName();
Cell *cell = network_->findAnyCell(module_name);
if (cell == nullptr) {
string inst_vname = verilogName(mod_inst);
if (make_black_boxes) {
cell = makeBlackBox(mod_inst, parent_module);
linkWarn(198, parent_module->filename(), mod_inst->line(),
"module %s not found. Creating black box for %s.",
mod_inst->moduleName(),
verilogName(mod_inst));
inst_vname.c_str());
}
else
linkError(199, parent_module->filename(), mod_inst->line(),
"module %s not found for instance %s.",
mod_inst->moduleName(),
verilogName(mod_inst));
inst_vname.c_str());
}
if (cell) {
LibertyCell *lib_cell = network_->libertyCell(cell);
@ -1868,20 +1895,22 @@ VerilogReader::makeNamedInstPins(Cell *cell,
VerilogBindingTbl *parent_bindings,
bool is_leaf)
{
string inst_vname = verilogName(mod_inst);
VerilogNetSeq::Iterator pin_iter(mod_inst->pins());
while (pin_iter.hasNext()) {
VerilogNetPortRef *vpin = dynamic_cast<VerilogNetPortRef*>(pin_iter.next());
const char *port_name = vpin->name();
const char *port_name = vpin->name().c_str();
Port *port = network_->findPort(cell, port_name);
if (port) {
if (vpin->hasNet()
&& network_->size(port) != vpin->size(parent_module))
&& network_->size(port) != vpin->size(parent_module)) {
linkWarn(200, parent_module->filename(), mod_inst->line(),
"instance %s port %s size %d does not match net size %d.",
verilogName(mod_inst),
inst_vname.c_str(),
network_->name(port),
network_->size(port),
vpin->size(parent_module));
}
else {
VerilogNetNameIterator *net_name_iter =
vpin->nameIterator(parent_module, this);
@ -1907,11 +1936,12 @@ VerilogReader::makeNamedInstPins(Cell *cell,
if (lib_cell)
pg_port = lib_cell->findPgPort(port_name);
// Do not warn about connections to pg ports (which are ignored).
if (pg_port == nullptr)
if (pg_port == nullptr) {
linkWarn(201, parent_module->filename(), mod_inst->line(),
"instance %s port %s not found.",
verilogName(mod_inst),
inst_vname.c_str(),
port_name);
}
}
}
}
@ -1931,13 +1961,15 @@ VerilogReader::makeOrderedInstPins(Cell *cell,
while (pin_iter.hasNext() && port_iter->hasNext()) {
VerilogNet *net = pin_iter.next();
Port *port = port_iter->next();
if (network_->size(port) != net->size(parent_module))
if (network_->size(port) != net->size(parent_module)) {
string inst_vname = verilogName(mod_inst);
linkWarn(202, parent_module->filename(), mod_inst->line(),
"instance %s port %s size %d does not match net size %d.",
verilogName(mod_inst),
inst_vname.c_str(),
network_->name(port),
network_->size(port),
net->size(parent_module));
}
else {
VerilogNetNameIterator *net_name_iter=net->nameIterator(parent_module,
this);
@ -2027,9 +2059,8 @@ VerilogReader::makeLibertyInst(VerilogLibertyInst *lib_inst,
if (dcl && dcl->isBus()) {
VerilogDclBus *dcl_bus = dynamic_cast<VerilogDclBus *>(dcl);
// Bus is only 1 bit wide.
const char *bus_name = verilogBusBitNameTmp(net_name,
dcl_bus->fromIndex());
net = parent_bindings->ensureNetBinding(bus_name, parent, network_);
string bus_name = verilogBusBitName(net_name, dcl_bus->fromIndex());
net = parent_bindings->ensureNetBinding(bus_name.c_str(), parent, network_);
}
else
net = parent_bindings->ensureNetBinding(net_name, parent, network_);
@ -2066,7 +2097,7 @@ VerilogReader::makeBlackBoxNamedPorts(Cell *cell,
VerilogNetSeq::Iterator pin_iter(mod_inst->pins());
while (pin_iter.hasNext()) {
VerilogNetNamed *vpin = dynamic_cast<VerilogNetNamed*>(pin_iter.next());
const char *port_name = vpin->name();
const char *port_name = vpin->name().c_str();
size_t size = vpin->size(parent_module);
Port *port = (size == 1)
? network_->makePort(cell, port_name)

View File

@ -32,6 +32,9 @@ VerilogParse_error(const char *msg);
namespace sta {
using std::string;
using std::set;
class Debug;
class Report;
class VerilogReader;
@ -117,6 +120,7 @@ public:
VerilogNet *rhs,
int line);
VerilogNetScalar *makeNetScalar(const char *name);
VerilogNetPortRef *makeNetNamedPortRefScalarNet(const char *port_vname);
VerilogNetPortRef *makeNetNamedPortRefScalarNet(const char *port_name,
const char *net_name);
VerilogNetPortRef *makeNetNamedPortRefBitSelect(const char *port_name,
@ -160,11 +164,11 @@ public:
void reportStmtCounts();
const char *constant10Max() const { return constant10_max_; }
size_t constant10MaxLength() const { return constant10_max_length_; }
const char *
string
verilogName(VerilogModuleInst *inst);
const char *
string
instanceVerilogName(const char *inst_name);
const char *
string
netVerilogName(const char *net_name);
protected:
@ -178,9 +182,9 @@ protected:
void makeNamedPortRefCellPorts(Cell *cell,
VerilogModule *module,
VerilogNet *mod_port,
StringSet &port_names);
set<string> &port_names);
void checkModuleDcls(VerilogModule *module,
StringSet &port_names);
set<string> &port_names);
void makeModuleInstBody(VerilogModule *module,
Instance *inst,
VerilogBindingTbl *bindings,
@ -488,8 +492,8 @@ class VerilogNet
public:
VerilogNet() {}
virtual ~VerilogNet() {}
virtual bool isNamed() = 0;
virtual const char *name() = 0;
virtual bool isNamed() const = 0;
virtual const string &name() const = 0;
virtual bool isNamedPortRef() { return false; }
virtual bool isNamedPortRefScalarNet() const { return false; }
virtual int size(VerilogModule *module) = 0;
@ -503,23 +507,27 @@ class VerilogNetUnnamed : public VerilogNet
{
public:
VerilogNetUnnamed() {}
virtual bool isNamed() { return false; }
virtual const char *name() { return nullptr; }
bool isNamed() const override { return false; }
const string &name() const override { return null_; }
private:
static const string null_;
};
class VerilogNetNamed : public VerilogNet
{
public:
explicit VerilogNetNamed(const char *name);
explicit VerilogNetNamed(const string &name);
virtual ~VerilogNetNamed();
virtual bool isNamed() { return true; }
bool isNamed() const override { return true; }
virtual bool isScalar() const = 0;
virtual const char *name() { return name_; }
const char *baseName() { return name_; }
const string &name() const override { return name_; }
const string baseName() const { return name_; }
void setName(const char *name);
protected:
const char *name_;
string name_;
};
// Named net reference, which could be the name of a scalar or bus signal.
@ -538,7 +546,6 @@ class VerilogNetBitSelect : public VerilogNetNamed
public:
VerilogNetBitSelect(const char *name,
int index);
virtual const char *name();
int index() { return index_; }
virtual bool isScalar() const { return false; }
virtual int size(VerilogModule *module);
@ -620,6 +627,7 @@ public:
class VerilogNetPortRefScalarNet : public VerilogNetPortRef
{
public:
VerilogNetPortRefScalarNet(const char *name);
VerilogNetPortRefScalarNet(const char *name,
const char *net_name);
virtual ~VerilogNetPortRefScalarNet();
@ -658,10 +666,10 @@ public:
VerilogNetPortRefBit(const char *name,
int index,
VerilogNet *net);
virtual const char *name();
const string &name() const override { return bit_name_; }
private:
int index_;
string bit_name_;
};
class VerilogNetPortRefPart : public VerilogNetPortRefBit
@ -671,7 +679,7 @@ public:
int from_index,
int to_index,
VerilogNet *net);
virtual const char *name();
const string &name() const override;
int toIndex() const { return to_index_; }
private:

View File

@ -159,8 +159,9 @@ VerilogWriter::writePorts(Cell *cell)
|| !network_->direction(port)->isPowerGround()) {
if (!first)
fprintf(stream_, ",\n ");
fprintf(stream_, "%s", portVerilogName(network_->name(port),
network_->pathEscape()));
string verillg_name = portVerilogName(network_->name(port),
network_->pathEscape());
fprintf(stream_, "%s", verillg_name.c_str());
first = false;
}
}
@ -177,8 +178,8 @@ VerilogWriter::writePortDcls(Cell *cell)
PortDirection *dir = network_->direction(port);
if (include_pwr_gnd_
|| !network_->direction(port)->isPowerGround()) {
const char *port_name = portVerilogName(network_->name(port),
network_->pathEscape());
string port_vname = portVerilogName(network_->name(port),
network_->pathEscape());
const char *vtype = verilogPortDir(dir);
if (vtype) {
fprintf(stream_, " %s", vtype);
@ -186,14 +187,14 @@ VerilogWriter::writePortDcls(Cell *cell)
fprintf(stream_, " [%d:%d]",
network_->fromIndex(port),
network_->toIndex(port));
fprintf(stream_, " %s;\n", port_name);
fprintf(stream_, " %s;\n", port_vname.c_str());
if (dir->isTristate()) {
fprintf(stream_, " tri");
if (network_->isBus(port))
fprintf(stream_, " [%d:%d]",
network_->fromIndex(port),
network_->toIndex(port));
fprintf(stream_, " %s;\n", port_name);
fprintf(stream_, " %s;\n", port_vname.c_str());
}
}
}
@ -238,16 +239,18 @@ VerilogWriter::writeWireDcls(Instance *inst)
const char *net_name = network_->name(net);
if (network_->findPort(cell, net_name) == nullptr) {
if (isBusName(net_name, '[', ']', escape)) {
char *bus_name;
bool is_bus;
string bus_name;
int index;
parseBusName(net_name, '[', ']', escape, bus_name, index);
BusIndexRange &range = bus_ranges[bus_name];
parseBusName(net_name, '[', ']', escape, is_bus, bus_name, index);
BusIndexRange &range = bus_ranges[bus_name.c_str()];
range.first = max(range.first, index);
range.second = min(range.second, index);
}
else
fprintf(stream_, " wire %s;\n",
netVerilogName(net_name, network_->pathEscape()));;
else {
string net_vname = netVerilogName(net_name, network_->pathEscape());
fprintf(stream_, " wire %s;\n", net_vname.c_str());;
}
}
}
delete net_iter;
@ -255,10 +258,11 @@ VerilogWriter::writeWireDcls(Instance *inst)
for (auto name_range : bus_ranges) {
const char *bus_name = name_range.first;
const BusIndexRange &range = name_range.second;
string net_vname = netVerilogName(bus_name, network_->pathEscape());
fprintf(stream_, " wire [%d:%d] %s;\n",
range.first,
range.second,
netVerilogName(bus_name, network_->pathEscape()));;
net_vname.c_str());;
}
// Wire net dcls for writeInstBusPinBit.
@ -297,11 +301,10 @@ VerilogWriter::writeChild(Instance *child)
Cell *child_cell = network_->cell(child);
if (!remove_cells_.hasKey(child_cell)) {
const char *child_name = network_->name(child);
const char *child_vname = instanceVerilogName(child_name,
network_->pathEscape());
string child_vname = instanceVerilogName(child_name, network_->pathEscape());
fprintf(stream_, " %s %s (",
network_->name(child_cell),
child_vname);
child_vname.c_str());
bool first_port = true;
CellPortIterator *port_iter = network_->portIterator(child_cell);
while (port_iter->hasNext()) {
@ -329,14 +332,14 @@ VerilogWriter::writeInstPin(Instance *inst,
Net *net = network_->net(pin);
if (net) {
const char *net_name = network_->name(net);
const char *net_vname = netVerilogName(net_name, network_->pathEscape());
string net_vname = netVerilogName(net_name, network_->pathEscape());
if (!first_port)
fprintf(stream_, ",\n ");
const char *port_name = portVerilogName(network_->name(port),
network_->pathEscape());
string port_vname = portVerilogName(network_->name(port),
network_->pathEscape());
fprintf(stream_, ".%s(%s)",
port_name,
net_vname);
port_vname.c_str(),
net_vname.c_str());
first_port = false;
}
}
@ -382,19 +385,17 @@ VerilogWriter::writeInstBusPinBit(Instance *inst,
bool &first_member)
{
Pin *pin = network_->findPin(inst, port);
const char *net_name = nullptr;
if (pin) {
Net *net = network_->net(pin);
if (net)
net_name = network_->name(net);
}
if (net_name == nullptr)
Net *net = pin ? network_->net(pin) : nullptr;
string net_name;
if (net)
net_name = network_->name(net);
else
// There is no verilog syntax to "skip" a bit in the concatentation.
net_name = stringPrintTmp("_NC%d", unconnected_net_index_++);
const char *net_vname = netVerilogName(net_name, network_->pathEscape());
stringPrint(net_name, "_NC%d", unconnected_net_index_++);
string net_vname = netVerilogName(net_name.c_str(), network_->pathEscape());
if (!first_member)
fprintf(stream_, ",\n ");
fprintf(stream_, "%s", net_vname);
fprintf(stream_, "%s", net_vname.c_str());
first_member = false;
}
@ -414,11 +415,13 @@ VerilogWriter::writeAssigns(Instance *inst)
&& network_->direction(port)->isAnyOutput()
&& !stringEqual(network_->name(port), network_->name(net))) {
// Port name is different from net name.
string port_vname = netVerilogName(network_->name(port),
network_->pathEscape());
string net_vname = netVerilogName(network_->name(net),
network_->pathEscape());
fprintf(stream_, " assign %s = %s;\n",
netVerilogName(network_->name(port),
network_->pathEscape()),
netVerilogName(network_->name(net),
network_->pathEscape()));
port_vname.c_str(),
net_vname.c_str());
}
}
delete pin_iter;