Remove unconnected part of the nets after HFNS.
This was the reason why we, sometimes got "UNCONNECTED" errors in the VHDL PORT MAP statements. This was the remnants of the originally connected driver. * Bug: In Etesian::BufferTree, as the root driver is disconnected from all the sinks, but the top tree buffer, we may end up with unconnected signal on instances that were using it. So now, call BufferTree::rcleaupNet() to remove the Net in the Cell that where used to "transmit" the original driver. * Bug: In Etesian::BufferTree, no longer use a _isDeepNet attribute guessed from the occurrences pathes of the RoutingPad, but trust the Net::isDeepNet() method.
This commit is contained in:
parent
86d539fe5d
commit
2efae3507e
|
@ -38,6 +38,7 @@ namespace Etesian {
|
|||
using Hurricane::tab;
|
||||
using Hurricane::Warning;
|
||||
using Hurricane::Error;
|
||||
using Hurricane::DebugSession;
|
||||
using Hurricane::Path;
|
||||
using Hurricane::Transformation;
|
||||
using Hurricane::DataBase;
|
||||
|
@ -249,6 +250,7 @@ namespace Etesian {
|
|||
|
||||
void Cluster::splitNet ()
|
||||
{
|
||||
cdebug_log(123,0) << "Cluster::splitNet()" << endl;
|
||||
createOutput();
|
||||
for ( Cluster* cluster : _clusters ) {
|
||||
cluster->createInput( _driverNet );
|
||||
|
@ -291,10 +293,10 @@ namespace Etesian {
|
|||
virtual void splitNet ();
|
||||
void rpartition ();
|
||||
uint32_t build ();
|
||||
bool rcleanupNet ( Net* );
|
||||
string _getTypeName () const;
|
||||
private:
|
||||
SubNetNames _subNetNames;
|
||||
bool _isDeepNet;
|
||||
Net* _rootNet;
|
||||
RoutingPad* _rpDriver;
|
||||
vector< vector<Cluster*> > _clustersStack;
|
||||
|
@ -304,7 +306,6 @@ namespace Etesian {
|
|||
BufferTree::BufferTree ( EtesianEngine* etesian, Net* rootNet )
|
||||
: Cluster(etesian)
|
||||
, _subNetNames ()
|
||||
, _isDeepNet (true)
|
||||
, _rootNet (rootNet)
|
||||
, _rpDriver (NULL)
|
||||
, _clustersStack()
|
||||
|
@ -331,14 +332,18 @@ namespace Etesian {
|
|||
|
||||
void BufferTree::splitNet ()
|
||||
{
|
||||
cdebug_log(123,0) << "BufferTree::splitNet()" << endl;
|
||||
if (not _rpDriver)
|
||||
throw Error( "BufferTree::splitNet(): Missing driver on %s.", getString(_rootNet).c_str() );
|
||||
|
||||
Net* origDriver = _rootNet;
|
||||
|
||||
Cluster::splitNet();
|
||||
if (_isDeepNet) {
|
||||
if (_rootNet->isDeepNet()) {
|
||||
Cell* topCell = getEtesian()->getCell();
|
||||
Name topNetName = _rootNet->getName();
|
||||
Occurrence driverRpOcc = _rpDriver->getPlugOccurrence();
|
||||
origDriver = dynamic_cast<Net*>( static_cast<DeepNet*>( _rootNet )->getRootNetOccurrence().getEntity() );
|
||||
_rootNet->destroy();
|
||||
_rootNet = Net::create( topCell, topNetName );
|
||||
Net* deepDriverNet = raddTransNet( _rootNet, driverRpOcc.getPath(), AS_DRIVER );
|
||||
|
@ -346,6 +351,7 @@ namespace Etesian {
|
|||
RoutingPad::create( _rootNet, driverRpOcc, RoutingPad::BiggestArea );
|
||||
}
|
||||
createInput( _rootNet );
|
||||
rcleanupNet( origDriver );
|
||||
}
|
||||
|
||||
|
||||
|
@ -361,16 +367,15 @@ namespace Etesian {
|
|||
RoutingPad* rpPin = NULL;
|
||||
for ( RoutingPad* rp : _rootNet->getRoutingPads() ) {
|
||||
Occurrence rpOccurrence = rp->getPlugOccurrence();
|
||||
if (rpOccurrence.getPath().isEmpty())
|
||||
_isDeepNet = false;
|
||||
Pin* pin = dynamic_cast<Pin* >( rpOccurrence.getEntity() );
|
||||
if (pin) {
|
||||
if (not rpPin) {
|
||||
if (dynamic_cast<Pin* >( rpOccurrence.getEntity() )) {
|
||||
cdebug_log(123,0) << "pin: " << rp << endl;
|
||||
rpPin = rp;
|
||||
}
|
||||
}
|
||||
cdebug_log(123,0) << "Excluded: " << pin << endl;
|
||||
cdebug_log(123,0) << "Excluded second pin: " << pin << endl;
|
||||
continue;
|
||||
}
|
||||
Plug* rpPlug = dynamic_cast<Plug*>( rpOccurrence.getEntity() );
|
||||
|
@ -383,6 +388,7 @@ namespace Etesian {
|
|||
cdebug_log(123,0) << "merge: " << _clustersStack[0].back()->getSize() << " " << rp << endl;
|
||||
_clustersStack[0].back()->merge( rp );
|
||||
} else {
|
||||
cdebug_log(123,0) << "driver: " << rp << endl;
|
||||
_rpDriver = rp;
|
||||
}
|
||||
}
|
||||
|
@ -432,6 +438,8 @@ namespace Etesian {
|
|||
|
||||
uint32_t BufferTree::build ()
|
||||
{
|
||||
DebugSession::open( _rootNet, 120, 130 );
|
||||
cdebug_log(123,1) << "BufferTree::build() " << _rootNet << endl;
|
||||
uint32_t bufferCount = 0;
|
||||
rpartition();
|
||||
for ( vector<Cluster*>& clusters : _clustersStack ) {
|
||||
|
@ -440,9 +448,29 @@ namespace Etesian {
|
|||
++bufferCount;
|
||||
}
|
||||
}
|
||||
cdebug_tabw(123,-1);
|
||||
DebugSession::close();
|
||||
return bufferCount;
|
||||
}
|
||||
|
||||
|
||||
bool BufferTree::rcleanupNet ( Net* net )
|
||||
{
|
||||
if (net->getCell()->isTerminalNetlist() or net->getCell()->isTerminal())
|
||||
return false;
|
||||
vector<Plug*> plugs;
|
||||
for ( Plug* plug : net->getPlugs() ) plugs.push_back( plug );
|
||||
for ( Plug* plug : plugs ) {
|
||||
rcleanupNet( plug->getMasterNet() );
|
||||
}
|
||||
if (net->getPlugs().getFirst() == nullptr) {
|
||||
cdebug_log(123,0) << "BufferTree::rcleanupNet() " << net << " of " << net->getCell() << endl;
|
||||
net->destroy();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
string BufferTree::_getTypeName () const
|
||||
{ return "BufferTree"; }
|
||||
|
@ -484,6 +512,7 @@ namespace Etesian {
|
|||
}
|
||||
}
|
||||
|
||||
//DebugSession::open( 120, 130 );
|
||||
UpdateSession::open();
|
||||
Go::disableAutoMaterialization();
|
||||
_bufferCount = 0;
|
||||
|
@ -508,6 +537,7 @@ namespace Etesian {
|
|||
// }
|
||||
Go::enableAutoMaterialization();
|
||||
UpdateSession::close();
|
||||
//DebugSession::close();
|
||||
|
||||
stopMeasures();
|
||||
printMeasures();
|
||||
|
|
|
@ -777,6 +777,7 @@ string Net::_getString() const
|
|||
{
|
||||
string bs = Inherit::_getString();
|
||||
string ds = "\"" + getString(_name) + "\" ";
|
||||
ds += ((isDeepNet() ) ? "d" : "-");
|
||||
ds += ((_isExternal ) ? "e" : "-");
|
||||
ds += ((_isGlobal ) ? "g" : "-");
|
||||
ds += ((_isAutomatic) ? "a" : "-");
|
||||
|
|
Loading…
Reference in New Issue