Apaired segments building for symmetric routing (step 1).
* Change: In Hurricane::BaseFlags, store flags in uint64_t instead of unsigned int because we start to need more than 32 different flags in some tools. * New: In ::getString() & ::getRecord() templates, add support for std::array<>. * Change: In CRL::ToolEngine, add support for timer (time & memory measurements) displaced from Katabatic. This way all ToolEngine can use this feature. The _postCreate() method display the memory just after ToolEngine allocation. * Change: In Etesian::EtesianEngine, make use of the ToolEngine builtin timer (remove the local one). Forgot to call the base class _postCreate() and _preDestroy(). * Change: In Anabatic::AnabaticEngine, make use of the ToolEngine builtin timer (remove the local one). * New: In Anabatic, new AutoSegments_Connecteds() collection. This Collection allows a deterministic walkthough *all* the AutoSegments connected either to source or target of one AutoSegment. * New: In Anabatic::AutoContactTerminal::isEndPoint() to check if an AutoContactTerminal is the *only one* anchored on a RoutingPad, thus being a true "end point" and not a kind of feed-through. * New: In Katana::KatanaEngine, added support for symmetric nets. Created new class DataSymmetric to store symmetric information of a net (mainly the paired AutoSegments). Added KatanaEngine::runSymmetricRouter(), for now only build the DataSymmetric informations. More to come... * Change: In Katana::GraphicKatanaEngine::_runTest(), now perform symmetric information building the non-symmetric routing.
This commit is contained in:
parent
b820d22daa
commit
b99a362509
|
@ -198,7 +198,6 @@ namespace Anabatic {
|
|||
|
||||
AnabaticEngine::AnabaticEngine ( Cell* cell )
|
||||
: Super(cell)
|
||||
, _timer ()
|
||||
, _configuration (new Configuration())
|
||||
, _chipTools (cell)
|
||||
, _state (EngineCreation)
|
||||
|
@ -947,45 +946,6 @@ namespace Anabatic {
|
|||
}
|
||||
|
||||
|
||||
void AnabaticEngine::startMeasures ()
|
||||
{
|
||||
_timer.resetIncrease();
|
||||
_timer.start();
|
||||
}
|
||||
|
||||
|
||||
void AnabaticEngine::stopMeasures ()
|
||||
{ _timer.stop(); }
|
||||
|
||||
|
||||
void AnabaticEngine::suspendMeasures ()
|
||||
{ _timer.suspend(); }
|
||||
|
||||
|
||||
void AnabaticEngine::resumeMeasures ()
|
||||
{ _timer.resume(); }
|
||||
|
||||
|
||||
void AnabaticEngine::printMeasures ( const string& tag ) const
|
||||
{
|
||||
ostringstream result;
|
||||
|
||||
result << Timer::getStringTime(_timer.getCombTime())
|
||||
<< ", " << Timer::getStringMemory(_timer.getIncrease());
|
||||
cmess1 << Dots::asString( " - Done in", result.str() ) << endl;
|
||||
|
||||
result.str("");
|
||||
result << _timer.getCombTime()
|
||||
<< "s, +" << (_timer.getIncrease()>>10) << "Kb/"
|
||||
<< Timer::getStringMemory(Timer::getMemorySize());
|
||||
cmess2 << Dots::asString( " - Raw measurements", result.str() ) << endl;
|
||||
|
||||
// result.str("");
|
||||
// result << Timer::getStringMemory(Timer::getMemorySize());
|
||||
// cmess1 << Dots::asString( " - Total memory", result.str() ) << endl;
|
||||
}
|
||||
|
||||
|
||||
void AnabaticEngine::updateDensity ()
|
||||
{ for ( GCell* gcell : _gcells ) gcell->updateDensity(); }
|
||||
|
||||
|
@ -1116,6 +1076,17 @@ namespace Anabatic {
|
|||
}
|
||||
|
||||
|
||||
void AnabaticEngine::printMeasures ( const string& tag ) const
|
||||
{
|
||||
Super::printMeasures();
|
||||
|
||||
// if (not tag.empty()) {
|
||||
// addMeasure<double>( getCell(), tag+"T", getTimer().getCombTime () );
|
||||
// addMeasure<size_t>( getCell(), tag+"S", (getTimer().getMemorySize() >> 20) );
|
||||
// }
|
||||
}
|
||||
|
||||
|
||||
string AnabaticEngine::_getTypeName () const
|
||||
{ return getString(_toolName); }
|
||||
|
||||
|
|
|
@ -121,6 +121,13 @@ namespace Anabatic {
|
|||
{ }
|
||||
|
||||
|
||||
bool AutoContactTerminal::isEndPoint () const
|
||||
{
|
||||
RoutingPad* rp = dynamic_cast<RoutingPad*>( getAnchor() );
|
||||
return (rp->getBodyHook()->getSlaveHooks().getSize() == 1);
|
||||
}
|
||||
|
||||
|
||||
AutoSegment* AutoContactTerminal::getOpposite ( const AutoSegment* ) const
|
||||
{ return NULL; }
|
||||
|
||||
|
@ -141,6 +148,14 @@ namespace Anabatic {
|
|||
}
|
||||
|
||||
|
||||
RoutingPad* AutoContactTerminal::getRoutingPad () const
|
||||
{ return dynamic_cast<RoutingPad*>(getAnchor()); }
|
||||
|
||||
|
||||
AutoSegments AutoContactTerminal::getRpConnecteds () const
|
||||
{ return AutoSegments_OnRoutingPad(this); }
|
||||
|
||||
|
||||
Box AutoContactTerminal::getNativeConstraintBox () const
|
||||
{
|
||||
cdebug_log(145,1) << "AutoContactTerminal::getNativeConstraintBox()" << endl;
|
||||
|
|
|
@ -635,6 +635,13 @@ namespace Anabatic {
|
|||
}
|
||||
|
||||
|
||||
AutoSegments AutoSegment::getConnecteds ( unsigned int flags )
|
||||
{
|
||||
cdebug_log(145,0) << "AutoSegment::getConnecteds() - flags:" << flags << endl;
|
||||
return AutoSegments_Connecteds( this, flags );
|
||||
}
|
||||
|
||||
|
||||
AutoSegments AutoSegment::getPerpandiculars ()
|
||||
{ return AutoSegments_Perpandiculars( this ); }
|
||||
|
||||
|
|
|
@ -15,7 +15,8 @@
|
|||
|
||||
|
||||
#include "hurricane/Error.h"
|
||||
#include "anabatic/AutoContact.h"
|
||||
#include "hurricane/RoutingPad.h"
|
||||
#include "anabatic/AutoContactTerminal.h"
|
||||
#include "anabatic/AutoSegment.h"
|
||||
|
||||
|
||||
|
@ -27,7 +28,7 @@ namespace Anabatic {
|
|||
using Hurricane::Error;
|
||||
using Hurricane::ForEachIterator;
|
||||
using Hurricane::Hook;
|
||||
using Hurricane::Contact;
|
||||
using Hurricane::RoutingPad;
|
||||
|
||||
|
||||
// -------------------------------------------------------------------
|
||||
|
@ -111,6 +112,183 @@ namespace Anabatic {
|
|||
}
|
||||
|
||||
|
||||
// -------------------------------------------------------------------
|
||||
// Class : "Anabatic::AutoSegments_OnRoutingPad".
|
||||
|
||||
AutoSegments_OnRoutingPad::Locator::Locator ( RoutingPad* rp, const AutoContactTerminal* contact )
|
||||
: AutoSegmentHL()
|
||||
, _elements ({NULL,NULL,NULL,NULL})
|
||||
, _index (0)
|
||||
{
|
||||
if (rp) {
|
||||
for ( Component* component : rp->getSlaveComponents() ) {
|
||||
AutoSegment* segment = Session::lookup( dynamic_cast<Segment*>(component) );
|
||||
if (not segment) continue;
|
||||
|
||||
size_t offset = 2;
|
||||
if (contact and (contact->getSegment() == segment)) offset = 0;
|
||||
|
||||
if (segment->isHorizontal()) _elements[offset ] = segment;
|
||||
else _elements[offset+1] = segment;
|
||||
}
|
||||
}
|
||||
|
||||
while ( (_index < 4) and not _elements[_index] ) ++_index;
|
||||
}
|
||||
|
||||
|
||||
AutoSegmentHL* AutoSegments_OnRoutingPad::Locator::getClone () const
|
||||
{ return new Locator(*this); }
|
||||
|
||||
|
||||
AutoSegment* AutoSegments_OnRoutingPad::Locator::getElement () const
|
||||
{ return (_index < 4) ? _elements[_index] : NULL; }
|
||||
|
||||
|
||||
bool AutoSegments_OnRoutingPad::Locator::isValid () const
|
||||
{ return (_index < 4); }
|
||||
|
||||
|
||||
void AutoSegments_OnRoutingPad::Locator::progress ()
|
||||
{
|
||||
cdebug_log(145,0) << "AutoSegments_OnRoutingPad::Locator::progress()" << endl;
|
||||
++_index;
|
||||
while ( (_index < 4) and not _elements[_index] ) ++_index;
|
||||
}
|
||||
|
||||
|
||||
string AutoSegments_OnRoutingPad::Locator::_getString () const
|
||||
{
|
||||
string s = "<" + _TName("AutoSegments_OnRoutingPad::Locator")
|
||||
+ getString(_index)
|
||||
+ ">";
|
||||
return s;
|
||||
}
|
||||
|
||||
|
||||
AutoSegments_OnRoutingPad::AutoSegments_OnRoutingPad ( const AutoContact* contact )
|
||||
: AutoSegmentHC()
|
||||
, _routingPad(NULL)
|
||||
, _contact (dynamic_cast<const AutoContactTerminal*>(contact))
|
||||
{
|
||||
if (_contact)
|
||||
_routingPad = dynamic_cast<RoutingPad*>(_contact->getAnchor());
|
||||
}
|
||||
|
||||
|
||||
AutoSegmentHC* AutoSegments_OnRoutingPad::getClone () const
|
||||
{ return new AutoSegments_OnRoutingPad(*this); }
|
||||
|
||||
|
||||
AutoSegmentHL* AutoSegments_OnRoutingPad::getLocator () const
|
||||
{ return new Locator(_routingPad,_contact); }
|
||||
|
||||
|
||||
string AutoSegments_OnRoutingPad::_getString () const
|
||||
{
|
||||
string s = "<" + _TName("AutoSegments_OnRoutingPad") + " "
|
||||
+ getString(_routingPad)
|
||||
+ ">";
|
||||
return s;
|
||||
}
|
||||
|
||||
|
||||
// -------------------------------------------------------------------
|
||||
// Class : "AutoSegments_Connecteds".
|
||||
|
||||
AutoSegments_Connecteds::Locator::Locator ( AutoSegment* segment, unsigned int flags )
|
||||
: AutoSegmentHL()
|
||||
, _stack ()
|
||||
{
|
||||
cdebug_log(145,0) << "AutoSegments_Connecteds::Locator::Locator()" << endl;
|
||||
|
||||
if (flags & Flags::Source) {
|
||||
AutoContact* contact = segment->getAutoSource();
|
||||
if (contact) _stack.push( contact, segment );
|
||||
}
|
||||
|
||||
if (flags & Flags::Target) {
|
||||
AutoContact* contact = segment->getAutoTarget();
|
||||
if (contact) _stack.push( contact, segment );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
AutoSegmentHL* AutoSegments_Connecteds::Locator::getClone () const
|
||||
{ return new Locator(*this); }
|
||||
|
||||
|
||||
bool AutoSegments_Connecteds::Locator::isValid () const
|
||||
{ return not _stack.isEmpty(); }
|
||||
|
||||
|
||||
void AutoSegments_Connecteds::Locator::progress ()
|
||||
{
|
||||
cdebug_log(145,0) << "AutoSegments_Connecteds::Locator::progress()" << endl;
|
||||
|
||||
while (not _stack.isEmpty()) {
|
||||
AutoContact* sourceContact = _stack.getAutoContact ();
|
||||
AutoSegment* sourceSegment = _stack.getAutoSegment ();
|
||||
|
||||
_stack.pop ();
|
||||
|
||||
AutoContactTerminal* sourceTerminal = dynamic_cast<AutoContactTerminal*>( sourceContact );
|
||||
if (sourceTerminal) {
|
||||
for ( AutoSegment* currentSegment : sourceTerminal->getRpConnecteds() ) {
|
||||
cdebug_log(145,0) << "Looking at: " << currentSegment << endl;
|
||||
if (currentSegment == sourceSegment) continue;
|
||||
|
||||
AutoContact* targetContact = currentSegment->getAutoSource();
|
||||
if (not targetContact->isTerminal()) _stack.push( targetContact, currentSegment );
|
||||
|
||||
targetContact = currentSegment->getAutoTarget();
|
||||
if (not targetContact->isTerminal()) _stack.push( targetContact, currentSegment );
|
||||
}
|
||||
} else {
|
||||
LocatorHelper helper (sourceContact,Flags::WithPerpands);
|
||||
for ( ; helper.isValid() ; helper.progress() ) {
|
||||
AutoSegment* currentSegment = helper.getSegment();
|
||||
cdebug_log(145,0) << "Looking at: " << currentSegment << endl;
|
||||
|
||||
if (currentSegment == sourceSegment) continue;
|
||||
|
||||
AutoContact* targetContact = currentSegment->getOppositeAnchor( sourceContact );
|
||||
if (targetContact) _stack.push( targetContact, currentSegment );
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
string AutoSegments_Connecteds::Locator::_getString () const
|
||||
{
|
||||
string s = "<" + _TName("AutoSegments_Connecteds::Locator") + ">";
|
||||
return s;
|
||||
}
|
||||
|
||||
|
||||
AutoSegmentHC* AutoSegments_Connecteds::getClone () const
|
||||
{ return new AutoSegments_Connecteds(*this); }
|
||||
|
||||
|
||||
AutoSegmentHL* AutoSegments_Connecteds::getLocator () const
|
||||
{ return new Locator(_segment,_flags); }
|
||||
|
||||
|
||||
AutoSegment* AutoSegments_Connecteds::Locator::getElement () const
|
||||
{ return _stack.getAutoSegment(); }
|
||||
|
||||
|
||||
string AutoSegments_Connecteds::_getString () const
|
||||
{
|
||||
string s = "<" + _TName("AutoSegments_Connecteds") + " "
|
||||
+ getString(_segment)
|
||||
+ ">";
|
||||
return s;
|
||||
}
|
||||
|
||||
|
||||
// -------------------------------------------------------------------
|
||||
// Class : "AutoSegments_Aligneds".
|
||||
|
||||
|
|
|
@ -22,67 +22,67 @@ namespace Anabatic {
|
|||
|
||||
using std::string;
|
||||
|
||||
const unsigned int Flags::NoFlags = 0;
|
||||
const uint64_t Flags::NoFlags = 0;
|
||||
// Flags used for both objects states & functions arguments.
|
||||
const unsigned int Flags::Horizontal = (1 << 0);
|
||||
const unsigned int Flags::Vertical = (1 << 1);
|
||||
const unsigned int Flags::Source = (1 << 2);
|
||||
const unsigned int Flags::Target = (1 << 3);
|
||||
const unsigned int Flags::Invalidated = (1 << 4);
|
||||
const uint64_t Flags::Horizontal = (1 << 0);
|
||||
const uint64_t Flags::Vertical = (1 << 1);
|
||||
const uint64_t Flags::Source = (1 << 2);
|
||||
const uint64_t Flags::Target = (1 << 3);
|
||||
const uint64_t Flags::Invalidated = (1 << 4);
|
||||
// Flags for GCell objects states only.
|
||||
const unsigned int Flags::DeviceGCell = (1 << 5);
|
||||
const unsigned int Flags::HChannelGCell = (1 << 6);
|
||||
const unsigned int Flags::VChannelGCell = (1 << 7);
|
||||
const unsigned int Flags::StrutGCell = (1 << 8);
|
||||
const unsigned int Flags::MatrixGCell = (1 << 9);
|
||||
const unsigned int Flags::IoPadGCell = (1 << 10);
|
||||
const unsigned int Flags::Saturated = (1 << 11);
|
||||
const uint64_t Flags::DeviceGCell = (1 << 5);
|
||||
const uint64_t Flags::HChannelGCell = (1 << 6);
|
||||
const uint64_t Flags::VChannelGCell = (1 << 7);
|
||||
const uint64_t Flags::StrutGCell = (1 << 8);
|
||||
const uint64_t Flags::MatrixGCell = (1 << 9);
|
||||
const uint64_t Flags::IoPadGCell = (1 << 10);
|
||||
const uint64_t Flags::Saturated = (1 << 11);
|
||||
// Flags for Anabatic objects states only.
|
||||
const unsigned int Flags::DemoMode = (1 << 5);
|
||||
const unsigned int Flags::WarnOnGCellOverload = (1 << 6);
|
||||
const unsigned int Flags::DestroyGCell = (1 << 7);
|
||||
const unsigned int Flags::DestroyBaseContact = (1 << 8);
|
||||
const unsigned int Flags::DestroyBaseSegment = (1 << 9);
|
||||
const uint64_t Flags::DemoMode = (1 << 5);
|
||||
const uint64_t Flags::WarnOnGCellOverload = (1 << 6);
|
||||
const uint64_t Flags::DestroyGCell = (1 << 7);
|
||||
const uint64_t Flags::DestroyBaseContact = (1 << 8);
|
||||
const uint64_t Flags::DestroyBaseSegment = (1 << 9);
|
||||
// Flags for NetDatas objects states only.
|
||||
const unsigned int Flags::GlobalRouted = (1 << 5);
|
||||
const uint64_t Flags::GlobalRouted = (1 << 5);
|
||||
// Masks.
|
||||
const unsigned int Flags::WestSide = Horizontal|Target;
|
||||
const unsigned int Flags::EastSide = Horizontal|Source;
|
||||
const unsigned int Flags::SouthSide = Vertical |Target;
|
||||
const unsigned int Flags::NorthSide = Vertical |Source;
|
||||
const unsigned int Flags::AllSides = WestSide|EastSide|SouthSide|NorthSide ;
|
||||
const unsigned int Flags::EndsMask = Source|Target;
|
||||
const unsigned int Flags::DirectionMask = Horizontal|Vertical;
|
||||
const unsigned int Flags::DestroyMask = DestroyGCell|DestroyBaseContact|DestroyBaseSegment;
|
||||
const unsigned int Flags::GCellTypeMask = DeviceGCell|HChannelGCell|VChannelGCell|StrutGCell|MatrixGCell|IoPadGCell;
|
||||
const uint64_t Flags::WestSide = Horizontal|Target;
|
||||
const uint64_t Flags::EastSide = Horizontal|Source;
|
||||
const uint64_t Flags::SouthSide = Vertical |Target;
|
||||
const uint64_t Flags::NorthSide = Vertical |Source;
|
||||
const uint64_t Flags::AllSides = WestSide|EastSide|SouthSide|NorthSide ;
|
||||
const uint64_t Flags::EndsMask = Source|Target;
|
||||
const uint64_t Flags::DirectionMask = Horizontal|Vertical;
|
||||
const uint64_t Flags::DestroyMask = DestroyGCell|DestroyBaseContact|DestroyBaseSegment;
|
||||
const uint64_t Flags::GCellTypeMask = DeviceGCell|HChannelGCell|VChannelGCell|StrutGCell|MatrixGCell|IoPadGCell;
|
||||
// Flags for functions arguments only.
|
||||
const unsigned int Flags::Create = (1 << 5);
|
||||
const unsigned int Flags::WithPerpands = (1 << 6);
|
||||
const unsigned int Flags::WithSelf = (1 << 7);
|
||||
const unsigned int Flags::AboveLayer = (1 << 8);
|
||||
const unsigned int Flags::BelowLayer = (1 << 9);
|
||||
const unsigned int Flags::OpenSession = (1 << 10);
|
||||
const unsigned int Flags::Realignate = (1 << 11);
|
||||
const unsigned int Flags::NativeConstraints = (1 << 12);
|
||||
const unsigned int Flags::ForceMove = (1 << 13);
|
||||
const unsigned int Flags::WarnOnError = (1 << 14);
|
||||
const unsigned int Flags::Topology = (1 << 15);
|
||||
const unsigned int Flags::GlobalSegment = (1 << 16);
|
||||
const unsigned int Flags::AllowTerminal = (1 << 17);
|
||||
const unsigned int Flags::AllowLocal = (1 << 18);
|
||||
const unsigned int Flags::IgnoreContacts = (1 << 19);
|
||||
const unsigned int Flags::Propagate = (1 << 20);
|
||||
const unsigned int Flags::Superior = (1 << 21);
|
||||
const unsigned int Flags::DoglegOnLeft = (1 << 22);
|
||||
const unsigned int Flags::DoglegOnRight = (1 << 23);
|
||||
const unsigned int Flags::WithNeighbors = (1 << 24);
|
||||
const unsigned int Flags::NoCheckLayer = (1 << 25);
|
||||
const unsigned int Flags::HalfSlacken = (1 << 26);
|
||||
const unsigned int Flags::NoGCellShrink = (1 << 27);
|
||||
const unsigned int Flags::CParanoid = (1 << 28);
|
||||
const unsigned int Flags::CheckLowDensity = (1 << 29);
|
||||
const unsigned int Flags::CheckLowUpDensity = (1 << 30);
|
||||
const unsigned int Flags::NoUpdate = (1 << 31);
|
||||
const uint64_t Flags::Create = (1 << 5);
|
||||
const uint64_t Flags::WithPerpands = (1 << 6);
|
||||
const uint64_t Flags::WithSelf = (1 << 7);
|
||||
const uint64_t Flags::AboveLayer = (1 << 8);
|
||||
const uint64_t Flags::BelowLayer = (1 << 9);
|
||||
const uint64_t Flags::OpenSession = (1 << 10);
|
||||
const uint64_t Flags::Realignate = (1 << 11);
|
||||
const uint64_t Flags::NativeConstraints = (1 << 12);
|
||||
const uint64_t Flags::ForceMove = (1 << 13);
|
||||
const uint64_t Flags::WarnOnError = (1 << 14);
|
||||
const uint64_t Flags::Topology = (1 << 15);
|
||||
const uint64_t Flags::GlobalSegment = (1 << 16);
|
||||
const uint64_t Flags::AllowTerminal = (1 << 17);
|
||||
const uint64_t Flags::AllowLocal = (1 << 18);
|
||||
const uint64_t Flags::IgnoreContacts = (1 << 19);
|
||||
const uint64_t Flags::Propagate = (1 << 20);
|
||||
const uint64_t Flags::Superior = (1 << 21);
|
||||
const uint64_t Flags::DoglegOnLeft = (1 << 22);
|
||||
const uint64_t Flags::DoglegOnRight = (1 << 23);
|
||||
const uint64_t Flags::WithNeighbors = (1 << 24);
|
||||
const uint64_t Flags::NoCheckLayer = (1 << 25);
|
||||
const uint64_t Flags::HalfSlacken = (1 << 26);
|
||||
const uint64_t Flags::NoGCellShrink = (1 << 27);
|
||||
const uint64_t Flags::CParanoid = (1 << 28);
|
||||
const uint64_t Flags::CheckLowDensity = (1 << 29);
|
||||
const uint64_t Flags::CheckLowUpDensity = (1 << 30);
|
||||
const uint64_t Flags::NoUpdate = (1 << 31);
|
||||
|
||||
|
||||
Flags::~Flags ()
|
||||
|
|
|
@ -22,7 +22,6 @@
|
|||
#include <vector>
|
||||
#include <set>
|
||||
|
||||
#include "hurricane/Timer.h"
|
||||
#include "hurricane/NetRoutingProperty.h"
|
||||
namespace Hurricane {
|
||||
class Instance;
|
||||
|
@ -42,7 +41,6 @@ namespace Anabatic {
|
|||
|
||||
using std::string;
|
||||
using std::vector;
|
||||
using Hurricane::Timer;
|
||||
using Hurricane::Name;
|
||||
using Hurricane::Record;
|
||||
using Hurricane::Interval;
|
||||
|
@ -271,16 +269,11 @@ namespace Anabatic {
|
|||
void _destroyAutoSegments ();
|
||||
void _check ( Net* net ) const;
|
||||
bool _check ( const char* message ) const;
|
||||
void printMeasures ( const string& tag ) const;
|
||||
// Misc. functions.
|
||||
inline const Flags& flags () const;
|
||||
inline Flags& flags ();
|
||||
void reset ();
|
||||
inline const Timer& getTimer () const;
|
||||
void startMeasures ();
|
||||
void stopMeasures ();
|
||||
void suspendMeasures ();
|
||||
void resumeMeasures ();
|
||||
void printMeasures ( const string& ) const;
|
||||
inline void _add ( GCell* );
|
||||
inline void _remove ( GCell* );
|
||||
inline void _updateLookup ( GCell* );
|
||||
|
@ -300,7 +293,6 @@ namespace Anabatic {
|
|||
AnabaticEngine& operator= ( const AnabaticEngine& );
|
||||
private:
|
||||
static Name _toolName;
|
||||
Timer _timer;
|
||||
Configuration* _configuration;
|
||||
ChipTools _chipTools;
|
||||
EngineState _state;
|
||||
|
@ -372,7 +364,6 @@ namespace Anabatic {
|
|||
}
|
||||
}
|
||||
|
||||
inline const Timer& AnabaticEngine::getTimer () const { return _timer; }
|
||||
inline int AnabaticEngine::getStamp () const { return _stamp; }
|
||||
inline int AnabaticEngine::incStamp () { return ++_stamp; }
|
||||
|
||||
|
|
|
@ -18,10 +18,17 @@
|
|||
#define ANABATIC_AUTOCONTACT_TERMINAL_H
|
||||
|
||||
#include "anabatic/AutoContact.h"
|
||||
#include "anabatic/AutoSegments.h"
|
||||
|
||||
namespace Hurricane {
|
||||
class RoutingPad;
|
||||
}
|
||||
|
||||
|
||||
namespace Anabatic {
|
||||
|
||||
using Hurricane::RoutingPad;
|
||||
|
||||
|
||||
// -------------------------------------------------------------------
|
||||
// Class : "Anabatic::AutoContactTerminal".
|
||||
|
@ -52,11 +59,14 @@ namespace Anabatic {
|
|||
virtual ~AutoContactTerminal ();
|
||||
virtual void _invalidate ( unsigned int flags );
|
||||
public:
|
||||
bool isEndPoint () const;
|
||||
virtual Box getNativeConstraintBox () const;
|
||||
RoutingPad* getRoutingPad () const;
|
||||
inline AutoSegment* getSegment () const;
|
||||
virtual AutoSegment* getSegment ( unsigned int ) const;
|
||||
virtual AutoSegment* getOpposite ( const AutoSegment* ) const;
|
||||
virtual AutoSegment* getPerpandicular ( const AutoSegment* ) const;
|
||||
AutoSegments getRpConnecteds () const;
|
||||
virtual void updateGeometry ();
|
||||
virtual void updateTopology ();
|
||||
virtual void forceOnGrid ( Point );
|
||||
|
|
|
@ -311,6 +311,7 @@ namespace Anabatic {
|
|||
AutoSegments getCachedOnSourceContact ( unsigned int direction );
|
||||
AutoSegments getCachedOnTargetContact ( unsigned int direction );
|
||||
AutoSegments getAligneds ( unsigned int flags=Flags::NoFlags );
|
||||
AutoSegments getConnecteds ( unsigned int flags=Flags::NoFlags );
|
||||
AutoSegments getPerpandiculars ();
|
||||
size_t getAlignedContacts ( map<AutoContact*,int>& ) const ;
|
||||
// Observers.
|
||||
|
@ -387,6 +388,7 @@ namespace Anabatic {
|
|||
|
||||
// Static Utilities.
|
||||
public:
|
||||
static inline unsigned int swapSourceTargetFlags ( AutoSegment* );
|
||||
static inline bool areAlignedsAndDiffLayer ( AutoSegment*, AutoSegment* );
|
||||
static bool isTopologicalBound ( AutoSegment* seed, unsigned int flags );
|
||||
static inline bool arePerpandiculars ( AutoSegment* a, AutoSegment* b );
|
||||
|
@ -520,6 +522,30 @@ namespace Anabatic {
|
|||
inline unsigned long AutoSegment::getMaxId ()
|
||||
{ return _maxId; }
|
||||
|
||||
inline unsigned int AutoSegment::swapSourceTargetFlags ( AutoSegment* segment )
|
||||
{
|
||||
unsigned int segFlags = segment->getFlags();
|
||||
unsigned int swapFlags = segment->getFlags() & ~(SegSourceTop |SegTargetTop
|
||||
|SegSourceBottom |SegTargetBottom
|
||||
|SegSourceTerminal |SegTargetTerminal
|
||||
|SegNotSourceAligned |SegNotTargetAligned
|
||||
|SegInvalidatedSource|SegInvalidatedTarget
|
||||
);
|
||||
|
||||
swapFlags |= (segFlags & SegSourceTop ) ? SegTargetTop : SegNoFlags;
|
||||
swapFlags |= (segFlags & SegSourceBottom ) ? SegTargetBottom : SegNoFlags;
|
||||
swapFlags |= (segFlags & SegSourceTerminal ) ? SegTargetTerminal : SegNoFlags;
|
||||
swapFlags |= (segFlags & SegNotSourceAligned ) ? SegNotTargetAligned : SegNoFlags;
|
||||
swapFlags |= (segFlags & SegInvalidatedSource) ? SegInvalidatedTarget : SegNoFlags;
|
||||
|
||||
swapFlags |= (segFlags & SegTargetTop ) ? SegSourceTop : SegNoFlags;
|
||||
swapFlags |= (segFlags & SegTargetBottom ) ? SegSourceBottom : SegNoFlags;
|
||||
swapFlags |= (segFlags & SegTargetTerminal ) ? SegSourceTerminal : SegNoFlags;
|
||||
swapFlags |= (segFlags & SegNotTargetAligned ) ? SegNotSourceAligned : SegNoFlags;
|
||||
swapFlags |= (segFlags & SegInvalidatedTarget) ? SegInvalidatedSource : SegNoFlags;
|
||||
return swapFlags;
|
||||
}
|
||||
|
||||
inline bool AutoSegment::areAlignedsAndDiffLayer ( AutoSegment* s1, AutoSegment* s2 )
|
||||
{ return s1 and s2
|
||||
and (s1->isHorizontal() == s2->isHorizontal())
|
||||
|
|
|
@ -20,6 +20,7 @@
|
|||
#include <string>
|
||||
#include <list>
|
||||
#include <vector>
|
||||
#include <array>
|
||||
#include <map>
|
||||
#include "hurricane/Collection.h"
|
||||
#include "hurricane/DbU.h"
|
||||
|
@ -30,6 +31,7 @@ namespace Hurricane {
|
|||
class Component;
|
||||
class Contact;
|
||||
class Segment;
|
||||
class RoutingPad;
|
||||
class Net;
|
||||
}
|
||||
|
||||
|
@ -49,6 +51,7 @@ namespace Anabatic {
|
|||
using Hurricane::Component;
|
||||
using Hurricane::Contact;
|
||||
using Hurricane::Segment;
|
||||
using Hurricane::RoutingPad;
|
||||
using Hurricane::Net;
|
||||
using Hurricane::Filter;
|
||||
using Hurricane::Locator;
|
||||
|
@ -59,6 +62,7 @@ namespace Anabatic {
|
|||
|
||||
class LocatorHelper;
|
||||
class AutoContact;
|
||||
class AutoContactTerminal;
|
||||
class AutoSegment;
|
||||
class GCell;
|
||||
|
||||
|
@ -155,6 +159,56 @@ namespace Anabatic {
|
|||
{ }
|
||||
|
||||
|
||||
// -------------------------------------------------------------------
|
||||
// Class : "Anabatic::AutoSegments_OnRoutingPad".
|
||||
|
||||
class AutoSegments_OnRoutingPad : public AutoSegmentHC {
|
||||
|
||||
public:
|
||||
// Sub-Class: Locator.
|
||||
class Locator : public AutoSegmentHL {
|
||||
public:
|
||||
Locator ( RoutingPad* rp, const AutoContactTerminal* contact );
|
||||
inline Locator ( const Locator& );
|
||||
virtual AutoSegment* getElement () const;
|
||||
virtual AutoSegmentHL* getClone () const;
|
||||
virtual bool isValid () const;
|
||||
virtual void progress ();
|
||||
virtual string _getString () const;
|
||||
protected:
|
||||
std::array<AutoSegment*,4> _elements;
|
||||
size_t _index;
|
||||
};
|
||||
|
||||
public:
|
||||
// AutoSegments_OnRoutingPad Methods.
|
||||
AutoSegments_OnRoutingPad ( const AutoContact* contact );
|
||||
inline AutoSegments_OnRoutingPad ( const AutoSegments_OnRoutingPad& );
|
||||
virtual AutoSegmentHC* getClone () const;
|
||||
virtual AutoSegmentHL* getLocator () const;
|
||||
virtual string _getString () const;
|
||||
|
||||
protected:
|
||||
// AutoSegments_OnRoutingPad Attributes.
|
||||
RoutingPad* _routingPad;
|
||||
const AutoContactTerminal* _contact;
|
||||
};
|
||||
|
||||
|
||||
inline AutoSegments_OnRoutingPad::Locator::Locator ( const Locator &locator )
|
||||
: AutoSegmentHL()
|
||||
, _elements(locator._elements)
|
||||
, _index (locator._index)
|
||||
{ }
|
||||
|
||||
|
||||
inline AutoSegments_OnRoutingPad::AutoSegments_OnRoutingPad ( const AutoSegments_OnRoutingPad& segments )
|
||||
: AutoSegmentHC()
|
||||
, _routingPad(segments._routingPad)
|
||||
, _contact (segments._contact)
|
||||
{ }
|
||||
|
||||
|
||||
// -------------------------------------------------------------------
|
||||
// Class : "AutoSegments_Aligneds".
|
||||
|
||||
|
@ -214,6 +268,61 @@ namespace Anabatic {
|
|||
{ }
|
||||
|
||||
|
||||
// -------------------------------------------------------------------
|
||||
// Class : "AutoSegments_Connecteds".
|
||||
|
||||
class AutoSegments_Connecteds : public AutoSegmentHC {
|
||||
|
||||
public:
|
||||
// Sub-Class: Locator.
|
||||
class Locator : public AutoSegmentHL {
|
||||
public:
|
||||
inline Locator ( AutoSegment* segment, unsigned int flags );
|
||||
inline Locator ( const Locator &locator );
|
||||
virtual AutoSegment* getElement () const;
|
||||
virtual AutoSegmentHL* getClone () const;
|
||||
virtual bool isValid () const;
|
||||
virtual void progress ();
|
||||
virtual string _getString () const;
|
||||
protected:
|
||||
AutoSegmentStack _stack;
|
||||
};
|
||||
|
||||
public:
|
||||
// AutoSegments_Connecteds Methods.
|
||||
AutoSegments_Connecteds ( AutoSegment*, unsigned int flags );
|
||||
AutoSegments_Connecteds ( const AutoSegments_Connecteds& );
|
||||
virtual AutoSegmentHC* getClone () const;
|
||||
virtual AutoSegmentHL* getLocator () const;
|
||||
virtual string _getString () const;
|
||||
|
||||
protected:
|
||||
// AutoSegments_Connecteds Attributes.
|
||||
unsigned int _flags;
|
||||
AutoSegment* _segment;
|
||||
};
|
||||
|
||||
|
||||
inline AutoSegments_Connecteds::Locator::Locator ( const Locator &locator )
|
||||
: AutoSegmentHL()
|
||||
, _stack (locator._stack)
|
||||
{ }
|
||||
|
||||
|
||||
inline AutoSegments_Connecteds::AutoSegments_Connecteds ( AutoSegment* segment, unsigned int flags )
|
||||
: AutoSegmentHC()
|
||||
, _flags (flags)
|
||||
, _segment(segment)
|
||||
{ }
|
||||
|
||||
|
||||
inline AutoSegments_Connecteds::AutoSegments_Connecteds ( const AutoSegments_Connecteds& autosegments )
|
||||
: AutoSegmentHC()
|
||||
, _flags (autosegments._flags)
|
||||
, _segment(autosegments._segment)
|
||||
{ }
|
||||
|
||||
|
||||
// -------------------------------------------------------------------
|
||||
// Class : "AutoSegments_Perpandiculars".
|
||||
|
||||
|
|
|
@ -24,69 +24,69 @@ namespace Anabatic {
|
|||
|
||||
class Flags : public Hurricane::BaseFlags {
|
||||
public:
|
||||
static const unsigned int NoFlags ; // = 0;
|
||||
static const uint64_t NoFlags ; // = 0;
|
||||
// Flags used for both objects states & functions arguments.
|
||||
static const unsigned int Horizontal ; // = (1 << 0);
|
||||
static const unsigned int Vertical ; // = (1 << 1);
|
||||
static const unsigned int Source ; // = (1 << 2);
|
||||
static const unsigned int Target ; // = (1 << 3);
|
||||
static const unsigned int Invalidated ; // = (1 << 4);
|
||||
static const uint64_t Horizontal ; // = (1 << 0);
|
||||
static const uint64_t Vertical ; // = (1 << 1);
|
||||
static const uint64_t Source ; // = (1 << 2);
|
||||
static const uint64_t Target ; // = (1 << 3);
|
||||
static const uint64_t Invalidated ; // = (1 << 4);
|
||||
// Flags for GCell objects states only.
|
||||
static const unsigned int DeviceGCell ; // = (1 << 5);
|
||||
static const unsigned int HChannelGCell ; // = (1 << 6);
|
||||
static const unsigned int VChannelGCell ; // = (1 << 7);
|
||||
static const unsigned int StrutGCell ; // = (1 << 8);
|
||||
static const unsigned int MatrixGCell ; // = (1 << 9);
|
||||
static const unsigned int IoPadGCell ; // = (1 << 10);
|
||||
static const unsigned int Saturated ; // = (1 << 11);
|
||||
static const uint64_t DeviceGCell ; // = (1 << 5);
|
||||
static const uint64_t HChannelGCell ; // = (1 << 6);
|
||||
static const uint64_t VChannelGCell ; // = (1 << 7);
|
||||
static const uint64_t StrutGCell ; // = (1 << 8);
|
||||
static const uint64_t MatrixGCell ; // = (1 << 9);
|
||||
static const uint64_t IoPadGCell ; // = (1 << 10);
|
||||
static const uint64_t Saturated ; // = (1 << 11);
|
||||
// Flags for Anabatic objects states only.
|
||||
static const unsigned int DemoMode ; // = (1 << 5);
|
||||
static const unsigned int WarnOnGCellOverload ; // = (1 << 6);
|
||||
static const unsigned int DestroyGCell ; // = (1 << 7);
|
||||
static const unsigned int DestroyBaseContact ; // = (1 << 8);
|
||||
static const unsigned int DestroyBaseSegment ; // = (1 << 9);
|
||||
static const uint64_t DemoMode ; // = (1 << 5);
|
||||
static const uint64_t WarnOnGCellOverload ; // = (1 << 6);
|
||||
static const uint64_t DestroyGCell ; // = (1 << 7);
|
||||
static const uint64_t DestroyBaseContact ; // = (1 << 8);
|
||||
static const uint64_t DestroyBaseSegment ; // = (1 << 9);
|
||||
// Flags for NetDatas objects states only.
|
||||
static const unsigned int GlobalRouted ; // = (1 << 5);
|
||||
static const uint64_t GlobalRouted ; // = (1 << 5);
|
||||
// Masks.
|
||||
static const unsigned int WestSide ; // = Horizontal|Target;
|
||||
static const unsigned int EastSide ; // = Horizontal|Source;
|
||||
static const unsigned int SouthSide ; // = Vertical |Target;
|
||||
static const unsigned int NorthSide ; // = Vertical |Source;
|
||||
static const unsigned int AllSides ; // = WestSide|EastSide|SouthSide|NorthSide ;
|
||||
static const unsigned int EndsMask ; // = Source|Target;
|
||||
static const unsigned int DirectionMask ; // = Horizontal|Vertical;
|
||||
static const unsigned int DestroyMask ; // = DestroyGCell|DestroyBaseContact|DestroyBaseSegment;
|
||||
static const unsigned int GCellTypeMask ; // = DeviceGCell|HChannelGCell|VChannelGCell|StrutGCell|MatrixGCell|IoPadGCell;
|
||||
static const uint64_t WestSide ; // = Horizontal|Target;
|
||||
static const uint64_t EastSide ; // = Horizontal|Source;
|
||||
static const uint64_t SouthSide ; // = Vertical |Target;
|
||||
static const uint64_t NorthSide ; // = Vertical |Source;
|
||||
static const uint64_t AllSides ; // = WestSide|EastSide|SouthSide|NorthSide ;
|
||||
static const uint64_t EndsMask ; // = Source|Target;
|
||||
static const uint64_t DirectionMask ; // = Horizontal|Vertical;
|
||||
static const uint64_t DestroyMask ; // = DestroyGCell|DestroyBaseContact|DestroyBaseSegment;
|
||||
static const uint64_t GCellTypeMask ; // = DeviceGCell|HChannelGCell|VChannelGCell|StrutGCell|MatrixGCell|IoPadGCell;
|
||||
// Flags for functions arguments only.
|
||||
static const unsigned int Create ; // = (1 << 5);
|
||||
static const unsigned int WithPerpands ;
|
||||
static const unsigned int WithSelf ;
|
||||
static const unsigned int AboveLayer ;
|
||||
static const unsigned int BelowLayer ;
|
||||
static const unsigned int OpenSession ;
|
||||
static const unsigned int Realignate ;
|
||||
static const unsigned int NativeConstraints ;
|
||||
static const unsigned int ForceMove ;
|
||||
static const unsigned int WarnOnError ;
|
||||
static const unsigned int Topology ;
|
||||
static const unsigned int GlobalSegment ;
|
||||
static const unsigned int AllowTerminal ;
|
||||
static const unsigned int AllowLocal ;
|
||||
static const unsigned int IgnoreContacts ;
|
||||
static const unsigned int Propagate ;
|
||||
static const unsigned int Superior ;
|
||||
static const unsigned int DoglegOnLeft ;
|
||||
static const unsigned int DoglegOnRight ;
|
||||
static const unsigned int WithNeighbors ;
|
||||
static const unsigned int NoCheckLayer ;
|
||||
static const unsigned int HalfSlacken ;
|
||||
static const unsigned int NoGCellShrink ;
|
||||
static const unsigned int CParanoid ;
|
||||
static const unsigned int CheckLowDensity ;
|
||||
static const unsigned int CheckLowUpDensity ;
|
||||
static const unsigned int NoUpdate ;
|
||||
static const uint64_t Create ; // = (1 << 5);
|
||||
static const uint64_t WithPerpands ;
|
||||
static const uint64_t WithSelf ;
|
||||
static const uint64_t AboveLayer ;
|
||||
static const uint64_t BelowLayer ;
|
||||
static const uint64_t OpenSession ;
|
||||
static const uint64_t Realignate ;
|
||||
static const uint64_t NativeConstraints ;
|
||||
static const uint64_t ForceMove ;
|
||||
static const uint64_t WarnOnError ;
|
||||
static const uint64_t Topology ;
|
||||
static const uint64_t GlobalSegment ;
|
||||
static const uint64_t AllowTerminal ;
|
||||
static const uint64_t AllowLocal ;
|
||||
static const uint64_t IgnoreContacts ;
|
||||
static const uint64_t Propagate ;
|
||||
static const uint64_t Superior ;
|
||||
static const uint64_t DoglegOnLeft ;
|
||||
static const uint64_t DoglegOnRight ;
|
||||
static const uint64_t WithNeighbors ;
|
||||
static const uint64_t NoCheckLayer ;
|
||||
static const uint64_t HalfSlacken ;
|
||||
static const uint64_t NoGCellShrink ;
|
||||
static const uint64_t CParanoid ;
|
||||
static const uint64_t CheckLowDensity ;
|
||||
static const uint64_t CheckLowUpDensity ;
|
||||
static const uint64_t NoUpdate ;
|
||||
public:
|
||||
inline Flags ( unsigned int flags = NoFlags );
|
||||
inline Flags ( uint64_t flags = NoFlags );
|
||||
inline Flags ( BaseFlags );
|
||||
virtual ~Flags ();
|
||||
virtual std::string _getTypeName () const;
|
||||
|
@ -94,8 +94,8 @@ namespace Anabatic {
|
|||
};
|
||||
|
||||
|
||||
Flags::Flags ( unsigned int flags ) : BaseFlags(flags) { }
|
||||
Flags::Flags ( BaseFlags base ) : BaseFlags(base) { }
|
||||
Flags::Flags ( uint64_t flags ) : BaseFlags(flags) { }
|
||||
Flags::Flags ( BaseFlags base ) : BaseFlags(base) { }
|
||||
|
||||
|
||||
enum EngineState { EngineCreation = 1
|
||||
|
|
|
@ -28,6 +28,7 @@ namespace {
|
|||
using std::cerr;
|
||||
using std::endl;
|
||||
using std::string;
|
||||
using std::ostringstream;
|
||||
using std::set;
|
||||
using std::vector;
|
||||
using Hurricane::ForEachIterator;
|
||||
|
@ -191,30 +192,37 @@ namespace CRL {
|
|||
|
||||
|
||||
ToolEngine::ToolEngine ( Cell* cell )
|
||||
: DBo()
|
||||
: Super()
|
||||
, _cell (cell)
|
||||
, _placementModificationFlag(0)
|
||||
, _routingModificationFlag (0)
|
||||
, _inRelationDestroy (false)
|
||||
{}
|
||||
, _timer ()
|
||||
{ }
|
||||
|
||||
|
||||
void ToolEngine::_postCreate ()
|
||||
{
|
||||
DBo::_postCreate();
|
||||
if ( !_cell )
|
||||
throw Error ( "Can't create " + _TName("ToolEngine") + " : empty _cell" );
|
||||
Super::_postCreate();
|
||||
if (not _cell)
|
||||
throw Error( "Can't create " + _TName("ToolEngine") + " : empty _cell" );
|
||||
|
||||
ToolEnginesRelation* enginesRelation = ToolEnginesRelation::getToolEnginesRelation(_cell);
|
||||
if ( !enginesRelation )
|
||||
enginesRelation = ToolEnginesRelation::create ( _cell );
|
||||
if (not enginesRelation)
|
||||
enginesRelation = ToolEnginesRelation::create( _cell );
|
||||
else
|
||||
forEach ( ToolEngine*, itool, enginesRelation->getSlaveOwners().getSubSet<ToolEngine*>() ) {
|
||||
if (itool->getName() == getName())
|
||||
throw Error ( "Can't create " + _TName("ToolEngine") + " : already exists !!" );
|
||||
for ( ToolEngine* tool : enginesRelation->getSlaveOwners().getSubSet<ToolEngine*>() ) {
|
||||
if (tool->getName() == getName())
|
||||
throw Error( "Can't create " + _TName("ToolEngine") + " : already exists !!" );
|
||||
}
|
||||
put ( enginesRelation );
|
||||
|
||||
put( enginesRelation );
|
||||
|
||||
cmess1 << " o Creating ToolEngine<" << getName() << "> for Cell <"
|
||||
<< _cell->getName() << ">" << endl;
|
||||
|
||||
cmess1 << Dots::asString( " - Initial memory"
|
||||
, Timer::getStringMemory(Timer::getMemorySize()) ) << endl;
|
||||
}
|
||||
|
||||
|
||||
|
@ -226,7 +234,7 @@ namespace CRL {
|
|||
throw Error( "Abnormal state: no ToolEnginesRelation on %s", getString(_cell).c_str() );
|
||||
remove( relation );
|
||||
}
|
||||
DBo::_preDestroy();
|
||||
Super::_preDestroy();
|
||||
_cell->notify( Cell::Flags::CellChanged );
|
||||
}
|
||||
|
||||
|
@ -249,7 +257,7 @@ namespace CRL {
|
|||
|
||||
string ToolEngine::_getString () const
|
||||
{
|
||||
string s = DBo::_getString();
|
||||
string s = Super::_getString();
|
||||
s.insert(s.length() - 1, " " + getString(_cell->getName()));
|
||||
return s;
|
||||
}
|
||||
|
@ -257,7 +265,7 @@ namespace CRL {
|
|||
|
||||
Record* ToolEngine::_getRecord () const
|
||||
{
|
||||
Record* record = DBo::_getRecord();
|
||||
Record* record = Super::_getRecord();
|
||||
if ( record ) {
|
||||
record->add ( getSlot ( "Cell" , _cell ) );
|
||||
record->add ( getSlot ( "Name" , getName() ) );
|
||||
|
@ -348,4 +356,43 @@ namespace CRL {
|
|||
}
|
||||
|
||||
|
||||
void ToolEngine::startMeasures ()
|
||||
{
|
||||
_timer.resetIncrease();
|
||||
_timer.start();
|
||||
}
|
||||
|
||||
|
||||
void ToolEngine::stopMeasures ()
|
||||
{ _timer.stop(); }
|
||||
|
||||
|
||||
void ToolEngine::suspendMeasures ()
|
||||
{ _timer.suspend(); }
|
||||
|
||||
|
||||
void ToolEngine::resumeMeasures ()
|
||||
{ _timer.resume(); }
|
||||
|
||||
|
||||
void ToolEngine::printMeasures () const
|
||||
{
|
||||
ostringstream result;
|
||||
|
||||
result << Timer::getStringTime(_timer.getCombTime())
|
||||
<< ", " << Timer::getStringMemory(_timer.getIncrease());
|
||||
cmess1 << Dots::asString( " - Done in", result.str() ) << endl;
|
||||
|
||||
result.str("");
|
||||
result << _timer.getCombTime()
|
||||
<< "s, +" << (_timer.getIncrease()>>10) << "Kb/"
|
||||
<< Timer::getStringMemory(Timer::getMemorySize());
|
||||
cmess2 << Dots::asString( " - Raw measurements", result.str() ) << endl;
|
||||
|
||||
// result.str("");
|
||||
// result << Timer::getStringMemory(Timer::getMemorySize());
|
||||
// cmess1 << Dots::asString( " - Total memory", result.str() ) << endl;
|
||||
}
|
||||
|
||||
|
||||
} // End of CRL namespace.
|
||||
|
|
|
@ -21,6 +21,7 @@
|
|||
#include <string>
|
||||
#include <vector>
|
||||
#include "hurricane/Commons.h"
|
||||
#include "hurricane/Timer.h"
|
||||
#include "hurricane/DBo.h"
|
||||
#include "hurricane/Slot.h"
|
||||
|
||||
|
@ -36,6 +37,7 @@ namespace CRL {
|
|||
|
||||
using std::string;
|
||||
using std::vector;
|
||||
using Hurricane::Timer;
|
||||
using Hurricane::Record;
|
||||
using Hurricane::Name;
|
||||
using Hurricane::DBo;
|
||||
|
@ -47,36 +49,45 @@ namespace CRL {
|
|||
|
||||
class ToolEngine : public DBo {
|
||||
public:
|
||||
static ToolEngines get ( const Cell* cell );
|
||||
static ToolEngine* get ( const Cell* cell, const Name& name );
|
||||
static void destroyAll ();
|
||||
static bool inDestroyAll ();
|
||||
typedef DBo Super;
|
||||
public:
|
||||
virtual const Name& getName () const = 0;
|
||||
inline Cell* getCell () const;
|
||||
bool placementModificationFlagHasChanged ();
|
||||
bool routingModificationFlagHasChanged ();
|
||||
inline void setInRelationDestroy ( bool );
|
||||
virtual string _getTypeName () const;
|
||||
virtual string _getString () const;
|
||||
virtual Record* _getRecord () const;
|
||||
static ToolEngines get ( const Cell* cell );
|
||||
static ToolEngine* get ( const Cell* cell, const Name& name );
|
||||
static void destroyAll ();
|
||||
static bool inDestroyAll ();
|
||||
public:
|
||||
virtual const Name& getName () const = 0;
|
||||
inline Cell* getCell () const;
|
||||
bool placementModificationFlagHasChanged ();
|
||||
bool routingModificationFlagHasChanged ();
|
||||
inline void setInRelationDestroy ( bool );
|
||||
inline const Timer& getTimer () const;
|
||||
void startMeasures ();
|
||||
void stopMeasures ();
|
||||
void suspendMeasures ();
|
||||
void resumeMeasures ();
|
||||
void printMeasures () const;
|
||||
virtual string _getTypeName () const;
|
||||
virtual string _getString () const;
|
||||
virtual Record* _getRecord () const;
|
||||
private:
|
||||
static bool _inDestroyAll;
|
||||
static bool _inDestroyAll;
|
||||
protected:
|
||||
Cell* _cell;
|
||||
Cell* _cell;
|
||||
private:
|
||||
unsigned int _placementModificationFlag;
|
||||
unsigned int _routingModificationFlag;
|
||||
bool _inRelationDestroy;
|
||||
unsigned int _placementModificationFlag;
|
||||
unsigned int _routingModificationFlag;
|
||||
bool _inRelationDestroy;
|
||||
Timer _timer;
|
||||
protected:
|
||||
ToolEngine ( Cell* cell );
|
||||
virtual void _postCreate ();
|
||||
virtual void _preDestroy ();
|
||||
protected:
|
||||
void grabPlacementModificationFlag ();
|
||||
void getPlacementModificationFlag ();
|
||||
void grabRoutingModificationFlag ();
|
||||
void getRoutingModificationFlag ();
|
||||
ToolEngine ( Cell* cell );
|
||||
virtual void _postCreate ();
|
||||
virtual void _preDestroy ();
|
||||
protected:
|
||||
void grabPlacementModificationFlag ();
|
||||
void getPlacementModificationFlag ();
|
||||
void grabRoutingModificationFlag ();
|
||||
void getRoutingModificationFlag ();
|
||||
};
|
||||
|
||||
|
||||
|
@ -84,8 +95,9 @@ namespace CRL {
|
|||
// Inline Functions.
|
||||
|
||||
|
||||
inline Cell* ToolEngine::getCell () const { return _cell; }
|
||||
inline void ToolEngine::setInRelationDestroy ( bool state ) { _inRelationDestroy = state; }
|
||||
inline Cell* ToolEngine::getCell () const { return _cell; }
|
||||
inline void ToolEngine::setInRelationDestroy ( bool state ) { _inRelationDestroy = state; }
|
||||
inline const Timer& ToolEngine::getTimer () const { return _timer; }
|
||||
|
||||
|
||||
} // CRL namespace.
|
||||
|
|
|
@ -244,11 +244,10 @@ namespace Etesian {
|
|||
|
||||
|
||||
EtesianEngine::EtesianEngine ( Cell* cell )
|
||||
: ToolEngine (cell)
|
||||
: Super (cell)
|
||||
, _configuration(new Configuration())
|
||||
, _placed (false)
|
||||
, _flatDesign (false)
|
||||
, _timer ()
|
||||
, _surface ()
|
||||
, _circuit ()
|
||||
, _placementLB ()
|
||||
|
@ -263,6 +262,8 @@ namespace Etesian {
|
|||
|
||||
void EtesianEngine::_postCreate ()
|
||||
{
|
||||
Super::_postCreate();
|
||||
|
||||
// Ugly: Name based detection of ISPD benchmarks.
|
||||
if (getString(getCell()->getName()).substr(0,7) == "bigblue") {
|
||||
cmess2 << " o ISPD benchmark <" << getCell()->getName()
|
||||
|
@ -292,6 +293,8 @@ namespace Etesian {
|
|||
cmess1 << " o Deleting ToolEngine<" << getName() << "> from Cell <"
|
||||
<< getCell()->getName() << ">" << endl;
|
||||
|
||||
Super::_preDestroy();
|
||||
|
||||
cdebug.log(129,-1);
|
||||
}
|
||||
|
||||
|
@ -314,33 +317,6 @@ namespace Etesian {
|
|||
{ return _configuration; }
|
||||
|
||||
|
||||
void EtesianEngine::startMeasures ()
|
||||
{
|
||||
_timer.resetIncrease();
|
||||
_timer.start();
|
||||
}
|
||||
|
||||
|
||||
void EtesianEngine::stopMeasures ()
|
||||
{ _timer.stop(); }
|
||||
|
||||
|
||||
void EtesianEngine::printMeasures ( string tag ) const
|
||||
{
|
||||
ostringstream result;
|
||||
|
||||
result << Timer::getStringTime(_timer.getCombTime()) << ", "
|
||||
<< Timer::getStringMemory(_timer.getIncrease());
|
||||
cmess1 << ::Dots::asString( " - Done in", result.str() ) << endl;
|
||||
|
||||
result.str("");
|
||||
result << _timer.getCombTime()
|
||||
<< "s, +" << (_timer.getIncrease()>>10) << "Kb/"
|
||||
<< (_timer.getMemorySize()>>10) << "Kb";
|
||||
cmess2 << ::Dots::asString( " - Raw measurements", result.str() ) << endl;
|
||||
}
|
||||
|
||||
|
||||
void EtesianEngine::setDefaultAb ()
|
||||
{
|
||||
double spaceMargin = getSpaceMargin();
|
||||
|
@ -925,7 +901,7 @@ namespace Etesian {
|
|||
|
||||
cmess1 << " o Placement finished." << endl;
|
||||
stopMeasures();
|
||||
printMeasures( "total" );
|
||||
printMeasures();
|
||||
cmess1 << ::Dots::asString
|
||||
( " - HPWL", DbU::getValueString( (DbU::Unit)coloquinte::gp::get_HPWL_wirelength(_circuit,_placementUB )*getPitch() ) ) << endl;
|
||||
cmess1 << ::Dots::asString
|
||||
|
@ -954,10 +930,7 @@ namespace Etesian {
|
|||
indent = label;
|
||||
}
|
||||
|
||||
ostringstream elapsed;
|
||||
//elapsed << " dTime:" << setw(5) << _timer.getCombTime() << "s ";
|
||||
|
||||
cmess2 << label << elapsed.str()
|
||||
cmess2 << label
|
||||
<< " HPWL:" << setw(11) << coloquinte::gp::get_HPWL_wirelength( _circuit, _placementUB )
|
||||
<< " RMST:" << setw(11) << coloquinte::gp::get_RSMT_wirelength( _circuit, _placementUB )
|
||||
<< endl;
|
||||
|
@ -977,10 +950,7 @@ namespace Etesian {
|
|||
indent = label;
|
||||
}
|
||||
|
||||
ostringstream elapsed;
|
||||
//elapsed << " dTime:" << setw(5) << _timer.getCombTime() << "s ";
|
||||
|
||||
cmess2 << label << elapsed.str()
|
||||
cmess2 << label
|
||||
<< " HPWL:" << setw(11) << coloquinte::gp::get_HPWL_wirelength( _circuit, _placementLB )
|
||||
<< " RMST:" << setw(11) << coloquinte::gp::get_RSMT_wirelength( _circuit, _placementLB )
|
||||
<< endl;
|
||||
|
@ -1042,7 +1012,7 @@ namespace Etesian {
|
|||
|
||||
Record* EtesianEngine::_getRecord () const
|
||||
{
|
||||
Record* record = ToolEngine::_getRecord ();
|
||||
Record* record = Super::_getRecord ();
|
||||
|
||||
if (record) {
|
||||
record->add( getSlot( "_configuration", _configuration ) );
|
||||
|
|
|
@ -52,6 +52,8 @@ namespace Etesian {
|
|||
// Class : "Etesian::EtesianEngine".
|
||||
|
||||
class EtesianEngine : public CRL::ToolEngine {
|
||||
public:
|
||||
typedef ToolEngine Super;
|
||||
public:
|
||||
static const Name& staticGetName ();
|
||||
static EtesianEngine* create ( Cell* );
|
||||
|
@ -73,10 +75,6 @@ namespace Etesian {
|
|||
inline Hurricane::CellViewer* getViewer () const;
|
||||
inline void setViewer ( Hurricane::CellViewer* );
|
||||
|
||||
void startMeasures ();
|
||||
void stopMeasures ();
|
||||
void printMeasures ( std::string ) const;
|
||||
|
||||
void setDefaultAb ();
|
||||
void resetPlacement ();
|
||||
void toColoquinte ();
|
||||
|
@ -104,7 +102,6 @@ namespace Etesian {
|
|||
bool _placed;
|
||||
bool _ySpinSet;
|
||||
bool _flatDesign;
|
||||
Timer _timer;
|
||||
coloquinte::box<coloquinte::int_t> _surface;
|
||||
coloquinte::netlist _circuit;
|
||||
coloquinte::placement_t _placementLB;
|
||||
|
|
|
@ -814,7 +814,7 @@ DeepNet* Cell::getDeepNet ( Path path, const Net* leafNet ) const
|
|||
}
|
||||
|
||||
|
||||
void Cell::flattenNets(unsigned int flags)
|
||||
void Cell::flattenNets(uint64_t flags)
|
||||
// ***************************************
|
||||
{
|
||||
cdebug_log(18,0) << "Cell::flattenNets() flags:0x" << hex << flags << endl;
|
||||
|
@ -892,7 +892,7 @@ void Cell::flattenNets(unsigned int flags)
|
|||
}
|
||||
|
||||
|
||||
void Cell::createRoutingPadRings(unsigned int flags)
|
||||
void Cell::createRoutingPadRings(uint64_t flags)
|
||||
// *************************************************
|
||||
{
|
||||
flags &= Flags::MaskRings;
|
||||
|
@ -1339,7 +1339,7 @@ void Cell::_toJsonCollections(JsonWriter* writer) const
|
|||
// Cell::Flags implementation
|
||||
// ****************************************************************************************************
|
||||
|
||||
Cell::Flags::Flags ( unsigned int flags)
|
||||
Cell::Flags::Flags ( uint64_t flags)
|
||||
: BaseFlags(flags)
|
||||
{ }
|
||||
|
||||
|
|
|
@ -47,7 +47,7 @@ namespace Hurricane {
|
|||
|
||||
string BaseFlags::_getString () const
|
||||
{
|
||||
static size_t width = sizeof(unsigned int) * CHAR_BIT;
|
||||
static size_t width = sizeof(uint64_t) * CHAR_BIT;
|
||||
|
||||
std::ostringstream formatted;
|
||||
formatted << "0x" << std::hex << std::setw(width) << std::setfill('0') << _flags;
|
||||
|
|
|
@ -99,7 +99,7 @@ class Cell : public Entity {
|
|||
};
|
||||
|
||||
public:
|
||||
Flags ( unsigned int flags = NoFlags );
|
||||
Flags ( uint64_t flags = NoFlags );
|
||||
virtual ~Flags ();
|
||||
virtual std::string _getTypeName () const;
|
||||
virtual std::string _getString () const;
|
||||
|
@ -357,9 +357,9 @@ class Cell : public Entity {
|
|||
public: virtual string _getTypeName() const {return _TName("Cell");};
|
||||
public: virtual string _getString() const;
|
||||
public: virtual Record* _getRecord() const;
|
||||
public: static string getFlagString( unsigned int );
|
||||
public: static Record* getFlagRecord( unsigned int );
|
||||
public: static Slot* getFlagSlot( unsigned int );
|
||||
public: static string getFlagString( uint64_t );
|
||||
public: static Record* getFlagRecord( uint64_t );
|
||||
public: static Slot* getFlagSlot( uint64_t );
|
||||
|
||||
public: InstanceMap& _getInstanceMap() {return _instanceMap;};
|
||||
public: QuadTree* _getQuadTree() {return _quadTree;};
|
||||
|
@ -506,10 +506,10 @@ class Cell : public Entity {
|
|||
public: void setFlattenLeaf(bool isFlattenLeaf) {_flags.set(Flags::FlattenLeaf,isFlattenLeaf);};
|
||||
public: void setPad(bool isPad) {_flags.set(Flags::Pad,isPad);};
|
||||
public: void setFeed(bool isFeed) {_flags.set(Flags::Feed,isFeed);};
|
||||
public: void flattenNets(unsigned int flags=Flags::BuildRings);
|
||||
public: void createRoutingPadRings(unsigned int flags=Flags::BuildRings);
|
||||
public: void setFlags(unsigned int flags) { _flags |= flags; }
|
||||
public: void resetFlags(unsigned int flags) { _flags &= ~flags; }
|
||||
public: void flattenNets(uint64_t flags=Flags::BuildRings);
|
||||
public: void createRoutingPadRings(uint64_t flags=Flags::BuildRings);
|
||||
public: void setFlags(uint64_t flags) { _flags |= flags; }
|
||||
public: void resetFlags(uint64_t flags) { _flags &= ~flags; }
|
||||
public: bool updatePlacedFlag();
|
||||
public: void materialize();
|
||||
public: void unmaterialize();
|
||||
|
|
|
@ -41,6 +41,7 @@
|
|||
#include <set>
|
||||
#include <map>
|
||||
#include <stack>
|
||||
#include <array>
|
||||
#include <vector>
|
||||
#include <iostream>
|
||||
#include <iomanip>
|
||||
|
@ -318,6 +319,104 @@ template<typename Data> inline Hurricane::Record* getRecord ( Data data )
|
|||
{ return NULL; }
|
||||
|
||||
|
||||
// -------------------------------------------------------------------
|
||||
// Inspector Support for : "[const] std::array<Element>*".
|
||||
|
||||
|
||||
template<typename Element,size_t N>
|
||||
inline std::string getString ( std::array<Element,N>* v )
|
||||
{
|
||||
std::string name = "const std::array<Element,N>:";
|
||||
return name + getString<size_t>(v->size());
|
||||
}
|
||||
|
||||
|
||||
template<typename Element,size_t N>
|
||||
inline Hurricane::Record* getRecord ( std::array<Element,N>* v )
|
||||
{
|
||||
Hurricane::Record* record = NULL;
|
||||
if ( !v->empty() ) {
|
||||
record = new Hurricane::Record ( "std::array<Element,N>" );
|
||||
unsigned n = 0;
|
||||
typename std::array<Element,N>::iterator iterator = v->begin();
|
||||
while ( iterator != v->end() ) {
|
||||
record->add ( getSlot<Element>(getString(n++), *iterator) );
|
||||
++iterator;
|
||||
}
|
||||
}
|
||||
return record;
|
||||
}
|
||||
|
||||
|
||||
template<typename Element,size_t N>
|
||||
inline std::string getString ( const std::array<Element,N>* v )
|
||||
{
|
||||
std::string name = "const std::array<Element,N>:";
|
||||
return name + getString<size_t>(v->size());
|
||||
}
|
||||
|
||||
|
||||
template<typename Element,size_t N>
|
||||
inline Hurricane::Record* getRecord ( const std::array<Element,N>* v )
|
||||
{
|
||||
Hurricane::Record* record = NULL;
|
||||
if ( !v->empty() ) {
|
||||
record = new Hurricane::Record ( "const std::array<Element,N>" );
|
||||
unsigned n = 0;
|
||||
typename std::array<Element,N>::const_iterator iterator = v->begin();
|
||||
while ( iterator != v->end() ) {
|
||||
record->add ( getSlot<const Element>(getString(n++), *iterator) );
|
||||
++iterator;
|
||||
}
|
||||
}
|
||||
return record;
|
||||
}
|
||||
|
||||
|
||||
template<typename Element,size_t N>
|
||||
inline std::string getString ( std::array<Element,N>& v )
|
||||
{
|
||||
std::string name = "std::array<Element,N>&:";
|
||||
return name + getString<size_t>(v.size());
|
||||
}
|
||||
|
||||
|
||||
template<typename Element,size_t N>
|
||||
inline Hurricane::Record* getRecord ( std::array<Element,N>& v )
|
||||
{
|
||||
Hurricane::Record* record = NULL;
|
||||
if (not v.empty()) {
|
||||
record = new Hurricane::Record ( "std::array<Element,N>&" );
|
||||
unsigned n = 0;
|
||||
for ( auto element : v )
|
||||
record->add( getSlot<Element>(getString(n++), element) );
|
||||
}
|
||||
return record;
|
||||
}
|
||||
|
||||
|
||||
template<typename Element,size_t N>
|
||||
inline std::string getString ( const std::array<Element,N>& v )
|
||||
{
|
||||
std::string name = "const std::array<Element,N>&:";
|
||||
return name + getString<size_t>(v.size());
|
||||
}
|
||||
|
||||
|
||||
template<typename Element,size_t N>
|
||||
inline Hurricane::Record* getRecord ( const std::array<Element,N>& v )
|
||||
{
|
||||
Hurricane::Record* record = NULL;
|
||||
if (not v.empty()) {
|
||||
record = new Hurricane::Record ( "const std::array<Element,N>&" );
|
||||
unsigned n = 0;
|
||||
for ( auto element : v )
|
||||
record->add( getSlot<Element>(getString(n++), element) );
|
||||
}
|
||||
return record;
|
||||
}
|
||||
|
||||
|
||||
// -------------------------------------------------------------------
|
||||
// Inspector Support for : "[const] std::vector<Element>*".
|
||||
|
||||
|
|
|
@ -32,6 +32,7 @@
|
|||
#ifndef HURRICANE_BASE_FLAGS_H
|
||||
#define HURRICANE_BASE_FLAGS_H
|
||||
|
||||
#include <cstdint>
|
||||
#include <string>
|
||||
#include "hurricane/Commons.h"
|
||||
|
||||
|
@ -42,7 +43,7 @@ namespace Hurricane {
|
|||
class BaseFlags {
|
||||
public:
|
||||
// Methods.
|
||||
inline BaseFlags ( unsigned int flags=0 );
|
||||
inline BaseFlags ( uint64_t flags=0 );
|
||||
virtual ~BaseFlags ();
|
||||
inline bool zero () const;
|
||||
inline BaseFlags& set ( BaseFlags, bool state=true );
|
||||
|
@ -50,7 +51,7 @@ namespace Hurricane {
|
|||
inline bool isset ( BaseFlags ) const;
|
||||
inline bool contains ( BaseFlags ) const;
|
||||
inline bool intersect ( BaseFlags ) const;
|
||||
inline BaseFlags nthbit ( unsigned int ) const;
|
||||
inline BaseFlags nthbit ( uint64_t ) const;
|
||||
inline BaseFlags operator compl () const;
|
||||
inline BaseFlags operator bitand ( BaseFlags ) const;
|
||||
inline BaseFlags operator bitor ( BaseFlags ) const;
|
||||
|
@ -60,11 +61,11 @@ namespace Hurricane {
|
|||
inline BaseFlags operator xor ( int ) const;
|
||||
inline BaseFlags lshift ( int ) const;
|
||||
inline BaseFlags rshift ( int ) const;
|
||||
inline BaseFlags operator bitand ( unsigned int ) const;
|
||||
inline BaseFlags operator bitor ( unsigned int ) const;
|
||||
inline BaseFlags operator xor ( unsigned int ) const;
|
||||
inline BaseFlags lshift ( unsigned int ) const;
|
||||
inline BaseFlags rshift ( unsigned int ) const;
|
||||
inline BaseFlags operator bitand ( uint64_t ) const;
|
||||
inline BaseFlags operator bitor ( uint64_t ) const;
|
||||
inline BaseFlags operator xor ( uint64_t ) const;
|
||||
inline BaseFlags lshift ( uint64_t ) const;
|
||||
inline BaseFlags rshift ( uint64_t ) const;
|
||||
inline BaseFlags& operator |= ( BaseFlags );
|
||||
inline BaseFlags& operator &= ( BaseFlags );
|
||||
inline bool operator == ( BaseFlags ) const;
|
||||
|
@ -77,12 +78,12 @@ namespace Hurricane {
|
|||
inline bool operator != ( int ) const;
|
||||
inline bool operator < ( int ) const;
|
||||
inline bool operator > ( int ) const;
|
||||
inline BaseFlags& operator |= ( unsigned int );
|
||||
inline BaseFlags& operator &= ( unsigned int );
|
||||
inline bool operator == ( unsigned int ) const;
|
||||
inline bool operator != ( unsigned int ) const;
|
||||
inline bool operator < ( unsigned int ) const;
|
||||
inline bool operator > ( unsigned int ) const;
|
||||
inline BaseFlags& operator |= ( uint64_t );
|
||||
inline BaseFlags& operator &= ( uint64_t );
|
||||
inline bool operator == ( uint64_t ) const;
|
||||
inline bool operator != ( uint64_t ) const;
|
||||
inline bool operator < ( uint64_t ) const;
|
||||
inline bool operator > ( uint64_t ) const;
|
||||
inline operator bool () const;
|
||||
//inline operator unsigned int () const;
|
||||
// Hurricane Managment.
|
||||
|
@ -91,12 +92,12 @@ namespace Hurricane {
|
|||
inline Record* _getRecord () const;
|
||||
protected:
|
||||
// Internal: Attributes.
|
||||
unsigned int _flags;
|
||||
uint64_t _flags;
|
||||
};
|
||||
|
||||
|
||||
// Inline Functions.
|
||||
inline BaseFlags::BaseFlags ( unsigned int flags ) : _flags(flags) { }
|
||||
inline BaseFlags::BaseFlags ( uint64_t flags ) : _flags(flags) { }
|
||||
inline bool BaseFlags::zero () const { return _flags == 0; }
|
||||
inline BaseFlags& BaseFlags::reset ( BaseFlags flags ) { _flags &= ~flags._flags; return *this; }
|
||||
inline bool BaseFlags::isset ( BaseFlags flags ) const { return _flags & flags._flags; }
|
||||
|
@ -107,34 +108,34 @@ namespace Hurricane {
|
|||
inline BaseFlags BaseFlags::operator bitand ( BaseFlags flags ) const { return _flags & flags._flags; }
|
||||
inline BaseFlags BaseFlags::operator bitor ( BaseFlags flags ) const { return _flags | flags._flags; }
|
||||
inline BaseFlags BaseFlags::operator xor ( BaseFlags flags ) const { return _flags ^ flags._flags; }
|
||||
inline BaseFlags BaseFlags::operator bitand ( int flags ) const { return _flags & (unsigned int)flags; }
|
||||
inline BaseFlags BaseFlags::operator bitor ( int flags ) const { return _flags | (unsigned int)flags; }
|
||||
inline BaseFlags BaseFlags::operator xor ( int flags ) const { return _flags ^ (unsigned int)flags; }
|
||||
inline BaseFlags BaseFlags::lshift ( int s ) const { return _flags << (unsigned int)s; }
|
||||
inline BaseFlags BaseFlags::rshift ( int s ) const { return _flags >> (unsigned int)s; }
|
||||
inline BaseFlags BaseFlags::operator bitand ( unsigned int flags ) const { return _flags & flags; }
|
||||
inline BaseFlags BaseFlags::operator bitor ( unsigned int flags ) const { return _flags | flags; }
|
||||
inline BaseFlags BaseFlags::operator xor ( unsigned int flags ) const { return _flags ^ flags; }
|
||||
inline BaseFlags BaseFlags::lshift ( unsigned int s ) const { return _flags << s; }
|
||||
inline BaseFlags BaseFlags::rshift ( unsigned int s ) const { return _flags >> s; }
|
||||
inline BaseFlags BaseFlags::operator bitand ( int flags ) const { return _flags & (uint64_t)flags; }
|
||||
inline BaseFlags BaseFlags::operator bitor ( int flags ) const { return _flags | (uint64_t)flags; }
|
||||
inline BaseFlags BaseFlags::operator xor ( int flags ) const { return _flags ^ (uint64_t)flags; }
|
||||
inline BaseFlags BaseFlags::lshift ( int s ) const { return _flags << (uint64_t)s; }
|
||||
inline BaseFlags BaseFlags::rshift ( int s ) const { return _flags >> (uint64_t)s; }
|
||||
inline BaseFlags BaseFlags::operator bitand ( uint64_t flags ) const { return _flags & flags; }
|
||||
inline BaseFlags BaseFlags::operator bitor ( uint64_t flags ) const { return _flags | flags; }
|
||||
inline BaseFlags BaseFlags::operator xor ( uint64_t flags ) const { return _flags ^ flags; }
|
||||
inline BaseFlags BaseFlags::lshift ( uint64_t s ) const { return _flags << s; }
|
||||
inline BaseFlags BaseFlags::rshift ( uint64_t s ) const { return _flags >> s; }
|
||||
inline BaseFlags& BaseFlags::operator |= ( BaseFlags flags ) { _flags |= flags._flags; return *this; }
|
||||
inline BaseFlags& BaseFlags::operator &= ( BaseFlags flags ) { _flags &= flags._flags; return *this; }
|
||||
inline bool BaseFlags::operator == ( BaseFlags flags ) const { return _flags == flags._flags; }
|
||||
inline bool BaseFlags::operator != ( BaseFlags flags ) const { return _flags != flags._flags; }
|
||||
inline bool BaseFlags::operator < ( BaseFlags flags ) const { return _flags < flags._flags; }
|
||||
inline bool BaseFlags::operator > ( BaseFlags flags ) const { return _flags > flags._flags; }
|
||||
inline BaseFlags& BaseFlags::operator |= ( int flags ) { _flags |= (unsigned int)flags; return *this; }
|
||||
inline BaseFlags& BaseFlags::operator &= ( int flags ) { _flags &= (unsigned int)flags; return *this; }
|
||||
inline bool BaseFlags::operator == ( int flags ) const { return _flags == (unsigned int)flags; }
|
||||
inline bool BaseFlags::operator != ( int flags ) const { return _flags != (unsigned int)flags; }
|
||||
inline bool BaseFlags::operator < ( int flags ) const { return _flags < (unsigned int)flags; }
|
||||
inline bool BaseFlags::operator > ( int flags ) const { return _flags > (unsigned int)flags; }
|
||||
inline BaseFlags& BaseFlags::operator |= ( unsigned int flags ) { _flags |= flags; return *this; }
|
||||
inline BaseFlags& BaseFlags::operator &= ( unsigned int flags ) { _flags &= flags; return *this; }
|
||||
inline bool BaseFlags::operator == ( unsigned int flags ) const { return _flags == flags; }
|
||||
inline bool BaseFlags::operator != ( unsigned int flags ) const { return _flags != flags; }
|
||||
inline bool BaseFlags::operator < ( unsigned int flags ) const { return _flags < flags; }
|
||||
inline bool BaseFlags::operator > ( unsigned int flags ) const { return _flags > flags; }
|
||||
inline BaseFlags& BaseFlags::operator |= ( int flags ) { _flags |= (uint64_t)flags; return *this; }
|
||||
inline BaseFlags& BaseFlags::operator &= ( int flags ) { _flags &= (uint64_t)flags; return *this; }
|
||||
inline bool BaseFlags::operator == ( int flags ) const { return _flags == (uint64_t)flags; }
|
||||
inline bool BaseFlags::operator != ( int flags ) const { return _flags != (uint64_t)flags; }
|
||||
inline bool BaseFlags::operator < ( int flags ) const { return _flags < (uint64_t)flags; }
|
||||
inline bool BaseFlags::operator > ( int flags ) const { return _flags > (uint64_t)flags; }
|
||||
inline BaseFlags& BaseFlags::operator |= ( uint64_t flags ) { _flags |= flags; return *this; }
|
||||
inline BaseFlags& BaseFlags::operator &= ( uint64_t flags ) { _flags &= flags; return *this; }
|
||||
inline bool BaseFlags::operator == ( uint64_t flags ) const { return _flags == flags; }
|
||||
inline bool BaseFlags::operator != ( uint64_t flags ) const { return _flags != flags; }
|
||||
inline bool BaseFlags::operator < ( uint64_t flags ) const { return _flags < flags; }
|
||||
inline bool BaseFlags::operator > ( uint64_t flags ) const { return _flags > flags; }
|
||||
inline BaseFlags::operator bool () const { return _flags != 0; }
|
||||
//inline BaseFlags::operator unsigned int () const { return _flags; }
|
||||
//inline BaseFlags::operator unsigned int () const { return _flags; }
|
||||
|
@ -146,9 +147,9 @@ namespace Hurricane {
|
|||
return *this;
|
||||
}
|
||||
|
||||
inline BaseFlags BaseFlags::nthbit ( unsigned int nth ) const
|
||||
inline BaseFlags BaseFlags::nthbit ( uint64_t nth ) const
|
||||
{
|
||||
unsigned int select = 1;
|
||||
uint64_t select = 1;
|
||||
for ( ; select ; select=select<<1 ) {
|
||||
if ( _flags & select ) nth--;
|
||||
if ( !nth ) break;
|
||||
|
|
|
@ -145,7 +145,6 @@ namespace Katabatic {
|
|||
|
||||
KatabaticEngine::KatabaticEngine ( Cell* cell )
|
||||
: ToolEngine (cell)
|
||||
, _timer ()
|
||||
, _state (EngineCreation)
|
||||
, _flags (EngineDestroyBaseContact)
|
||||
, _configuration (new ConfigurationConcrete())
|
||||
|
@ -361,34 +360,13 @@ namespace Katabatic {
|
|||
}
|
||||
|
||||
|
||||
void KatabaticEngine::startMeasures ()
|
||||
{
|
||||
_timer.resetIncrease();
|
||||
_timer.start();
|
||||
}
|
||||
|
||||
|
||||
void KatabaticEngine::stopMeasures ()
|
||||
{ _timer.stop(); }
|
||||
|
||||
|
||||
void KatabaticEngine::printMeasures ( const string& tag ) const
|
||||
{
|
||||
ostringstream result;
|
||||
Super::printMeasures();
|
||||
|
||||
result << Timer::getStringTime(_timer.getCombTime())
|
||||
<< ", " << Timer::getStringMemory(_timer.getIncrease());
|
||||
cmess1 << Dots::asString( " - Done in", result.str() ) << endl;
|
||||
|
||||
result.str("");
|
||||
result << _timer.getCombTime()
|
||||
<< "s, +" << (_timer.getIncrease()>>10) << "Kb/"
|
||||
<< Timer::getStringMemory(Timer::getMemorySize());
|
||||
cmess2 << Dots::asString( " - Raw measurements", result.str() ) << endl;
|
||||
|
||||
if (not tag.empty()) {
|
||||
addMeasure<double>( getCell(), tag+"T", _timer.getCombTime () );
|
||||
addMeasure<size_t>( getCell(), tag+"S", (_timer.getMemorySize() >> 20) );
|
||||
if (not tag.empty()) {
|
||||
addMeasure<double>( getCell(), tag+"T", getTimer().getCombTime () );
|
||||
addMeasure<size_t>( getCell(), tag+"S", (getTimer().getMemorySize() >> 20) );
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -22,7 +22,6 @@
|
|||
#include <vector>
|
||||
#include <set>
|
||||
#include <map>
|
||||
#include "hurricane/Timer.h"
|
||||
#include "hurricane/DbU.h"
|
||||
#include "hurricane/Torus.h"
|
||||
#include "hurricane/Layer.h"
|
||||
|
@ -91,6 +90,7 @@ namespace Katabatic {
|
|||
|
||||
class KatabaticEngine : public ToolEngine {
|
||||
public:
|
||||
typedef ToolEngine Super;
|
||||
typedef set<Net*,NetCompareByName> NetSet;
|
||||
|
||||
public:
|
||||
|
@ -134,8 +134,6 @@ namespace Katabatic {
|
|||
inline void setGlobalThreshold ( DbU::Unit );
|
||||
inline void setSaturateRatio ( float );
|
||||
inline void setSaturateRp ( size_t );
|
||||
void startMeasures ();
|
||||
void stopMeasures ();
|
||||
void printMeasures ( const string& ) const;
|
||||
void refresh ( unsigned int flags=KbOpenSession );
|
||||
virtual void createDetailedGrid ();
|
||||
|
@ -192,7 +190,6 @@ namespace Katabatic {
|
|||
protected:
|
||||
// Attributes.
|
||||
static Name _toolName;
|
||||
Timer _timer;
|
||||
EngineState _state;
|
||||
unsigned int _flags;
|
||||
Configuration* _configuration;
|
||||
|
|
|
@ -12,6 +12,7 @@
|
|||
set( includes katana/Constants.h
|
||||
katana/TrackCost.h
|
||||
katana/DataNegociate.h
|
||||
katana/DataSymmetric.h
|
||||
katana/TrackElement.h katana/TrackElements.h
|
||||
katana/TrackSegment.h
|
||||
katana/TrackFixedSegment.h
|
||||
|
@ -40,6 +41,7 @@
|
|||
set( cpps Constants.cpp
|
||||
Configuration.cpp
|
||||
DataNegociate.cpp
|
||||
DataSymmetric.cpp
|
||||
TrackCost.cpp
|
||||
TrackElement.cpp
|
||||
TrackElements.cpp
|
||||
|
@ -64,6 +66,7 @@
|
|||
ProtectRoutingPads.cpp
|
||||
PreProcess.cpp
|
||||
GlobalRoute.cpp
|
||||
SymmetricRoute.cpp
|
||||
KatanaEngine.cpp
|
||||
GraphicKatanaEngine.cpp
|
||||
)
|
||||
|
|
|
@ -21,17 +21,18 @@
|
|||
namespace Katana {
|
||||
|
||||
|
||||
const unsigned int Flags::AllowDoglegReuse = (1 << 20);
|
||||
const unsigned int Flags::DataSelf = (1 << 21);
|
||||
const unsigned int Flags::Nearest = (1 << 22);
|
||||
const unsigned int Flags::Force = (1 << 23);
|
||||
const unsigned int Flags::ResetCount = (1 << 24);
|
||||
const unsigned int Flags::WithConstraints = (1 << 25);
|
||||
const unsigned int Flags::MoveToLeft = (1 << 26);
|
||||
const unsigned int Flags::MoveToRight = (1 << 27);
|
||||
const unsigned int Flags::LoadingStage = (1 << 28);
|
||||
const unsigned int Flags::SlowMotion = (1 << 29);
|
||||
const unsigned int Flags::PreRoutedStage = (1 << 30);
|
||||
const uint64_t Flags::AllowDoglegReuse = (1 << 20);
|
||||
const uint64_t Flags::DataSelf = (1 << 21);
|
||||
const uint64_t Flags::Nearest = (1 << 22);
|
||||
const uint64_t Flags::Force = (1 << 23);
|
||||
const uint64_t Flags::ResetCount = (1 << 24);
|
||||
const uint64_t Flags::WithConstraints = (1 << 25);
|
||||
const uint64_t Flags::MoveToLeft = (1 << 26);
|
||||
const uint64_t Flags::MoveToRight = (1 << 27);
|
||||
const uint64_t Flags::LoadingStage = (1 << 28);
|
||||
const uint64_t Flags::SlowMotion = (1 << 29);
|
||||
const uint64_t Flags::PreRoutedStage = (1 << 30);
|
||||
const uint64_t Flags::SymmetricStage = (1 << 31);
|
||||
|
||||
|
||||
} // Anabatic namespace.
|
||||
|
|
|
@ -0,0 +1,269 @@
|
|||
// -*- C++ -*-
|
||||
//
|
||||
// This file is part of the Coriolis Software.
|
||||
// Copyright (c) UPMC 2008-2016, All Rights Reserved
|
||||
//
|
||||
// +-----------------------------------------------------------------+
|
||||
// | C O R I O L I S |
|
||||
// | K i t e - D e t a i l e d R o u t e r |
|
||||
// | |
|
||||
// | Author : Jean-Paul CHAPUT |
|
||||
// | E-mail : Jean-Paul.Chaput@lip6.fr |
|
||||
// | =============================================================== |
|
||||
// | C++ Module : "./DataSymmetric.cpp" |
|
||||
// +-----------------------------------------------------------------+
|
||||
|
||||
#include "anabatic/AutoSegment.h"
|
||||
#include "katana/DataSymmetric.h"
|
||||
|
||||
|
||||
namespace {
|
||||
|
||||
using namespace std;
|
||||
|
||||
|
||||
class Message {
|
||||
public:
|
||||
inline Message ( size_t, string header="" );
|
||||
inline size_t size () const;
|
||||
inline ostringstream& newline ();
|
||||
inline ostringstream& line ();
|
||||
inline void setHeader ( string );
|
||||
void print ( ostream& );
|
||||
private:
|
||||
size_t _indent;
|
||||
string _header;
|
||||
vector<string> _lines;
|
||||
ostringstream _current;
|
||||
};
|
||||
|
||||
|
||||
inline Message::Message ( size_t indent, string header )
|
||||
: _indent (indent)
|
||||
, _header (header)
|
||||
, _lines ()
|
||||
, _current()
|
||||
{ }
|
||||
|
||||
inline size_t Message::size () const { return _lines.size(); }
|
||||
inline void Message::setHeader ( string header ) { _header = header; }
|
||||
inline ostringstream& Message::line () { return _current; }
|
||||
|
||||
inline ostringstream& Message::newline ()
|
||||
{
|
||||
if (_current.str().size())
|
||||
_lines.push_back(_current.str());
|
||||
_current.str("");
|
||||
return _current;
|
||||
}
|
||||
|
||||
void Message::print ( ostream& o )
|
||||
{
|
||||
if (not _header.empty()) _indent = _header.size()+1;
|
||||
|
||||
string head ( _indent, ' ' );
|
||||
for ( size_t i=0 ; i<_lines.size() ; ++i ) {
|
||||
if ((i == 0) and not _header.empty()) o << _header << " ";
|
||||
else o << head;
|
||||
o << _lines[i] << endl;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
} // Anonymous namespace.
|
||||
|
||||
|
||||
namespace Katana {
|
||||
|
||||
using namespace std;
|
||||
using Anabatic::AutoSegmentFlag;
|
||||
|
||||
|
||||
DataSymmetric* DataSymmetric::create ( Net* net )
|
||||
{
|
||||
NetRoutingState* state = NetRoutingExtension::get( net );
|
||||
|
||||
if (not state or not state->isSymmetric()) return NULL;
|
||||
if (state->getSymNet() and not state->isSymMaster()) return NULL;
|
||||
|
||||
return new DataSymmetric ( net );
|
||||
}
|
||||
|
||||
|
||||
DataSymmetric::DataSymmetric ( Net* net )
|
||||
: _valid (true)
|
||||
, _net (net)
|
||||
, _symNet (NULL)
|
||||
, _state (NetRoutingExtension::get(_net))
|
||||
, _paireds ()
|
||||
, _symIndex(0)
|
||||
{
|
||||
_symNet = _state->getSymNet();
|
||||
}
|
||||
|
||||
|
||||
void DataSymmetric::addSymmetrical ( AutoSegment* symmetrical )
|
||||
{
|
||||
if (_paireds.size() > _symIndex) _paireds[_symIndex++][1] = symmetrical;
|
||||
else _paireds.push_back( { NULL, symmetrical } );
|
||||
}
|
||||
|
||||
|
||||
AutoSegment* DataSymmetric::getSymmetrical ( AutoSegment* segment ) const
|
||||
{
|
||||
for ( const array<AutoSegment*,2>& paired : _paireds ) {
|
||||
if (segment == paired[0]) return paired[1];
|
||||
if (segment == paired[1]) return paired[0];
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
bool DataSymmetric::checkPairing ()
|
||||
{
|
||||
const unsigned int mask = ~(AutoSegmentFlag::SegIsReduced);
|
||||
Message errors ( 0, "[ERROR]" );
|
||||
|
||||
size_t refs = 0;
|
||||
size_t syms = 0;
|
||||
for ( const array<AutoSegment*,2>& paired : _paireds ) {
|
||||
refs += (paired[0]) ? 1 : 0;
|
||||
syms += (paired[1]) ? 1 : 0;
|
||||
}
|
||||
if (refs != syms) {
|
||||
errors.newline() << "Segments symmetric sets size mismatch, reference:" << refs
|
||||
<< " symmetricals:" << syms << ".";
|
||||
_valid = false;
|
||||
} else {
|
||||
size_t index = 0;
|
||||
for ( const array<AutoSegment*,2>& paired : _paireds ) {
|
||||
if (paired[0]->isHorizontal() xor paired[1]->isHorizontal()) {
|
||||
errors.newline() << "Direction mismatch @ [" << index << "]";
|
||||
errors.newline() << "| " << paired[0];
|
||||
errors.newline() << "| " << paired[1];
|
||||
_valid = false;
|
||||
}
|
||||
|
||||
if (paired[0]->getLayer() != paired[1]->getLayer()) {
|
||||
errors.newline() << "Layer mismatch @ [" << index << "]";
|
||||
errors.newline() << "| " << paired[0];
|
||||
errors.newline() << "| " << paired[1];
|
||||
_valid = false;
|
||||
}
|
||||
|
||||
if (_state->isSymVertical()) {
|
||||
if (paired[0]->isVertical()) {
|
||||
if ( (paired[0]->getFlags() ^ paired[1]->getFlags()) & mask ) {
|
||||
errors.newline() << "Flags mismatch at index " << index
|
||||
<< " " << paired[0]->getFlags()
|
||||
<< " vs. " << paired[1]->getFlags();
|
||||
errors.newline() << "| " << paired[0];
|
||||
errors.newline() << "| " << paired[1];
|
||||
_valid = false;
|
||||
}
|
||||
|
||||
if (2*getSymAxis() - paired[0]->getAxis() != paired[1]->getAxis()) {
|
||||
errors.newline() << "Mirror axis mismatch @ [" << index << "] "
|
||||
<< DbU::getValueString(paired[1]->getAxis()) << " (should be: "
|
||||
<< DbU::getValueString(2*getSymAxis() - paired[0]->getAxis()) << ")";
|
||||
errors.newline() << "| " << paired[0];
|
||||
errors.newline() << "| " << paired[1];
|
||||
_valid = false;
|
||||
}
|
||||
} else {
|
||||
if ( (paired[0]->getFlags() ^ AutoSegment::swapSourceTargetFlags(paired[1])) & mask ) {
|
||||
errors.newline() << "Flags mismatch at index " << index
|
||||
<< " " << paired[0]->getFlags()
|
||||
<< " vs. " << paired[1]->getFlags()
|
||||
<< " swp " << AutoSegment::swapSourceTargetFlags(paired[1]);
|
||||
_valid = false;
|
||||
}
|
||||
|
||||
if (paired[0]->getAxis() != paired[1]->getAxis()) {
|
||||
errors.newline() << "Axis mismatch index " << index << " "
|
||||
<< DbU::getValueString(paired[1]->getAxis()) << " (should be:"
|
||||
<< DbU::getValueString(paired[0]->getAxis()) << ")";
|
||||
errors.newline() << "| " << paired[0];
|
||||
errors.newline() << "| " << paired[1];
|
||||
_valid = false;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (paired[0]->isHorizontal()) {
|
||||
if (2*getSymAxis() - paired[0]->getAxis() != paired[1]->getAxis()) {
|
||||
errors.newline() << "Mirror axis mismatch index " << index << " "
|
||||
<< DbU::getValueString(paired[1]->getAxis()) << " (should be:"
|
||||
<< DbU::getValueString(2*getSymAxis() - paired[0]->getAxis()) << ")";
|
||||
errors.newline() << "| " << paired[0];
|
||||
errors.newline() << "| " << paired[1];
|
||||
_valid = false;
|
||||
}
|
||||
} else {
|
||||
if (paired[0]->getAxis() != paired[1]->getAxis()) {
|
||||
errors.newline() << "Axis mismatch index " << index << " "
|
||||
<< DbU::getValueString(paired[1]->getAxis()) << " (should be:"
|
||||
<< DbU::getValueString(paired[0]->getAxis()) << ")";
|
||||
errors.newline() << "| " << paired[0];
|
||||
errors.newline() << "| " << paired[1];
|
||||
_valid = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
++index;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
errors.newline();
|
||||
if (errors.size()) {
|
||||
cmess2 << " pairing failed." << endl;
|
||||
errors.print( cmess2 );
|
||||
} else {
|
||||
cmess2 << " paired." << endl;
|
||||
}
|
||||
|
||||
return _valid;
|
||||
}
|
||||
|
||||
|
||||
void DataSymmetric::print ( ostream& o ) const
|
||||
{
|
||||
Message lines ( 0 );
|
||||
|
||||
lines.newline() << "Paired components of Net \"" << _net->getName() << "\"";
|
||||
if (_symNet) lines.line() << " (symmetrical:\"" << _symNet->getName() << "\")";
|
||||
|
||||
size_t index = 0;
|
||||
for ( const array<AutoSegment*,2>& paired : _paireds ) {
|
||||
lines.newline() << "| " << setw(2) << index << " " << paired[0];
|
||||
lines.newline() << "+ " << setw(2) << index << " " << paired[1];
|
||||
++index;
|
||||
}
|
||||
|
||||
lines.newline();
|
||||
lines.print( o );
|
||||
}
|
||||
|
||||
|
||||
string DataSymmetric::_getString () const
|
||||
{
|
||||
return "<DataSymmetric " + getString(_net->getName()) + ">";
|
||||
}
|
||||
|
||||
|
||||
Record* DataSymmetric::_getRecord () const
|
||||
{
|
||||
Record* record = new Record ( getString(this) );
|
||||
record->add( getSlot( "_valid" , _valid ) );
|
||||
record->add( getSlot( "_net" , _net ) );
|
||||
record->add( getSlot( "_symNet" , _symNet ) );
|
||||
record->add( getSlot( "_state" , _state ) );
|
||||
record->add( getSlot( "_paireds" , &_paireds ) );
|
||||
record->add( getSlot( "_symIndex" , &_symIndex ) );
|
||||
|
||||
return record;
|
||||
}
|
||||
|
||||
|
||||
} // Katana namespace.
|
|
@ -231,10 +231,10 @@ namespace Katana {
|
|||
|
||||
void GraphicKatanaEngine::_loadGlobalRouting ()
|
||||
{
|
||||
KatanaEngine* anabatic = getForFramework( NoFlags );
|
||||
KatanaEngine* katana = getForFramework( NoFlags );
|
||||
|
||||
_viewer->clearToolInterrupt();
|
||||
anabatic->loadGlobalRouting( Anabatic::EngineLoadGrByNet );
|
||||
katana->loadGlobalRouting( Anabatic::EngineLoadGrByNet );
|
||||
}
|
||||
|
||||
|
||||
|
@ -273,7 +273,12 @@ namespace Katana {
|
|||
void GraphicKatanaEngine::_runTest ()
|
||||
{
|
||||
KatanaEngine* katana = getForFramework( NoFlags );
|
||||
if (katana) katana->runTest();
|
||||
if (katana) {
|
||||
katana->loadGlobalRouting( Anabatic::EngineLoadGrByNet );
|
||||
katana->runTest();
|
||||
katana->runNegociate( Flags::SymmetricStage );
|
||||
katana->runNegociate();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -256,9 +256,6 @@ namespace Katana {
|
|||
|
||||
KatanaEngine* KatanaEngine::create ( Cell* cell )
|
||||
{
|
||||
cmess1 << Dots::asString( " - Initial memory"
|
||||
, Timer::getStringMemory(Timer::getMemorySize()) ) << endl;
|
||||
|
||||
KatanaEngine* katana = new KatanaEngine ( cell );
|
||||
|
||||
katana->_postCreate();
|
||||
|
@ -340,6 +337,13 @@ namespace Katana {
|
|||
}
|
||||
|
||||
|
||||
DataSymmetric* KatanaEngine::getDataSymmetric ( Net* net )
|
||||
{
|
||||
auto idata = _symmetrics.find( net );
|
||||
if (idata != _symmetrics.end()) return (*idata).second;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void KatanaEngine::openSession ()
|
||||
{ Session::_open(this); }
|
||||
|
||||
|
@ -353,6 +357,26 @@ namespace Katana {
|
|||
}
|
||||
|
||||
|
||||
DataSymmetric* KatanaEngine::addDataSymmetric ( Net* net )
|
||||
{
|
||||
DataSymmetric* data = getDataSymmetric( net );
|
||||
if (data) {
|
||||
cerr << Error( "KatanaEngine::addDataSymmetric(): Try to add twice Net \"%s\" (ignored)."
|
||||
, getString(net->getName()).c_str() ) << endl;
|
||||
return data;
|
||||
}
|
||||
|
||||
data = DataSymmetric::create( net );
|
||||
if (data) {
|
||||
_symmetrics.insert( make_pair(net,data) );
|
||||
if (data->getSymNet())
|
||||
_symmetrics.insert( make_pair(data->getSymNet(),data) );
|
||||
}
|
||||
|
||||
return data;
|
||||
}
|
||||
|
||||
|
||||
void KatanaEngine::annotateGlobalGraph ()
|
||||
{
|
||||
cmess1 << " o Back annotate global routing graph." << endl;
|
||||
|
@ -649,6 +673,10 @@ namespace Katana {
|
|||
for ( size_t depth=0 ; depth < maxDepth ; depth++ ) {
|
||||
_routingPlanes[depth]->destroy();
|
||||
}
|
||||
_routingPlanes.clear();
|
||||
|
||||
for ( auto symmetric : _symmetrics ) delete symmetric.second;
|
||||
_symmetrics.clear();
|
||||
|
||||
Session::close();
|
||||
}
|
||||
|
@ -702,8 +730,9 @@ namespace Katana {
|
|||
Record* record = Super::_getRecord ();
|
||||
|
||||
if (record) {
|
||||
record->add( getSlot( "_routingPlanes", &_routingPlanes ) );
|
||||
record->add( getSlot( "_configuration", _configuration ) );
|
||||
record->add( getSlot( "_routingPlanes", &_routingPlanes ) );
|
||||
record->add( getSlot( "_symmetrics" , &_symmetrics ) );
|
||||
}
|
||||
return record;
|
||||
}
|
||||
|
|
|
@ -552,6 +552,11 @@ namespace Katana {
|
|||
Session::getKatanaEngine()->_check( overlaps, "after _createRouting(GCell*)" );
|
||||
#endif
|
||||
|
||||
if (flags & Flags::SymmetricStage) {
|
||||
_katana->runSymmetricRouter();
|
||||
Session::revalidate();
|
||||
}
|
||||
|
||||
_flags |= flags;
|
||||
_negociate();
|
||||
printStatistics();
|
||||
|
|
|
@ -43,8 +43,8 @@ namespace {
|
|||
|
||||
|
||||
void getPerpandiculars ( TrackElement* segment
|
||||
, Anabatic::AutoContact* from
|
||||
, unsigned int direction
|
||||
, Anabatic::AutoContact* from
|
||||
, Flags direction
|
||||
, vector<TrackElement*>& perpandiculars
|
||||
)
|
||||
{
|
||||
|
@ -69,7 +69,7 @@ namespace {
|
|||
}
|
||||
|
||||
|
||||
void findFailedPerpandiculars ( RoutingPad* rp, unsigned int direction, set<TrackElement*>& faileds )
|
||||
void findFailedPerpandiculars ( RoutingPad* rp, Flags direction, set<TrackElement*>& faileds )
|
||||
{
|
||||
cdebug_log(159,0) << "Find failed caging: " << rp << endl;
|
||||
|
||||
|
|
|
@ -98,6 +98,10 @@ namespace Katana {
|
|||
{ return Session::getKatanaEngine()->getConfiguration(); }
|
||||
|
||||
|
||||
AutoContact* Session::lookup ( Contact* contact )
|
||||
{ return Super::lookup(contact); }
|
||||
|
||||
|
||||
TrackElement* Session::lookup ( Segment* segment )
|
||||
{ return Session::get("Session::lookup(Segment*)")->_getKatanaEngine()->_lookup(segment); }
|
||||
|
||||
|
|
|
@ -0,0 +1,372 @@
|
|||
// -*- C++ -*-
|
||||
//
|
||||
// This file is part of the Coriolis Software.
|
||||
// Copyright (c) UPMC 2014-2016, All Rights Reserved
|
||||
//
|
||||
// +-----------------------------------------------------------------+
|
||||
// | C O R I O L I S |
|
||||
// | K i t e - D e t a i l e d R o u t e r |
|
||||
// | |
|
||||
// | Author : Jean-Paul CHAPUT |
|
||||
// | E-mail : Jean-Paul.Chaput@asim.lip6.fr |
|
||||
// | =============================================================== |
|
||||
// | C++ Module : "./SymmetricRoute.cpp" |
|
||||
// +-----------------------------------------------------------------+
|
||||
|
||||
|
||||
#include <map>
|
||||
#include <list>
|
||||
#include "hurricane/Error.h"
|
||||
#include "hurricane/Warning.h"
|
||||
#include "hurricane/DebugSession.h"
|
||||
#include "hurricane/NetRoutingProperty.h"
|
||||
#include "hurricane/RoutingPad.h"
|
||||
#include "anabatic/AutoContactTerminal.h"
|
||||
#include "katana/RoutingPlane.h"
|
||||
#include "katana/TrackFixedSegment.h"
|
||||
#include "katana/Track.h"
|
||||
#include "katana/KatanaEngine.h"
|
||||
|
||||
|
||||
namespace {
|
||||
|
||||
using namespace std;
|
||||
using Hurricane::Error;
|
||||
using Hurricane::DebugSession;
|
||||
using Hurricane::DbU;
|
||||
using Hurricane::Point;
|
||||
using Hurricane::Net;
|
||||
using Hurricane::NetRoutingState;
|
||||
using Hurricane::NetRoutingExtension;
|
||||
using Hurricane::Component;
|
||||
using Hurricane::Contact;
|
||||
using Hurricane::Segment;
|
||||
using Hurricane::Horizontal;
|
||||
using Hurricane::Vertical;
|
||||
using Hurricane::RoutingPad;
|
||||
using Anabatic::Flags;
|
||||
using Anabatic::GCell;
|
||||
using Anabatic::AutoContact;
|
||||
using Anabatic::AutoContactTerminal;
|
||||
using Anabatic::AutoSegment;
|
||||
using Anabatic::AutoSegmentFlag;
|
||||
using Katana::KatanaEngine;
|
||||
using Katana::DataSymmetric;
|
||||
using Katana::Session;
|
||||
|
||||
|
||||
class Message {
|
||||
public:
|
||||
inline Message ( size_t, string header="" );
|
||||
inline size_t size () const;
|
||||
inline ostringstream& newline ();
|
||||
inline ostringstream& line ();
|
||||
inline void setHeader ( string );
|
||||
void print ( ostream& );
|
||||
private:
|
||||
size_t _indent;
|
||||
string _header;
|
||||
vector<string> _lines;
|
||||
ostringstream _current;
|
||||
};
|
||||
|
||||
|
||||
inline Message::Message ( size_t indent, string header )
|
||||
: _indent (indent)
|
||||
, _header (header)
|
||||
, _lines ()
|
||||
, _current()
|
||||
{ }
|
||||
|
||||
inline size_t Message::size () const { return _lines.size(); }
|
||||
inline void Message::setHeader ( string header ) { _header = header; }
|
||||
inline ostringstream& Message::line () { return _current; }
|
||||
|
||||
inline ostringstream& Message::newline ()
|
||||
{
|
||||
if (_current.str().size())
|
||||
_lines.push_back(_current.str());
|
||||
_current.str("");
|
||||
return _current;
|
||||
}
|
||||
|
||||
void Message::print ( ostream& o )
|
||||
{
|
||||
if (not _header.empty()) _indent = _header.size()+1;
|
||||
|
||||
string head ( _indent, ' ' );
|
||||
for ( size_t i=0 ; i<_lines.size() ; ++i ) {
|
||||
if ((i == 0) and not _header.empty()) o << _header << " ";
|
||||
else o << head;
|
||||
o << _lines[i] << endl;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
class TopologicalPairing {
|
||||
public:
|
||||
TopologicalPairing ( KatanaEngine*, Net* );
|
||||
bool doPairing ();
|
||||
void _doSelfPairing ();
|
||||
void _doDualPairing ();
|
||||
AutoContactTerminal* _getSymmetricTerminal ( AutoContactTerminal* masterContact );
|
||||
Component* _findMiddleComponent ();
|
||||
private:
|
||||
KatanaEngine* _katana;
|
||||
AutoSegment* _seed;
|
||||
DataSymmetric* _data;
|
||||
};
|
||||
|
||||
|
||||
TopologicalPairing::TopologicalPairing ( KatanaEngine* katana, Net* net )
|
||||
: _katana (katana)
|
||||
, _seed (NULL)
|
||||
, _data (NULL)
|
||||
{
|
||||
_data = _katana->getDataSymmetric( net );
|
||||
if (not _data)
|
||||
_data = _katana->addDataSymmetric( net );
|
||||
|
||||
if (_data and (_data->getNet() != net) ) _data = NULL;
|
||||
}
|
||||
|
||||
|
||||
bool TopologicalPairing::doPairing ()
|
||||
{
|
||||
if (not _data) return false;
|
||||
if (not _data->isValid()) return _data->isValid();
|
||||
|
||||
DebugSession::open( _data->getNet(), 144, 146 );
|
||||
|
||||
cmess2 << " - Net: \"" << _data->getNet()->getName() << "\" ";
|
||||
cmess2 << "@" << DbU::getValueString(_data->getSymAxis()) << " ";
|
||||
cmess2 << (_data->isSymVertical() ? "Vertical" : "Horizontal") << " ";
|
||||
if (_data->getSymNet()) cmess2 << "(paired: \"" << _data->getSymNet()->getName() << "\")";
|
||||
else cmess2 << "(self symmetric)";
|
||||
|
||||
if (_data->getSymNet()) _doDualPairing();
|
||||
else _doSelfPairing();
|
||||
|
||||
if (_data->isValid()) _data->checkPairing();
|
||||
|
||||
DebugSession::close();
|
||||
|
||||
return _data->isValid();
|
||||
}
|
||||
|
||||
|
||||
void TopologicalPairing::_doSelfPairing ()
|
||||
{
|
||||
Component* middle = _findMiddleComponent();
|
||||
|
||||
AutoSegment* _seed = Session::base()->lookup( dynamic_cast<Segment*>( middle ) );
|
||||
if (_seed) {
|
||||
for ( AutoSegment* segment : _seed->getConnecteds(Flags::Source) )
|
||||
_data->addReference( segment );
|
||||
|
||||
for ( AutoSegment* segment : _seed->getConnecteds(Flags::Target) )
|
||||
_data->addSymmetrical( segment );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void TopologicalPairing::_doDualPairing ()
|
||||
{
|
||||
for ( Contact* terminal : _data->getNet()->getContacts() ) {
|
||||
AutoContactTerminal* autoTerminal = dynamic_cast<AutoContactTerminal*>(Session::lookup( terminal ));
|
||||
if (autoTerminal) {
|
||||
if (not autoTerminal->isEndPoint()) continue;
|
||||
|
||||
_seed = autoTerminal->getSegment();
|
||||
unsigned int flags = (_seed->getAutoSource() == autoTerminal) ? Flags::Target : Flags::Source;
|
||||
for ( AutoSegment* segment : _seed->getConnecteds(flags) )
|
||||
_data->addReference( segment );
|
||||
|
||||
AutoContactTerminal* symTerminal = _getSymmetricTerminal( autoTerminal );
|
||||
if (not symTerminal) { _data->setValid( false ); break; }
|
||||
|
||||
AutoSegment* symSeed = symTerminal->getSegment();
|
||||
if (not symSeed) { _data->setValid( false ); break; }
|
||||
|
||||
flags = (symSeed->getAutoSource() == symTerminal) ? Flags::Target : Flags::Source;
|
||||
for ( AutoSegment* segment : symSeed->getConnecteds(flags) ) {
|
||||
_data->addSymmetrical( segment );
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
AutoContactTerminal* TopologicalPairing::_getSymmetricTerminal ( AutoContactTerminal* masterContact )
|
||||
{
|
||||
Point mirror = masterContact->getCenter();
|
||||
_data->getSymmetrical( mirror );
|
||||
|
||||
GCell* mirrorGCell = _katana->getGCellUnder( mirror );
|
||||
if (not mirrorGCell) {
|
||||
cerr << Error( "getSymmetricTerminal() No GCell under symmetric position (%s,%s)."
|
||||
, DbU::getValueString(mirror.getX()).c_str()
|
||||
, DbU::getValueString(mirror.getY()).c_str()
|
||||
) << endl;
|
||||
_data->setValid( false );
|
||||
return NULL;
|
||||
}
|
||||
|
||||
for ( AutoContact* mirrorContact : mirrorGCell->getContacts() ) {
|
||||
if (mirrorContact->getNet() == _data->getSymNet()) {
|
||||
AutoContactTerminal* symContact = dynamic_cast<AutoContactTerminal*>( mirrorContact );
|
||||
if (symContact) return symContact;
|
||||
}
|
||||
}
|
||||
|
||||
cerr << Error( "getSymmetricTerminal() Missing terminal contact in symmetric GCell."
|
||||
) << endl;
|
||||
|
||||
_data->setValid( false );
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
Component* TopologicalPairing::_findMiddleComponent ()
|
||||
{
|
||||
DbU::Unit axis = _data->getSymAxis();
|
||||
Component* middle = NULL;
|
||||
|
||||
if (_data->isSymVertical()) {
|
||||
for ( Component* component : _data->getNet()->getComponents() ) {
|
||||
Horizontal* horizontal = dynamic_cast<Horizontal*>(component);
|
||||
if (horizontal) {
|
||||
if ( (horizontal->getSourceX() < axis) and (axis < horizontal->getTargetX()) ) {
|
||||
if (not middle) middle = horizontal;
|
||||
else {
|
||||
cerr << Error( "::findMiddleComponent(): Multiple middle Horizontal candidates on \"%s\"\n"
|
||||
" %s\n"
|
||||
" %s"
|
||||
, getString(_data->getNet()->getName()).c_str()
|
||||
, getString(middle).c_str()
|
||||
, getString(horizontal).c_str()
|
||||
) << endl;
|
||||
_data->setValid( false );
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Vertical* vertical = dynamic_cast<Vertical*>(component);
|
||||
if (vertical) {
|
||||
if (vertical->getSourceX() == axis) {
|
||||
if (not middle) middle = vertical;
|
||||
else {
|
||||
cerr << Error( "::findMiddleComponent(): Multiple middle Vertical candidates on \"%s\"\n"
|
||||
" %s\n"
|
||||
" %s"
|
||||
, getString(_data->getNet()->getName()).c_str()
|
||||
, getString(middle).c_str()
|
||||
, getString(vertical).c_str()
|
||||
) << endl;
|
||||
_data->setValid( false );
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
RoutingPad* rp = dynamic_cast<RoutingPad*>(component);
|
||||
if (rp) {
|
||||
if ( (rp->getSourcePosition().getX() < axis) and (axis < rp->getTargetPosition().getX()) ) {
|
||||
if (not middle) middle = rp;
|
||||
else {
|
||||
cerr << Error( "::findMiddleComponent(): Multiple middle Horizontal candidates on \"%s\"\n"
|
||||
" %s\n"
|
||||
" %s"
|
||||
, getString(_data->getNet()->getName()).c_str()
|
||||
, getString(middle).c_str()
|
||||
, getString(rp).c_str()
|
||||
) << endl;
|
||||
_data->setValid( false );
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for ( Component* component : _data->getNet()->getComponents() ) {
|
||||
Vertical* vertical = dynamic_cast<Vertical*>(component);
|
||||
if (vertical) {
|
||||
if ( (vertical->getSourceY() < axis) and (axis > vertical->getTargetY()) ) {
|
||||
if (not middle) middle = vertical;
|
||||
else {
|
||||
cerr << Error( "::findMiddleComponent(): Multiple middle Vertical candidates on \"%s\"\n"
|
||||
" %s\n"
|
||||
" %s"
|
||||
, getString(_data->getNet()->getName()).c_str()
|
||||
, getString(middle).c_str()
|
||||
, getString(vertical).c_str()
|
||||
) << endl;
|
||||
_data->setValid( false );
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Horizontal* horizontal = dynamic_cast<Horizontal*>(component);
|
||||
if (horizontal) {
|
||||
if (horizontal->getSourceY() == axis) {
|
||||
if (not middle) middle = horizontal;
|
||||
else {
|
||||
cerr << Error( "::findMiddleComponent(): Multiple middle Horizontal candidates on \"%s\"\n"
|
||||
" %s\n"
|
||||
" %s"
|
||||
, getString(_data->getNet()->getName()).c_str()
|
||||
, getString(middle).c_str()
|
||||
, getString(horizontal).c_str()
|
||||
) << endl;
|
||||
_data->setValid( false );
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
RoutingPad* rp = dynamic_cast<RoutingPad*>(component);
|
||||
if (rp) {
|
||||
if ( (rp->getSourcePosition().getY() < axis) and (axis > rp->getTargetPosition().getY()) ) {
|
||||
if (not middle) middle = rp;
|
||||
else {
|
||||
cerr << Error( "::findMiddleComponent(): Multiple middle Horizontal candidates on \"%s\"\n"
|
||||
" %s\n"
|
||||
" %s"
|
||||
, getString(_data->getNet()->getName()).c_str()
|
||||
, getString(middle).c_str()
|
||||
, getString(rp).c_str()
|
||||
) << endl;
|
||||
_data->setValid( false );
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return middle;
|
||||
}
|
||||
|
||||
|
||||
} // Anonymous namespace.
|
||||
|
||||
|
||||
namespace Katana {
|
||||
|
||||
using namespace std;
|
||||
|
||||
|
||||
void KatanaEngine::runSymmetricRouter ()
|
||||
{
|
||||
for ( Net* net : getCell()->getNets() ) {
|
||||
TopologicalPairing(this,net).doPairing();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
} // Katana namespace.
|
|
@ -510,7 +510,7 @@ namespace Katana {
|
|||
{
|
||||
if (not hasSourceDogleg()) return NULL;
|
||||
|
||||
unsigned int direction = perpandicularTo( getDirection() );
|
||||
Flags direction = perpandicularTo( getDirection() );
|
||||
TrackElement* dogleg = NULL;
|
||||
for( Segment* segment : base()->getAutoSource()->getSlaveComponents().getSubSet<Segment*>() ) {
|
||||
dogleg = Session::lookup( segment );
|
||||
|
@ -527,7 +527,7 @@ namespace Katana {
|
|||
{
|
||||
if (not hasSourceDogleg()) return NULL;
|
||||
|
||||
unsigned int direction = perpandicularTo( getDirection() );
|
||||
Flags direction = perpandicularTo( getDirection() );
|
||||
TrackElement* dogleg = NULL;
|
||||
for( Segment* segment : base()->getAutoTarget()->getSlaveComponents().getSubSet<Segment*>() ) {
|
||||
dogleg = Session::lookup( segment );
|
||||
|
|
|
@ -26,24 +26,25 @@ namespace Katana {
|
|||
public:
|
||||
typedef Anabatic::Flags Super;
|
||||
public:
|
||||
static const unsigned int AllowDoglegReuse;
|
||||
static const unsigned int DataSelf;
|
||||
static const unsigned int Nearest;
|
||||
static const unsigned int Force;
|
||||
static const unsigned int ResetCount;
|
||||
static const unsigned int WithConstraints;
|
||||
static const unsigned int MoveToLeft;
|
||||
static const unsigned int MoveToRight;
|
||||
static const unsigned int LoadingStage;
|
||||
static const unsigned int SlowMotion;
|
||||
static const unsigned int PreRoutedStage;
|
||||
static const uint64_t AllowDoglegReuse;
|
||||
static const uint64_t DataSelf;
|
||||
static const uint64_t Nearest;
|
||||
static const uint64_t Force;
|
||||
static const uint64_t ResetCount;
|
||||
static const uint64_t WithConstraints;
|
||||
static const uint64_t MoveToLeft;
|
||||
static const uint64_t MoveToRight;
|
||||
static const uint64_t LoadingStage;
|
||||
static const uint64_t SlowMotion;
|
||||
static const uint64_t PreRoutedStage;
|
||||
static const uint64_t SymmetricStage;
|
||||
public:
|
||||
inline Flags ( unsigned int );
|
||||
inline Flags ( uint64_t );
|
||||
inline Flags ( const Super& );
|
||||
};
|
||||
|
||||
|
||||
inline Flags::Flags ( unsigned int flags ) : Super(flags) { }
|
||||
inline Flags::Flags ( uint64_t flags ) : Super(flags) { }
|
||||
inline Flags::Flags ( const Flags::Super& base ) : Super(base) { }
|
||||
|
||||
|
||||
|
|
|
@ -0,0 +1,97 @@
|
|||
// -*- C++ -*-
|
||||
//
|
||||
// This file is part of the Coriolis Software.
|
||||
// Copyright (c) UPMC 2008-2016, All Rights Reserved
|
||||
//
|
||||
// +-----------------------------------------------------------------+
|
||||
// | C O R I O L I S |
|
||||
// | K i t e - D e t a i l e d R o u t e r |
|
||||
// | |
|
||||
// | Author : Jean-Paul CHAPUT |
|
||||
// | E-mail : Jean-Paul.Chaput@lip6.fr |
|
||||
// | =============================================================== |
|
||||
// | C++ Header : "./katana/DataSymmetric.h" |
|
||||
// +-----------------------------------------------------------------+
|
||||
|
||||
|
||||
#ifndef KATANA_DATA_SYMMETRIC_H
|
||||
#define KATANA_DATA_SYMMETRIC_H
|
||||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <array>
|
||||
#include "hurricane/Net.h"
|
||||
#include "hurricane/NetRoutingProperty.h"
|
||||
|
||||
namespace Hurricane {
|
||||
class Record;
|
||||
}
|
||||
|
||||
namespace Anabatic {
|
||||
class AutoSegment;
|
||||
}
|
||||
|
||||
|
||||
namespace Katana {
|
||||
|
||||
using Hurricane::Record;
|
||||
using Hurricane::DbU;
|
||||
using Hurricane::Point;
|
||||
using Hurricane::Net;
|
||||
using Hurricane::NetRoutingState;
|
||||
using Hurricane::NetRoutingExtension;
|
||||
using Anabatic::AutoSegment;
|
||||
|
||||
|
||||
class DataSymmetric {
|
||||
public:
|
||||
static DataSymmetric* create ( Net* );
|
||||
public:
|
||||
inline bool isValid () const;
|
||||
inline bool isSymVertical () const;
|
||||
inline Net* getNet () const;
|
||||
inline DbU::Unit getSymAxis () const;
|
||||
inline Net* getSymNet () const;
|
||||
inline Point& getSymmetrical ( Point& ) const;
|
||||
AutoSegment* getSymmetrical ( AutoSegment* ) const;
|
||||
void addSymmetrical ( AutoSegment* );
|
||||
inline void addReference ( AutoSegment* );
|
||||
inline void setValid ( bool );
|
||||
bool checkPairing ();
|
||||
void print ( std::ostream& ) const;
|
||||
Record* _getRecord () const;
|
||||
std::string _getString () const;
|
||||
private:
|
||||
DataSymmetric ( Net* );
|
||||
private:
|
||||
bool _valid;
|
||||
Net* _net;
|
||||
Net* _symNet;
|
||||
NetRoutingState* _state;
|
||||
std::vector< std::array<AutoSegment*,2> > _paireds;
|
||||
size_t _symIndex;
|
||||
};
|
||||
|
||||
|
||||
inline bool DataSymmetric::isValid () const { return _valid; }
|
||||
inline bool DataSymmetric::isSymVertical () const { return _state->isSymVertical(); }
|
||||
inline Net* DataSymmetric::getNet () const { return _net; }
|
||||
inline DbU::Unit DataSymmetric::getSymAxis () const { return _state->getSymAxis(); }
|
||||
inline Net* DataSymmetric::getSymNet () const { return _symNet; }
|
||||
inline void DataSymmetric::addReference ( AutoSegment* segment ) { _paireds.push_back( {segment,NULL} ); }
|
||||
inline void DataSymmetric::setValid ( bool state ) { _valid = state; }
|
||||
|
||||
inline Point& DataSymmetric::getSymmetrical ( Point& point ) const
|
||||
{
|
||||
if (_state->isSymVertical()) point.setX( 2*getSymAxis() - point.getX() );
|
||||
else point.setY( 2*getSymAxis() - point.getY() );
|
||||
return point;
|
||||
}
|
||||
|
||||
|
||||
} // Katana namespace.
|
||||
|
||||
#endif // KATANA_DATA_SYMMETRIC_H
|
||||
|
||||
|
||||
INSPECTOR_P_SUPPORT(Katana::DataSymmetric);
|
|
@ -37,6 +37,7 @@ namespace Knik {
|
|||
#include "katana/Constants.h"
|
||||
#include "katana/TrackElement.h"
|
||||
#include "katana/Configuration.h"
|
||||
#include "katana/DataSymmetric.h"
|
||||
|
||||
|
||||
namespace Katana {
|
||||
|
@ -85,6 +86,7 @@ namespace Katana {
|
|||
RoutingPlane* getRoutingPlaneByIndex ( size_t index ) const;
|
||||
RoutingPlane* getRoutingPlaneByLayer ( const Layer* ) const;
|
||||
Track* getTrackByPosition ( const Layer*, DbU::Unit axis, unsigned int mode=Constant::Nearest ) const;
|
||||
DataSymmetric* getDataSymmetric ( Net* );
|
||||
inline void printConfiguration () const;
|
||||
void printCompletion () const;
|
||||
void dumpMeasures ( std::ostream& ) const;
|
||||
|
@ -98,6 +100,7 @@ namespace Katana {
|
|||
inline void setRipupCost ( unsigned int );
|
||||
inline void setHTracksReservedLocal ( size_t );
|
||||
inline void setVTracksReservedLocal ( size_t );
|
||||
DataSymmetric* addDataSymmetric ( Net* );
|
||||
void setupPowerRails ();
|
||||
void protectRoutingPads ();
|
||||
void preProcess ();
|
||||
|
@ -110,6 +113,7 @@ namespace Katana {
|
|||
void analogInit ();
|
||||
void runNegociate ( unsigned int flags=Flags::NoFlags );
|
||||
void runGlobalRouter ();
|
||||
void runSymmetricRouter ();
|
||||
void runTest ();
|
||||
virtual void finalizeLayout ();
|
||||
void _runKatanaInit ();
|
||||
|
@ -124,14 +128,15 @@ namespace Katana {
|
|||
virtual string _getTypeName () const;
|
||||
private:
|
||||
// Attributes.
|
||||
static Name _toolName;
|
||||
protected:
|
||||
CellViewer* _viewer;
|
||||
Configuration* _configuration;
|
||||
vector<RoutingPlane*> _routingPlanes;
|
||||
NegociateWindow* _negociateWindow;
|
||||
double _minimumWL;
|
||||
mutable bool _toolSuccess;
|
||||
static Name _toolName;
|
||||
protected:
|
||||
CellViewer* _viewer;
|
||||
Configuration* _configuration;
|
||||
vector<RoutingPlane*> _routingPlanes;
|
||||
NegociateWindow* _negociateWindow;
|
||||
double _minimumWL;
|
||||
std::map<Net*,DataSymmetric*> _symmetrics;
|
||||
mutable bool _toolSuccess;
|
||||
protected:
|
||||
// Constructors & Destructors.
|
||||
KatanaEngine ( Cell* );
|
||||
|
|
|
@ -10,7 +10,7 @@
|
|||
// | Author : Jean-Paul CHAPUT |
|
||||
// | E-mail : Jean-Paul.Chaput@asim.lip6.fr |
|
||||
// | =============================================================== |
|
||||
// | C++ Header : "./katana/SegmentFsm.h" |
|
||||
// | C++ Header : "./katana/SegmentFsm.h" |
|
||||
// +-----------------------------------------------------------------+
|
||||
|
||||
|
||||
|
|
|
@ -24,12 +24,14 @@
|
|||
namespace Hurricane {
|
||||
class Record;
|
||||
class Net;
|
||||
class Contact;
|
||||
class Segment;
|
||||
}
|
||||
|
||||
#include "anabatic/Session.h"
|
||||
namespace Anabatic {
|
||||
class GCell;
|
||||
class AutoContact;
|
||||
class AutoSegment;
|
||||
}
|
||||
|
||||
|
@ -41,8 +43,10 @@ namespace Katana {
|
|||
using std::string;
|
||||
using Hurricane::Record;
|
||||
using Hurricane::Net;
|
||||
using Hurricane::Contact;
|
||||
using Hurricane::Segment;
|
||||
using Hurricane::DbU;
|
||||
using Anabatic::AutoContact;
|
||||
using Anabatic::AutoSegment;
|
||||
|
||||
class Track;
|
||||
|
@ -77,6 +81,7 @@ namespace Katana {
|
|||
inline static void addMoveEvent ( TrackElement* , Track* );
|
||||
inline static void addSortEvent ( Track*, bool forced=false );
|
||||
inline static size_t revalidate ();
|
||||
static AutoContact* lookup ( Contact* );
|
||||
static TrackElement* lookup ( Segment* );
|
||||
static TrackElement* lookup ( AutoSegment* );
|
||||
static Session* _open ( KatanaEngine* );
|
||||
|
|
Loading…
Reference in New Issue