34static Vec_Int_t * Abc_NtkRetimeGetLags(
Abc_Ntk_t * pNtk,
int nIterLimit,
int fVerbose );
35static int Abc_NtkRetimeSearch_rec(
Abc_Ntk_t * pNtk,
Vec_Ptr_t * vNodes,
Vec_Ptr_t * vLatches,
int FiMin,
int FiMax,
int nMaxIters,
int fVerbose );
36static int Abc_NtkRetimeForPeriod(
Abc_Ntk_t * pNtk,
Vec_Ptr_t * vNodes,
Vec_Ptr_t * vLatches,
int Fi,
int nMaxIters,
int fVerbose );
38static int Abc_NtkRetimePosOverLimit(
Abc_Ntk_t * pNtk,
int Fi );
42static inline int Abc_NodeComputeLag(
int LValue,
int Fi ) {
return (LValue + (1<<16)*Fi)/Fi - (1<<16) - (
int)(LValue % Fi == 0); }
43static inline int Abc_NodeGetLValue(
Abc_Obj_t * pNode ) {
return (
int)(ABC_PTRUINT_T)pNode->
pCopy; }
44static inline void Abc_NodeSetLValue(
Abc_Obj_t * pNode,
int Value ) { pNode->
pCopy = (
Abc_Obj_t *)(ABC_PTRUINT_T)Value; }
64 int nLatches = Abc_NtkLatchNum(pNtk);
65 assert( Abc_NtkIsLogic( pNtk ) );
67 vLags = Abc_NtkRetimeGetLags( pNtk, nIterLimit, fVerbose );
75 fprintf( stdout,
"Abc_NtkRetimeLValue(): Network check has failed.\n" );
77 return nLatches - Abc_NtkLatchNum(pNtk);
96 int i, FiMax, FiBest, RetValue;
105 vLatches = Abc_ManCollectLatches( pNtk );
106 if ( !Abc_NtkRetimeForPeriod( pNtk, vNodes, vLatches, FiMax, nIterLimit, fVerbose ) )
108 Vec_PtrFree( vLatches );
109 Vec_PtrFree( vNodes );
110 printf(
"Abc_NtkRetimeGetLags() error: The upper bound on the clock period cannot be computed.\n" );
111 return Vec_IntStart( Abc_NtkObjNumMax(pNtk) + 1 );
116 FiBest = Abc_NtkRetimeSearch_rec( pNtk, vNodes, vLatches, 0, FiMax, nIterLimit, fVerbose );
117clkIter = Abc_Clock() - clk;
120 RetValue = Abc_NtkRetimeForPeriod( pNtk, vNodes, vLatches, FiBest, nIterLimit, fVerbose );
126 Abc_NodeSetLValue( pNode, 0 );
129 vLags = Vec_IntStart( Abc_NtkObjNumMax(pNtk) + 1 );
132 NodeLag = Abc_NodeComputeLag( Abc_NodeGetLValue(pNode), FiBest );
133 Vec_IntWriteEntry( vLags, pNode->
Id, NodeLag );
146 printf(
"The best clock period is %3d. (Currently, network is not modified.)\n", FiBest );
156 Vec_PtrFree( vNodes );
157 Vec_PtrFree( vLatches );
172int Abc_NtkRetimeSearch_rec(
Abc_Ntk_t * pNtk,
Vec_Ptr_t * vNodes,
Vec_Ptr_t * vLatches,
int FiMin,
int FiMax,
int nMaxIters,
int fVerbose )
176 if ( FiMin + 1 == FiMax )
178 Median = FiMin + (FiMax - FiMin)/2;
179 if ( Abc_NtkRetimeForPeriod( pNtk, vNodes, vLatches, Median, nMaxIters, fVerbose ) )
180 return Abc_NtkRetimeSearch_rec( pNtk, vNodes, vLatches, FiMin, Median, nMaxIters, fVerbose );
182 return Abc_NtkRetimeSearch_rec( pNtk, vNodes, vLatches, Median, FiMax, nMaxIters, fVerbose );
199 int c, i, fConverged;
202 if ( Abc_ObjFaninNum(pObj) == 0 )
203 Abc_NodeSetLValue( pObj, 0 );
208 for ( c = 1; c <= nMaxIters; c++ )
210 if ( !Abc_NtkRetimeUpdateLValue( pNtk, vNodes, vLatches, Fi ) )
215 if ( Abc_NtkRetimePosOverLimit(pNtk, Fi) )
222 printf(
"Period = %3d. Iterations = %3d. Infeasible %s\n", Fi, c, (c > nMaxIters)?
"(timeout)" :
"" );
224 printf(
"Period = %3d. Iterations = %3d. Feasible\n", Fi, c );
252 int i, k, lValueNew, fChange;
257 assert( Abc_ObjIsNode(pObj) );
261 if ( lValueNew < Abc_NodeGetLValue(pFanin) )
262 lValueNew = Abc_NodeGetLValue(pFanin);
265 if ( Abc_NodeGetLValue(pObj) < lValueNew )
267 Abc_NodeSetLValue( pObj, lValueNew );
273 Abc_NodeSetLValue( Abc_ObjFanout0(pObj), Abc_NodeGetLValue(Abc_ObjFanin0(Abc_ObjFanin0(pObj))) - Fi );
288int Abc_NtkRetimePosOverLimit(
Abc_Ntk_t * pNtk,
int Fi )
293 if ( Abc_NodeGetLValue(Abc_ObjFanin0(pObj)) > Fi )
312 if ( !Abc_ObjIsLatch(pObj) )
315 if ( Abc_NodeIsTravIdCurrent(pObj) )
317 Abc_NodeSetTravIdCurrent(pObj);
319 pDriver = Abc_ObjFanin0(Abc_ObjFanin0(pObj));
321 if ( Abc_ObjIsBo(pDriver) )
324 Vec_PtrPush( vLatches, pObj );
343 vLatches = Vec_PtrAlloc( Abc_NtkLatchNum(pNtk) );
344 Abc_NtkIncrementTravId( pNtk );
347 assert( Vec_PtrSize(vLatches) == Abc_NtkLatchNum(pNtk) );
365 int fChanges, fForward, nTotalMoves, Lag, Counter, i;
372 Lag = Vec_IntEntry( vLags, pObj->
Id );
375 fForward = (Lag < 0);
381 Vec_IntAddToEntry( vLags, pObj->
Id, fForward? 1 : -1 );
384 }
while ( fChanges );
386 printf(
"Total latch moves = %d.\n", nTotalMoves );
390 Counter += (Vec_IntEntry( vLags, pObj->
Id ) != 0);
392 printf(
"Warning! The number of nodes with unrealized lag = %d.\n", Counter );
struct Abc_Obj_t_ Abc_Obj_t
#define Abc_NtkForEachPo(pNtk, pPo, i)
#define Abc_NtkForEachLatch(pNtk, pObj, i)
ABC_DLL Vec_Ptr_t * Abc_NtkDfs(Abc_Ntk_t *pNtk, int fCollectAll)
ABC_DLL int Abc_NtkCheck(Abc_Ntk_t *pNtk)
FUNCTION DEFINITIONS ///.
#define Abc_NtkForEachObj(pNtk, pObj, i)
ITERATORS ///.
#define Abc_ObjForEachFanin(pObj, pFanin, i)
struct Abc_Ntk_t_ Abc_Ntk_t
ABC_DLL int Abc_NtkLevel(Abc_Ntk_t *pNtk)
#define Abc_NtkForEachNode(pNtk, pNode, i)
#define ABC_INFINITY
MACRO DEFINITIONS ///.
#define ABC_NAMESPACE_IMPL_START
#define ABC_NAMESPACE_IMPL_END
typedefABC_NAMESPACE_IMPL_START struct Vec_Int_t_ Vec_Int_t
DECLARATIONS ///.
void Abc_NtkRetimeNode(Abc_Obj_t *pObj, int fForward, int fInitial)
int Abc_NtkRetimeNodeIsEnabled(Abc_Obj_t *pObj, int fForward)
int Abc_NtkRetimeLValue(Abc_Ntk_t *pNtk, int nIterLimit, int fVerbose)
FUNCTION DEFINITIONS ///.
void Abc_ManCollectLatches_rec(Abc_Obj_t *pObj, Vec_Ptr_t *vLatches)
typedefABC_NAMESPACE_HEADER_START struct Vec_Ptr_t_ Vec_Ptr_t
INCLUDES ///.
#define Vec_PtrForEachEntry(Type, vVec, pEntry, i)
MACRO DEFINITIONS ///.