Various bugs in the virtual flattening mechanism.
* Bug: In Hurricane, in Cell::flattenNets(), addition to the topHyperNets vector was done *inside* the components loop, resulting in multiple additions of the same top net. This was leading to the RoutingPads created multiple times on the same connectors. Hence the conflict in KiteEngine::protectRoutingPads(). * Change: In Hurricane, in Cell::flattenNets(), do not create RoutingPads or build rings on already routed Nets. A Net is considered already routed if it has at least one Segment. This way we avoid Rubbers to be drawn over routed Nets. * Change: In Hurricane, in DeepNet, do not build RoutingPads & rings on already routed Nets (same condition as in Cell::flattenNets()). * New: In Hurricane, in HyperNet, new collection of all component occurrences of an HyperNet. May or may not (default) include components from the leaf cells.
This commit is contained in:
parent
ae0e6aed25
commit
33355f0e54
|
@ -617,20 +617,22 @@ void Cell::flattenNets(unsigned int flags)
|
||||||
|
|
||||||
HyperNet hyperNet ( occurrence );
|
HyperNet hyperNet ( occurrence );
|
||||||
if ( not occurrence.getPath().isEmpty() ) {
|
if ( not occurrence.getPath().isEmpty() ) {
|
||||||
|
//cerr << "* HyperNet: " << occurrence.getName() << endl;
|
||||||
Net* duplicate = getNet( occurrence.getName() );
|
Net* duplicate = getNet( occurrence.getName() );
|
||||||
if (not duplicate) {
|
if (not duplicate) {
|
||||||
hyperNets.push_back( HyperNet(occurrence) );
|
hyperNets.push_back( HyperNet(occurrence) );
|
||||||
} else {
|
} else {
|
||||||
trace << "Found " << duplicate << " in " << duplicate->getCell() << endl;
|
trace << "Found " << duplicate << " in " << duplicate->getCell() << endl;
|
||||||
}
|
}
|
||||||
} else {
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
bool hasRoutingPads = false;
|
bool hasRoutingPads = false;
|
||||||
for ( Component* component : net->getComponents() ) {
|
for ( Component* component : net->getComponents() ) {
|
||||||
RoutingPad* rp = dynamic_cast<RoutingPad*>( component );
|
RoutingPad* rp = dynamic_cast<RoutingPad*>( component );
|
||||||
if (rp) {
|
if (rp) {
|
||||||
// At least one RoutingPad is present: assumes that the net is already
|
// At least one RoutingPad is present: assumes that the net is already
|
||||||
// flattened (completly).
|
// flattened (completly).
|
||||||
//cerr << net << " has already RoutingPads, skipped " << rp << endl;
|
|
||||||
hasRoutingPads = true;
|
hasRoutingPads = true;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -639,7 +641,6 @@ void Cell::flattenNets(unsigned int flags)
|
||||||
|
|
||||||
topHyperNets.push_back( HyperNet(occurrence) );
|
topHyperNets.push_back( HyperNet(occurrence) );
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
for ( size_t i=0 ; i<hyperNets.size() ; ++i ) {
|
for ( size_t i=0 ; i<hyperNets.size() ; ++i ) {
|
||||||
DeepNet* deepNet = DeepNet::create( hyperNets[i] );
|
DeepNet* deepNet = DeepNet::create( hyperNets[i] );
|
||||||
|
@ -686,10 +687,11 @@ void Cell::createRoutingPadRings(unsigned int flags)
|
||||||
} else {
|
} else {
|
||||||
buildRing = flags & Cell::Flags::BuildRings;
|
buildRing = flags & Cell::Flags::BuildRings;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (not buildRing) continue;
|
if (not buildRing) continue;
|
||||||
|
|
||||||
for ( Component* component : net->getComponents() ) {
|
for ( Component* component : net->getComponents() ) {
|
||||||
|
if (dynamic_cast<Segment*>(component)) { buildRing = false; break; }
|
||||||
|
|
||||||
Plug* primaryPlug = dynamic_cast<Plug*>( component );
|
Plug* primaryPlug = dynamic_cast<Plug*>( component );
|
||||||
if (primaryPlug) {
|
if (primaryPlug) {
|
||||||
if (not primaryPlug->getBodyHook()->getSlaveHooks().isEmpty()) {
|
if (not primaryPlug->getBodyHook()->getSlaveHooks().isEmpty()) {
|
||||||
|
@ -700,6 +702,7 @@ void Cell::createRoutingPadRings(unsigned int flags)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if (not buildRing) continue;
|
||||||
|
|
||||||
for ( RoutingPad* rp : net->getRoutingPads() ) {
|
for ( RoutingPad* rp : net->getRoutingPads() ) {
|
||||||
if ( previousRp
|
if ( previousRp
|
||||||
|
@ -781,6 +784,15 @@ void Cell::uniquify(unsigned int depth)
|
||||||
{
|
{
|
||||||
//cerr << "Cell::uniquify() " << this << endl;
|
//cerr << "Cell::uniquify() " << this << endl;
|
||||||
|
|
||||||
|
vector<DeepNet*> deepNets;
|
||||||
|
for ( DeepNet* deepNet : getNets().getSubSet<DeepNet*>() ) {
|
||||||
|
deepNets.push_back( deepNet );
|
||||||
|
}
|
||||||
|
while ( not deepNets.empty() ) {
|
||||||
|
deepNets.back()->destroy();
|
||||||
|
deepNets.pop_back();
|
||||||
|
}
|
||||||
|
|
||||||
vector<Instance*> toUniquify;
|
vector<Instance*> toUniquify;
|
||||||
set<Cell*> masterCells;
|
set<Cell*> masterCells;
|
||||||
|
|
||||||
|
|
|
@ -81,18 +81,25 @@ namespace Hurricane {
|
||||||
size_t nbRoutingPads = 0;
|
size_t nbRoutingPads = 0;
|
||||||
HyperNet hyperNet ( _netOccurrence );
|
HyperNet hyperNet ( _netOccurrence );
|
||||||
RoutingPad* currentRp = NULL;
|
RoutingPad* currentRp = NULL;
|
||||||
|
bool createRp = true;
|
||||||
|
|
||||||
forEach ( Occurrence, ioccurrence, hyperNet.getLeafPlugOccurrences() ) {
|
for ( Occurrence occurrence : hyperNet.getComponentOccurrences() ) {
|
||||||
|
if ( dynamic_cast<RoutingPad*>(occurrence.getEntity()) ) { createRp = false; break; }
|
||||||
|
if ( dynamic_cast<Segment* >(occurrence.getEntity()) ) { createRp = false; break; }
|
||||||
|
}
|
||||||
|
if (not createRp) return 0;
|
||||||
|
|
||||||
|
for ( Occurrence occurrence : hyperNet.getLeafPlugOccurrences() ) {
|
||||||
nbRoutingPads++;
|
nbRoutingPads++;
|
||||||
|
|
||||||
currentRp = RoutingPad::create( this, *ioccurrence, RoutingPad::BiggestArea );
|
currentRp = RoutingPad::create( this, occurrence, RoutingPad::BiggestArea );
|
||||||
if (flags & Cell::Flags::WarnOnUnplacedInstances)
|
if (flags & Cell::Flags::WarnOnUnplacedInstances)
|
||||||
currentRp->isPlacedOccurrence ( RoutingPad::ShowWarning );
|
currentRp->isPlacedOccurrence ( RoutingPad::ShowWarning );
|
||||||
|
|
||||||
if (nbRoutingPads == 1) {
|
if (nbRoutingPads == 1) {
|
||||||
//Net* net =
|
//Net* net =
|
||||||
currentRp->getNet();
|
currentRp->getNet();
|
||||||
//cerr << "_createRoutingPads on " << net->getName() << " buildRing:" << buildRing << endl;
|
//cerr << "_createRoutingPads on " << net->getName() << " buildRing:" << endl;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -253,6 +253,78 @@ class HyperNet_LeafPlugOccurrences : public Collection<Occurrence> {
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
// ****************************************************************************************************
|
||||||
|
// HyperNet_ComponentOccurrences definition
|
||||||
|
// ****************************************************************************************************
|
||||||
|
|
||||||
|
class HyperNet_ComponentOccurrences : public Collection<Occurrence> {
|
||||||
|
// *****************************************************************
|
||||||
|
|
||||||
|
// Types
|
||||||
|
// *****
|
||||||
|
|
||||||
|
public: typedef Collection<Occurrence> Inherit;
|
||||||
|
|
||||||
|
public: class Locator : public Hurricane::Locator<Occurrence> {
|
||||||
|
// *********************************************************
|
||||||
|
|
||||||
|
public: typedef Hurricane::Locator<Occurrence> Inherit;
|
||||||
|
|
||||||
|
private: bool _withLeafCells;
|
||||||
|
private: OccurrenceLocator _netOccurrenceLocator;
|
||||||
|
private: ComponentLocator _componentLocator;
|
||||||
|
private: Occurrence _componentOccurrence;
|
||||||
|
|
||||||
|
public: Locator();
|
||||||
|
public: Locator(const HyperNet* hyperNet, bool withLeafCells = false, bool doExtraction = false, bool allowInterruption = false);
|
||||||
|
public: Locator(const Locator& locator);
|
||||||
|
|
||||||
|
public: Locator& operator=(const Locator& locator);
|
||||||
|
|
||||||
|
public: virtual Occurrence getElement() const;
|
||||||
|
public: virtual Hurricane::Locator<Occurrence>* getClone() const;
|
||||||
|
|
||||||
|
public: virtual bool isValid() const;
|
||||||
|
|
||||||
|
public: virtual void progress();
|
||||||
|
|
||||||
|
public: virtual string _getString() const;
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
// Attributes
|
||||||
|
// **********
|
||||||
|
|
||||||
|
private: const HyperNet* _hyperNet;
|
||||||
|
private: bool _withLeafCells;
|
||||||
|
private: bool _doExtraction;
|
||||||
|
private: bool _allowInterruption;
|
||||||
|
|
||||||
|
// Constructors
|
||||||
|
// ************
|
||||||
|
|
||||||
|
public: HyperNet_ComponentOccurrences();
|
||||||
|
public: HyperNet_ComponentOccurrences(const HyperNet* hyperNet, bool withLeafCells = false, bool doExtraction = false, bool allowInterruption = false);
|
||||||
|
public: HyperNet_ComponentOccurrences(const HyperNet_ComponentOccurrences& componentOccurrences);
|
||||||
|
|
||||||
|
// Operators
|
||||||
|
// *********
|
||||||
|
|
||||||
|
public: HyperNet_ComponentOccurrences& operator=(const HyperNet_ComponentOccurrences& componentOccurrences);
|
||||||
|
|
||||||
|
// Accessors
|
||||||
|
// *********
|
||||||
|
|
||||||
|
public: virtual Collection<Occurrence>* getClone() const;
|
||||||
|
public: virtual Hurricane::Locator<Occurrence>* getLocator() const;
|
||||||
|
|
||||||
|
// Others
|
||||||
|
// ******
|
||||||
|
|
||||||
|
public: virtual string _getString() const;
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
// ****************************************************************************************************
|
// ****************************************************************************************************
|
||||||
// HyperNet implementation
|
// HyperNet implementation
|
||||||
|
@ -292,6 +364,12 @@ Occurrences HyperNet::getLeafPlugOccurrences(bool doExtraction, bool allowInterr
|
||||||
return HyperNet_LeafPlugOccurrences(this, doExtraction, allowInterruption);
|
return HyperNet_LeafPlugOccurrences(this, doExtraction, allowInterruption);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Occurrences HyperNet::getComponentOccurrences(bool doExtraction, bool allowInterruption) const
|
||||||
|
// *******************************************************************************************
|
||||||
|
{
|
||||||
|
return HyperNet_ComponentOccurrences(this, doExtraction, allowInterruption);
|
||||||
|
}
|
||||||
|
|
||||||
string HyperNet::_getString() const
|
string HyperNet::_getString() const
|
||||||
// ********************************
|
// ********************************
|
||||||
{
|
{
|
||||||
|
@ -1001,6 +1079,185 @@ string HyperNet_LeafPlugOccurrences::Locator::_getString() const
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// ****************************************************************************************************
|
||||||
|
// HyperNet_ComponentOccurrences implementation
|
||||||
|
// ****************************************************************************************************
|
||||||
|
|
||||||
|
HyperNet_ComponentOccurrences::HyperNet_ComponentOccurrences()
|
||||||
|
// ***********************************************************
|
||||||
|
: Inherit(),
|
||||||
|
_hyperNet(NULL),
|
||||||
|
_withLeafCells(false),
|
||||||
|
_doExtraction(false),
|
||||||
|
_allowInterruption(false)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
HyperNet_ComponentOccurrences::HyperNet_ComponentOccurrences(const HyperNet* hyperNet, bool withLeafCells, bool doExtraction, bool allowInterruption)
|
||||||
|
// ****************************************************************************************************************************************************
|
||||||
|
: Inherit(),
|
||||||
|
_hyperNet(hyperNet),
|
||||||
|
_withLeafCells(withLeafCells),
|
||||||
|
_doExtraction(doExtraction),
|
||||||
|
_allowInterruption(allowInterruption)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
HyperNet_ComponentOccurrences::HyperNet_ComponentOccurrences(const HyperNet_ComponentOccurrences& netOccurrences)
|
||||||
|
// **************************************************************************************************************
|
||||||
|
: Inherit(),
|
||||||
|
_hyperNet(netOccurrences._hyperNet),
|
||||||
|
_withLeafCells(netOccurrences._withLeafCells),
|
||||||
|
_doExtraction(netOccurrences._doExtraction),
|
||||||
|
_allowInterruption(netOccurrences._allowInterruption)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
HyperNet_ComponentOccurrences& HyperNet_ComponentOccurrences::operator=(const HyperNet_ComponentOccurrences& netOccurrences)
|
||||||
|
// *************************************************************************************************************************
|
||||||
|
{
|
||||||
|
_hyperNet = netOccurrences._hyperNet;
|
||||||
|
_withLeafCells = netOccurrences._withLeafCells;
|
||||||
|
_doExtraction = netOccurrences._doExtraction;
|
||||||
|
_allowInterruption = netOccurrences._allowInterruption;
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
Collection<Occurrence>* HyperNet_ComponentOccurrences::getClone() const
|
||||||
|
// ********************************************************************
|
||||||
|
{
|
||||||
|
return new HyperNet_ComponentOccurrences(*this);
|
||||||
|
}
|
||||||
|
|
||||||
|
Locator<Occurrence>* HyperNet_ComponentOccurrences::getLocator() const
|
||||||
|
// *******************************************************************
|
||||||
|
{
|
||||||
|
return new Locator(_hyperNet, _withLeafCells, _doExtraction, _allowInterruption);
|
||||||
|
}
|
||||||
|
|
||||||
|
string HyperNet_ComponentOccurrences::_getString() const
|
||||||
|
// *****************************************************
|
||||||
|
{
|
||||||
|
string s = "<" + _TName("HyperNet::ComponentOccurrences");
|
||||||
|
if (_hyperNet) {
|
||||||
|
s += " " + getString(_hyperNet);
|
||||||
|
if (_withLeafCells) {
|
||||||
|
s += " LEAFS";
|
||||||
|
if (_doExtraction) {
|
||||||
|
s += " DO_EXTRACTION";
|
||||||
|
if (_allowInterruption) s += " ALLOW_INTERRUPTION";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
s += ">";
|
||||||
|
return s;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
// ****************************************************************************************************
|
||||||
|
// HyperNet_ComponentOccurrences::Locator implementation
|
||||||
|
// ****************************************************************************************************
|
||||||
|
|
||||||
|
HyperNet_ComponentOccurrences::Locator::Locator()
|
||||||
|
// **********************************************
|
||||||
|
: Inherit(),
|
||||||
|
_netOccurrenceLocator(),
|
||||||
|
_componentLocator(),
|
||||||
|
_componentOccurrence()
|
||||||
|
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
HyperNet_ComponentOccurrences::Locator::Locator(const HyperNet* hyperNet, bool withLeafCells, bool doExtraction, bool allowInterruption)
|
||||||
|
// *************************************************************************************************************************************
|
||||||
|
: Inherit(),
|
||||||
|
_withLeafCells(withLeafCells),
|
||||||
|
_netOccurrenceLocator(),
|
||||||
|
_componentLocator(),
|
||||||
|
_componentOccurrence()
|
||||||
|
{
|
||||||
|
if (hyperNet) {
|
||||||
|
_netOccurrenceLocator = hyperNet->getNetOccurrences(doExtraction,allowInterruption).getLocator();
|
||||||
|
progress();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
HyperNet_ComponentOccurrences::Locator::Locator(const Locator& locator)
|
||||||
|
// ********************************************************************
|
||||||
|
: Inherit(),
|
||||||
|
_withLeafCells(locator._withLeafCells),
|
||||||
|
_netOccurrenceLocator(locator._netOccurrenceLocator),
|
||||||
|
_componentLocator(locator._componentLocator),
|
||||||
|
_componentOccurrence(locator._componentOccurrence)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
HyperNet_ComponentOccurrences::Locator& HyperNet_ComponentOccurrences::Locator::operator=(const Locator& locator)
|
||||||
|
// **************************************************************************************************************
|
||||||
|
{
|
||||||
|
_withLeafCells = locator._withLeafCells;
|
||||||
|
_netOccurrenceLocator = locator._netOccurrenceLocator;
|
||||||
|
_componentLocator = locator._componentLocator;
|
||||||
|
_componentOccurrence = locator._componentOccurrence;
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
|
Occurrence HyperNet_ComponentOccurrences::Locator::getElement() const
|
||||||
|
// ******************************************************************
|
||||||
|
{
|
||||||
|
return _componentOccurrence;
|
||||||
|
}
|
||||||
|
|
||||||
|
Locator<Occurrence>* HyperNet_ComponentOccurrences::Locator::getClone() const
|
||||||
|
// **************************************************************************
|
||||||
|
{
|
||||||
|
return new Locator(*this);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool HyperNet_ComponentOccurrences::Locator::isValid() const
|
||||||
|
// *********************************************************
|
||||||
|
{
|
||||||
|
return _componentOccurrence.isValid();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void HyperNet_ComponentOccurrences::Locator::progress()
|
||||||
|
// ****************************************************
|
||||||
|
{
|
||||||
|
_componentOccurrence = Occurrence();
|
||||||
|
while ( not _componentOccurrence.isValid() ) {
|
||||||
|
if (_componentLocator.isValid()) {
|
||||||
|
Path path = _netOccurrenceLocator.getElement().getPath();
|
||||||
|
Component* component = _componentLocator.getElement();
|
||||||
|
_componentLocator.progress();
|
||||||
|
|
||||||
|
_componentOccurrence = Occurrence( component, path.getHeadPath() );
|
||||||
|
} else {
|
||||||
|
if (_netOccurrenceLocator.isValid()) {
|
||||||
|
Occurrence netOccurrence = _netOccurrenceLocator.getElement();
|
||||||
|
_netOccurrenceLocator.progress();
|
||||||
|
|
||||||
|
Net* net = static_cast<Net*>( netOccurrence.getEntity() );
|
||||||
|
if (_withLeafCells or not net->getCell()->isTerminal()) {
|
||||||
|
_componentLocator = net->getComponents().getLocator();
|
||||||
|
}
|
||||||
|
} else
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
string HyperNet_ComponentOccurrences::Locator::_getString() const
|
||||||
|
// **************************************************************
|
||||||
|
{
|
||||||
|
string s = "<" + _TName("HyperNet::ComponentOccurrences::Locator");
|
||||||
|
s += " " + getString(_netOccurrenceLocator);
|
||||||
|
s += "+" + getString(_componentLocator);
|
||||||
|
s += ">";
|
||||||
|
return s;
|
||||||
|
}
|
||||||
|
|
||||||
} // End of Hurricane namespace.
|
} // End of Hurricane namespace.
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -58,6 +58,7 @@ class HyperNet {
|
||||||
public: Occurrences getNetOccurrencesUnder(Box area, bool doExtraction = false,
|
public: Occurrences getNetOccurrencesUnder(Box area, bool doExtraction = false,
|
||||||
bool allowInterruption = false) const;
|
bool allowInterruption = false) const;
|
||||||
public: Occurrences getLeafPlugOccurrences(bool doExtraction = false , bool allowInterruption = false) const;
|
public: Occurrences getLeafPlugOccurrences(bool doExtraction = false , bool allowInterruption = false) const;
|
||||||
|
public: Occurrences getComponentOccurrences(bool doExtraction = false , bool allowInterruption = false) const;
|
||||||
|
|
||||||
// Predicates
|
// Predicates
|
||||||
// **********
|
// **********
|
||||||
|
|
|
@ -98,8 +98,6 @@ namespace {
|
||||||
}
|
}
|
||||||
|
|
||||||
for ( size_t i=0 ; i<segments.size() ; ++i ) {
|
for ( size_t i=0 ; i<segments.size() ; ++i ) {
|
||||||
//cerr << "Protecting " << segments[i] << endl;
|
|
||||||
|
|
||||||
RoutingPlane* plane = Session::getKiteEngine()->getRoutingPlaneByLayer(segments[i]->getLayer());
|
RoutingPlane* plane = Session::getKiteEngine()->getRoutingPlaneByLayer(segments[i]->getLayer());
|
||||||
unsigned int direction = plane->getDirection();
|
unsigned int direction = plane->getDirection();
|
||||||
DbU::Unit wireWidth = plane->getLayerGauge()->getWireWidth();
|
DbU::Unit wireWidth = plane->getLayerGauge()->getWireWidth();
|
||||||
|
|
Loading…
Reference in New Issue