Set::intersects

Signed-off-by: James Cherry <cherry@parallaxsw.com>
This commit is contained in:
James Cherry 2023-06-15 09:52:32 -07:00
parent 44159bbb53
commit b0bede4c6d
7 changed files with 110 additions and 57 deletions

View File

@ -61,7 +61,8 @@ public:
ExceptionThruSeq *thrus() const { return thrus_; } ExceptionThruSeq *thrus() const { return thrus_; }
ExceptionTo *to() const { return to_; } ExceptionTo *to() const { return to_; }
ExceptionPt *firstPt(); ExceptionPt *firstPt();
bool intersectsPts(ExceptionPath *exception) const; bool intersectsPts(ExceptionPath *exception,
const Network *network) const;
const MinMaxAll *minMax() const { return min_max_; } const MinMaxAll *minMax() const { return min_max_; }
virtual bool matches(const MinMax *min_max, virtual bool matches(const MinMax *min_max,
bool exact) const; bool exact) const;
@ -71,7 +72,8 @@ public:
virtual bool resetMatch(ExceptionFrom *from, virtual bool resetMatch(ExceptionFrom *from,
ExceptionThruSeq *thrus, ExceptionThruSeq *thrus,
ExceptionTo *to, ExceptionTo *to,
const MinMaxAll *min_max); const MinMaxAll *min_max,
const Network *network);
// The priority remains the same even though pin/clock/net/inst objects // The priority remains the same even though pin/clock/net/inst objects
// are added to the exceptions points during exception merging because // are added to the exceptions points during exception merging because
// only exceptions with the same priority are merged. // only exceptions with the same priority are merged.
@ -262,7 +264,8 @@ public:
virtual bool resetMatch(ExceptionFrom *from, virtual bool resetMatch(ExceptionFrom *from,
ExceptionThruSeq *thrus, ExceptionThruSeq *thrus,
ExceptionTo *to, ExceptionTo *to,
const MinMaxAll *min_max); const MinMaxAll *min_max,
const Network *network);
virtual int typePriority() const; virtual int typePriority() const;
virtual bool tighterThan(ExceptionPath *exception) const; virtual bool tighterThan(ExceptionPath *exception) const;
}; };
@ -424,7 +427,8 @@ public:
const Network *network); const Network *network);
ExceptionFrom *clone(const Network *network); ExceptionFrom *clone(const Network *network);
virtual bool isFrom() const { return true; } virtual bool isFrom() const { return true; }
bool intersectsPts(ExceptionFrom *from) const; bool intersectsPts(ExceptionFrom *from,
const Network *network) const;
virtual int typePriority() const { return 0; } virtual int typePriority() const { return 0; }
protected: protected:
@ -448,7 +452,8 @@ public:
virtual bool isTo() const { return true; } virtual bool isTo() const { return true; }
const char *asString(const Network *network) const; const char *asString(const Network *network) const;
const RiseFallBoth *endTransition() { return end_rf_; } const RiseFallBoth *endTransition() { return end_rf_; }
bool intersectsPts(ExceptionTo *to) const; bool intersectsPts(ExceptionTo *to,
const Network *network) const;
virtual int typePriority() const { return 1; } virtual int typePriority() const { return 1; }
bool matches(const Pin *pin, bool matches(const Pin *pin,
const ClockEdge *clk_edge, const ClockEdge *clk_edge,
@ -511,7 +516,8 @@ public:
const Network *network) const; const Network *network) const;
virtual void mergeInto(ExceptionPt *pt, virtual void mergeInto(ExceptionPt *pt,
const Network *network); const Network *network);
bool intersectsPts(ExceptionThru *thru) const; bool intersectsPts(ExceptionThru *thru,
const Network *network) const;
virtual int typePriority() const { return 2; } virtual int typePriority() const { return 2; }
virtual size_t objectCount() const; virtual size_t objectCount() const;
virtual void connectPinAfter(PinSet *drvrs, virtual void connectPinAfter(PinSet *drvrs,

View File

@ -146,6 +146,9 @@ public:
static int compare(const InstanceSet *set1, static int compare(const InstanceSet *set1,
const InstanceSet *set2, const InstanceSet *set2,
const Network *network); const Network *network);
static bool intersects(const InstanceSet *set1,
const InstanceSet *set2,
const Network *network);
}; };
class PinSet : public Set<const Pin*, PinIdLess> class PinSet : public Set<const Pin*, PinIdLess>
@ -156,6 +159,9 @@ public:
static int compare(const PinSet *set1, static int compare(const PinSet *set1,
const PinSet *set2, const PinSet *set2,
const Network *network); const Network *network);
static bool intersects(const PinSet *set1,
const PinSet *set2,
const Network *network);
}; };
class NetSet : public Set<const Net*, NetIdLess> class NetSet : public Set<const Net*, NetIdLess>
@ -166,6 +172,9 @@ public:
static int compare(const NetSet *set1, static int compare(const NetSet *set1,
const NetSet *set2, const NetSet *set2,
const Network *network); const Network *network);
static bool intersects(const NetSet *set1,
const NetSet *set2,
const Network *network);
}; };
} // namespace } // namespace

View File

@ -70,7 +70,8 @@ public:
static bool static bool
intersects(const std::set<KEY, CMP> *set1, intersects(const std::set<KEY, CMP> *set1,
const std::set<KEY, CMP> *set2); const std::set<KEY, CMP> *set2,
CMP key_less);
// Java style container itererator // Java style container itererator
// Set::Iterator<Key*> iter(set); // Set::Iterator<Key*> iter(set);
@ -170,20 +171,21 @@ Set<KEY, CMP>::isSubset(const std::set<KEY, CMP> *set2)
template <class KEY, class CMP> template <class KEY, class CMP>
bool bool
Set<KEY, CMP>::intersects(const std::set<KEY, CMP> *set1, Set<KEY, CMP>::intersects(const std::set<KEY, CMP> *set1,
const std::set<KEY, CMP> *set2) const std::set<KEY, CMP> *set2,
CMP key_less)
{ {
if (set1 && !set1->empty() if (set1 && set2) {
&& set2 && !set2->empty()) { auto iter1 = set1->begin();
if (set2->size() > set1->size())
std::swap(set1, set2);
auto end1 = set1->end(); auto end1 = set1->end();
auto iter2 = set2->begin(); auto iter2 = set2->begin();
auto end2 = set2->end(); auto end2 = set2->end();
while (iter2 != end2) { while (iter1 != end1 && iter2 != end2) {
const KEY key2 = *iter2; if (key_less(*iter1, *iter2))
if (set1->find(key2) != end1) iter1++;
return true; else if (key_less(*iter2, *iter1))
iter2++; iter2++;
else
return true;
} }
} }
return false; return false;

View File

@ -2093,6 +2093,16 @@ InstanceSet::compare(const InstanceSet *set1,
return (size1 > size2) ? 1 : -1; return (size1 > size2) ? 1 : -1;
} }
bool
InstanceSet::intersects(const InstanceSet *set1,
const InstanceSet *set2,
const Network *network)
{
return Set<const Instance*, InstanceIdLess>::intersects(set1, set2, InstanceIdLess(network));
}
////////////////////////////////////////////////////////////////
PinSet::PinSet() : PinSet::PinSet() :
Set<const Pin*, PinIdLess>(PinIdLess(nullptr)) Set<const Pin*, PinIdLess>(PinIdLess(nullptr))
{ {
@ -2130,6 +2140,16 @@ PinSet::compare(const PinSet *set1,
return (size1 > size2) ? 1 : -1; return (size1 > size2) ? 1 : -1;
} }
bool
PinSet::intersects(const PinSet *set1,
const PinSet *set2,
const Network *network)
{
return Set<const Pin*, PinIdLess>::intersects(set1, set2, PinIdLess(network));
}
////////////////////////////////////////////////////////////////
NetSet::NetSet() : NetSet::NetSet() :
Set<const Net*, NetIdLess>(NetIdLess(nullptr)) Set<const Net*, NetIdLess>(NetIdLess(nullptr))
{ {
@ -2167,4 +2187,12 @@ NetSet::compare(const NetSet *set1,
return (size1 > size2) ? 1 : -1; return (size1 > size2) ? 1 : -1;
} }
bool
NetSet::intersects(const NetSet *set1,
const NetSet *set2,
const Network *network)
{
return Set<const Net*, NetIdLess>::intersects(set1, set2, NetIdLess(network));
}
} // namespace } // namespace

View File

@ -31,7 +31,8 @@ namespace sta {
static bool static bool
thrusIntersectPts(ExceptionThruSeq *thrus1, thrusIntersectPts(ExceptionThruSeq *thrus1,
ExceptionThruSeq *thrus2); ExceptionThruSeq *thrus2,
const Network *network);
static void static void
insertPinPairsThruHierPin(const Pin *hpin, insertPinPairsThruHierPin(const Pin *hpin,
const Network *network, const Network *network,
@ -273,23 +274,24 @@ ExceptionPath::mergeablePts(ExceptionPath *exception2,
} }
bool bool
ExceptionPath::intersectsPts(ExceptionPath *exception) const ExceptionPath::intersectsPts(ExceptionPath *exception,
const Network *network) const
{ {
ExceptionFrom *from2 = exception->from(); ExceptionFrom *from2 = exception->from();
ExceptionThruSeq *thrus2 = exception->thrus(); ExceptionThruSeq *thrus2 = exception->thrus();
ExceptionTo *to2 = exception->to(); ExceptionTo *to2 = exception->to();
if (((from_ == nullptr && from2 == nullptr) if (((from_ == nullptr && from2 == nullptr)
|| (from_ && from2 && from_->intersectsPts(from2))) || (from_ && from2 && from_->intersectsPts(from2, network)))
&& ((thrus_ == nullptr && thrus2 == nullptr) && ((thrus_ == nullptr && thrus2 == nullptr)
|| (thrus_ && thrus2 && thrus_->size() == thrus2->size())) || (thrus_ && thrus2 && thrus_->size() == thrus2->size()))
&& ((to_ == nullptr && to2 == nullptr) && ((to_ == nullptr && to2 == nullptr)
|| (to_ && to2 && to_->intersectsPts(to2)))) { || (to_ && to2 && to_->intersectsPts(to2, network)))) {
ExceptionThruSeq::Iterator thrus_iter1(thrus_); ExceptionThruSeq::Iterator thrus_iter1(thrus_);
ExceptionThruSeq::Iterator thrus_iter2(thrus2); ExceptionThruSeq::Iterator thrus_iter2(thrus2);
while (thrus_iter1.hasNext() && thrus_iter2.hasNext()) { while (thrus_iter1.hasNext() && thrus_iter2.hasNext()) {
ExceptionThru *thru1 = thrus_iter1.next(); ExceptionThru *thru1 = thrus_iter1.next();
ExceptionThru *thru2 = thrus_iter2.next(); ExceptionThru *thru2 = thrus_iter2.next();
if (!thru1->intersectsPts(thru2)) if (!thru1->intersectsPts(thru2, network))
return false; return false;
} }
return true; return true;
@ -373,7 +375,8 @@ bool
ExceptionPath::resetMatch(ExceptionFrom *from, ExceptionPath::resetMatch(ExceptionFrom *from,
ExceptionThruSeq *thrus, ExceptionThruSeq *thrus,
ExceptionTo *to, ExceptionTo *to,
const MinMaxAll *min_max) const MinMaxAll *min_max,
const Network *network)
{ {
// Only the reset expception points need to match. // Only the reset expception points need to match.
// For example, if the reset is -from, it matches any // For example, if the reset is -from, it matches any
@ -382,56 +385,57 @@ ExceptionPath::resetMatch(ExceptionFrom *from,
return ((from && from_ return ((from && from_
&& thrus == nullptr && thrus == nullptr
&& to == nullptr && to == nullptr
&& from_->intersectsPts(from)) && from_->intersectsPts(from, network))
// -thru // -thru
|| (from == nullptr || (from == nullptr
&& thrus && thrus_ && thrus && thrus_
&& to == nullptr && to == nullptr
&& thrusIntersectPts(thrus_, thrus)) && thrusIntersectPts(thrus_, thrus, network))
// -to // -to
|| (from == nullptr || (from == nullptr
&& thrus == nullptr && thrus == nullptr
&& to && to_ && to && to_
&& to_->intersectsPts(to)) && to_->intersectsPts(to, network))
// -from -thru // -from -thru
|| (from && from_ || (from && from_
&& thrus && thrus_ && thrus && thrus_
&& to == nullptr && to == nullptr
&& from_->intersectsPts(from) && from_->intersectsPts(from, network)
&& thrusIntersectPts(thrus_, thrus)) && thrusIntersectPts(thrus_, thrus, network))
// -from -to // -from -to
|| (from && from_ || (from && from_
&& thrus == nullptr && thrus == nullptr
&& to && to_ && to && to_
&& from_->intersectsPts(from) && from_->intersectsPts(from, network)
&& to_->intersectsPts(to)) && to_->intersectsPts(to, network))
// -thru -to // -thru -to
|| (from == nullptr || (from == nullptr
&& thrus && thrus_ && thrus && thrus_
&& to && to_ && to && to_
&& thrusIntersectPts(thrus_, thrus) && thrusIntersectPts(thrus_, thrus, network)
&& to_->intersectsPts(to)) && to_->intersectsPts(to, network))
// -from -thru -to // -from -thru -to
|| (from && from_ || (from && from_
&& thrus && thrus_ && thrus && thrus_
&& to && to_ && to && to_
&& from_->intersectsPts(from) && from_->intersectsPts(from, network)
&& thrusIntersectPts(thrus_, thrus) && thrusIntersectPts(thrus_, thrus, network)
&& to_->intersectsPts(to))) && to_->intersectsPts(to, network)))
&& (min_max == MinMaxAll::all() && (min_max == MinMaxAll::all()
|| min_max_ == min_max); || min_max_ == min_max);
} }
static bool static bool
thrusIntersectPts(ExceptionThruSeq *thrus1, thrusIntersectPts(ExceptionThruSeq *thrus1,
ExceptionThruSeq *thrus2) ExceptionThruSeq *thrus2,
const Network *network)
{ {
ExceptionThruSeq::Iterator thrus_iter1(thrus1); ExceptionThruSeq::Iterator thrus_iter1(thrus1);
ExceptionThruSeq::Iterator thrus_iter2(thrus2); ExceptionThruSeq::Iterator thrus_iter2(thrus2);
while (thrus_iter1.hasNext() && thrus_iter2.hasNext()) { while (thrus_iter1.hasNext() && thrus_iter2.hasNext()) {
ExceptionThru *thru1 = thrus_iter1.next(); ExceptionThru *thru1 = thrus_iter1.next();
ExceptionThru *thru2 = thrus_iter2.next(); ExceptionThru *thru2 = thrus_iter2.next();
if (!thru1->intersectsPts(thru2)) if (!thru1->intersectsPts(thru2, network))
return false; return false;
} }
return true; return true;
@ -774,7 +778,8 @@ bool
FilterPath::resetMatch(ExceptionFrom *, FilterPath::resetMatch(ExceptionFrom *,
ExceptionThruSeq *, ExceptionThruSeq *,
ExceptionTo *, ExceptionTo *,
const MinMaxAll *) const MinMaxAll *,
const Network *)
{ {
return false; return false;
} }
@ -1220,12 +1225,13 @@ ExceptionFrom::clone(const Network *network)
} }
bool bool
ExceptionFrom::intersectsPts(ExceptionFrom *from) const ExceptionFrom::intersectsPts(ExceptionFrom *from,
const Network *network) const
{ {
return from->transition() == rf_ return from->transition() == rf_
&& ((pins_ && PinSet::intersects(pins_, from->pins())) && ((pins_ && PinSet::intersects(pins_, from->pins(), network))
|| (clks_ && ClockSet::intersects(clks_, from->clks())) || (clks_ && ClockSet::intersects(clks_, from->clks(), ClockIndexLess()))
|| (insts_ && InstanceSet::intersects(insts_, from->instances()))); || (insts_ && InstanceSet::intersects(insts_, from->instances(), network)));
} }
const char * const char *
@ -1284,13 +1290,14 @@ ExceptionTo::asString(const Network *network) const
} }
bool bool
ExceptionTo::intersectsPts(ExceptionTo *to) const ExceptionTo::intersectsPts(ExceptionTo *to,
const Network *network) const
{ {
return to->transition() == rf_ return to->transition() == rf_
&& to->endTransition() == end_rf_ && to->endTransition() == end_rf_
&& ((pins_ && PinSet::intersects(pins_, to->pins())) && ((pins_ && PinSet::intersects(pins_, to->pins(), network))
|| (clks_ && ClockSet::intersects(clks_, to->clks())) || (clks_ && ClockSet::intersects(clks_, to->clks(), ClockIndexLess()))
|| (insts_ && InstanceSet::intersects(insts_, to->instances()))); || (insts_ && InstanceSet::intersects(insts_, to->instances(), network)));
} }
bool bool
@ -1926,12 +1933,13 @@ ExceptionThru::deleteObjects(ExceptionThru *pt,
} }
bool bool
ExceptionThru::intersectsPts(ExceptionThru *thru) const ExceptionThru::intersectsPts(ExceptionThru *thru,
const Network *network) const
{ {
return thru->transition() == rf_ return thru->transition() == rf_
&& ((pins_ && PinSet::intersects(pins_, thru->pins())) && ((pins_ && PinSet::intersects(pins_, thru->pins(), network))
|| (nets_ && NetSet::intersects(nets_, thru->nets())) || (nets_ && NetSet::intersects(nets_, thru->nets(), network))
|| (insts_ && InstanceSet::intersects(insts_, thru->instances()))); || (insts_ && InstanceSet::intersects(insts_, thru->instances(), network)));
} }
size_t size_t
@ -1973,7 +1981,7 @@ ExceptionThru::connectPinAfter(PinSet *drvrs,
for (const Pin *thru_pin : *pins_) { for (const Pin *thru_pin : *pins_) {
if (network->isHierarchical(thru_pin)) { if (network->isHierarchical(thru_pin)) {
PinSet *thru_pin_drvrs = network->drivers(thru_pin); PinSet *thru_pin_drvrs = network->drivers(thru_pin);
if (PinSet::intersects(drvrs, thru_pin_drvrs)) if (PinSet::intersects(drvrs, thru_pin_drvrs, network))
makePinEdges(thru_pin, network); makePinEdges(thru_pin, network);
} }
} }
@ -1985,7 +1993,7 @@ ExceptionThru::connectPinAfter(PinSet *drvrs,
while (inst_pin_iter->hasNext()) { while (inst_pin_iter->hasNext()) {
Pin *inst_pin = inst_pin_iter->next(); Pin *inst_pin = inst_pin_iter->next();
PinSet *inst_pin_drvrs = network->drivers(inst_pin); PinSet *inst_pin_drvrs = network->drivers(inst_pin);
if (PinSet::intersects(drvrs, inst_pin_drvrs)) if (PinSet::intersects(drvrs, inst_pin_drvrs, network))
makePinEdges(inst_pin, network); makePinEdges(inst_pin, network);
} }
delete inst_pin_iter; delete inst_pin_iter;
@ -1995,7 +2003,7 @@ ExceptionThru::connectPinAfter(PinSet *drvrs,
if (nets_) { if (nets_) {
for (const Net *net : *nets_) { for (const Net *net : *nets_) {
PinSet *net_drvrs = network->drivers(net); PinSet *net_drvrs = network->drivers(net);
if (PinSet::intersects(drvrs, net_drvrs)) if (PinSet::intersects(drvrs, net_drvrs, network))
makeNetEdges(net, network); makeNetEdges(net, network);
} }
} }

View File

@ -4355,7 +4355,7 @@ Sdc::findMatchingExceptionsFirstThru(ExceptionPath *exception,
ExceptionThru *match_thru = (*match->thrus())[0]; ExceptionThru *match_thru = (*match->thrus())[0];
if (match_thru->nets()->hasKey(net) if (match_thru->nets()->hasKey(net)
&& match->overrides(exception) && match->overrides(exception)
&& match->intersectsPts(exception)) && match->intersectsPts(exception, network_))
matches.insert(match); matches.insert(match);
} }
} }
@ -4427,7 +4427,7 @@ Sdc::findMatchingExceptions(ExceptionPath *exception,
if (potential_matches) { if (potential_matches) {
for (ExceptionPath *match : *potential_matches) { for (ExceptionPath *match : *potential_matches) {
if (match->overrides(exception) if (match->overrides(exception)
&& match->intersectsPts(exception)) && match->intersectsPts(exception, network_))
matches.insert(match); matches.insert(match);
} }
} }
@ -5072,7 +5072,7 @@ Sdc::resetPath(ExceptionFrom *from,
ExceptionPathSet::Iterator except_iter(exceptions_); ExceptionPathSet::Iterator except_iter(exceptions_);
while (except_iter.hasNext()) { while (except_iter.hasNext()) {
ExceptionPath *match = except_iter.next(); ExceptionPath *match = except_iter.next();
if (match->resetMatch(from, thrus, to, min_max)) { if (match->resetMatch(from, thrus, to, min_max, network_)) {
debugPrint(debug_, "exception_match", 3, "reset match %s", debugPrint(debug_, "exception_match", 3, "reset match %s",
match->asString(network_)); match->asString(network_));
ExceptionPathSet expansions; ExceptionPathSet expansions;
@ -5081,7 +5081,7 @@ Sdc::resetPath(ExceptionFrom *from,
ExceptionPathSet::Iterator expand_iter(expansions); ExceptionPathSet::Iterator expand_iter(expansions);
while (expand_iter.hasNext()) { while (expand_iter.hasNext()) {
ExceptionPath *expand = expand_iter.next(); ExceptionPath *expand = expand_iter.next();
if (expand->resetMatch(from, thrus, to, min_max)) { if (expand->resetMatch(from, thrus, to, min_max, network_)) {
unrecordPathDelayInternalStartpoints(expand->from()); unrecordPathDelayInternalStartpoints(expand->from());
unrecordPathDelayInternalEndpoints(expand); unrecordPathDelayInternalEndpoints(expand);
delete expand; delete expand;

View File

@ -402,7 +402,7 @@ CheckCrpr::crprPossible(const Clock *clk1,
|| clk1->isGenerated() || clk1->isGenerated()
|| clk2->isGenerated() || clk2->isGenerated()
// Different non-generated clocks with the same source pins (using -add). // Different non-generated clocks with the same source pins (using -add).
|| PinSet::intersects(&clk1->pins(), &clk2->pins())); || PinSet::intersects(&clk1->pins(), &clk2->pins(), network_));
} }
} // namespace } // namespace