diff --git a/src/aig/gia/gia.h b/src/aig/gia/gia.h index 68266bb2d..dab6770bb 100644 --- a/src/aig/gia/gia.h +++ b/src/aig/gia/gia.h @@ -241,6 +241,9 @@ struct Gia_Man_t_ Vec_Int_t vSuppVars; // used variables Vec_Int_t vVarMap; // used variables Gia_Dat_t * pUData; + // retiming data + Vec_Str_t * vStopsF; + Vec_Str_t * vStopsB; }; diff --git a/src/aig/gia/giaMan.c b/src/aig/gia/giaMan.c index 0efb5b29f..a48da5c29 100644 --- a/src/aig/gia/giaMan.c +++ b/src/aig/gia/giaMan.c @@ -156,6 +156,8 @@ void Gia_ManStop( Gia_Man_t * p ) Vec_IntErase( &p->vHash ); Vec_IntErase( &p->vHTable ); Vec_IntErase( &p->vRefs ); + Vec_StrFreeP( &p->vStopsF ); + Vec_StrFreeP( &p->vStopsB ); ABC_FREE( p->pData2 ); ABC_FREE( p->pTravIds ); ABC_FREE( p->pPlacement ); diff --git a/src/aig/gia/giaMini.c b/src/aig/gia/giaMini.c index c0473fea3..85647eac5 100644 --- a/src/aig/gia/giaMini.c +++ b/src/aig/gia/giaMini.c @@ -1228,6 +1228,98 @@ void Gia_MiniAigGenerateFromFile() Mini_AigStop( p ); } +/**Function************************************************************* + + Synopsis [] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ +Vec_Str_t * Gia_ManRetimableF( Gia_Man_t * p, int * pRst, int * pSet, int * pEna ) +{ + Vec_Str_t * vStops = Vec_StrStart( Gia_ManObjNum(p) ); + Vec_Int_t * vTemps = Vec_IntStartFull( 3*Gia_ManObjNum(p) ); + Gia_Obj_t * pObj, * pObjRi, * pObjRo; int i; + char * pStops = Vec_StrArray(vStops); + assert( Gia_ManRegNum(p) > 0 ); + Gia_ManForEachRiRo( p, pObjRi, pObjRo, i ) { + Vec_IntWriteEntry( vTemps, 3*Gia_ObjId(p, pObjRo) + 0, pRst[i] ); + Vec_IntWriteEntry( vTemps, 3*Gia_ObjId(p, pObjRo) + 1, pSet[i] ); + Vec_IntWriteEntry( vTemps, 3*Gia_ObjId(p, pObjRo) + 2, pEna[i] ); + } + Gia_ManForEachAnd( p, pObj, i ) { + int * pFan0 = Vec_IntEntryP( vTemps, 3*Gia_ObjFaninId0(pObj, i) ); + int * pFan1 = Vec_IntEntryP( vTemps, 3*Gia_ObjFaninId1(pObj, i) ); + int * pNode = Vec_IntEntryP( vTemps, 3*i ); + pStops[i] = (char)1; + if ( pFan0[0] != -1 && pFan0[0] == pFan1[0] && pFan0[1] == pFan1[1] && pFan0[2] == pFan1[2] ) + pStops[i] = (char)0, pNode[0] = pFan0[0], pNode[1] = pFan0[1], pNode[2] = pFan0[2]; + } + Vec_IntFree( vTemps ); + return vStops; +} +Vec_Str_t * Gia_ManRetimableB( Gia_Man_t * p, int * pRst, int * pSet, int * pEna ) +{ + Vec_Str_t * vStops = Vec_StrStart( Gia_ManObjNum(p) ); + Vec_Int_t * vTemps = Vec_IntStartFull( 3*Gia_ManObjNum(p) ); + Gia_Obj_t * pObj, * pObjRi, * pObjRo; int i, n; + char * pStops = Vec_StrArray(vStops); + assert( Gia_ManRegNum(p) > 0 ); + Gia_ManForEachRiRo( p, pObjRi, pObjRo, i ) { + Vec_IntWriteEntry( vTemps, 3*Gia_ObjFaninId0p(p, pObjRi) + 0, pRst[i] ); + Vec_IntWriteEntry( vTemps, 3*Gia_ObjFaninId0p(p, pObjRi) + 1, pSet[i] ); + Vec_IntWriteEntry( vTemps, 3*Gia_ObjFaninId0p(p, pObjRi) + 2, pEna[i] ); + } + Gia_ManForEachAndReverse( p, pObj, i ) { + int iFans[2] = { Gia_ObjFaninId0(pObj, i), Gia_ObjFaninId1(pObj, i) }; + int * pFans[2] = { Vec_IntEntryP( vTemps, 3*iFans[0] ), Vec_IntEntryP( vTemps, 3*iFans[1] ) }; + int * pNode = Vec_IntEntryP( vTemps, 3*i ); + if ( pNode[0] == -1 ) + continue; + for ( n = 0; n < 2; n++ ) + if ( pFans[n][0] == -1 ) + pStops[iFans[n]] = (char)1, pFans[n][0] = pNode[0], pFans[n][1] = pNode[1], pFans[n][2] = pNode[2]; + else if ( pFans[n][0] != pNode[0] || pFans[n][1] != pNode[1] || pFans[n][2] != pNode[2] ) + pStops[iFans[n]] = (char)0; + } + pStops[0] = (char)0; + Gia_ManForEachCi( p, pObj, i ) + pStops[Gia_ObjId(p, pObj)] = (char)0; + Gia_ManForEachAnd( p, pObj, i ) + pStops[i] = (char)!pStops[i]; + Vec_IntFree( vTemps ); + return vStops; +} + +/**Function************************************************************* + + Synopsis [] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ +void Abc_FrameSetRetimingData( Abc_Frame_t * pAbc, int * pRst, int * pSet, int * pEna ) +{ + Gia_Man_t * pGia; + if ( pAbc == NULL ) + printf( "ABC framework is not initialized by calling Abc_Start()\n" ); + pGia = Abc_FrameReadGia( pAbc ); + if ( pGia == NULL ) + printf( "Current network in ABC framework is not defined.\n" ); + assert( pGia->vStopsF == NULL ); + assert( pGia->vStopsB == NULL ); + pGia->vStopsF = Gia_ManRetimableF( pGia, pRst, pSet, pEna ); + pGia->vStopsB = Gia_ManRetimableB( pGia, pRst, pSet, pEna ); +} + //////////////////////////////////////////////////////////////////////// /// END OF FILE /// //////////////////////////////////////////////////////////////////////// diff --git a/src/aig/gia/giaSif.c b/src/aig/gia/giaSif.c index db7629fb3..c52ab4dd9 100644 --- a/src/aig/gia/giaSif.c +++ b/src/aig/gia/giaSif.c @@ -490,13 +490,16 @@ int Gia_ManSifCheckIter( Gia_Man_t * p, Vec_Int_t * vCuts, Vec_Int_t * vTimes, i } int Gia_ManSifCheckPeriod( Gia_Man_t * p, Vec_Int_t * vCuts, Vec_Int_t * vTimes, int nLutSize, int Period, int * pIters ) { - Gia_Obj_t * pObj; int i, Id, nSize = nLutSize+1; + Gia_Obj_t * pObj; int i, Id, Stop, nSize = nLutSize+1; assert( Gia_ManRegNum(p) > 0 ); Gia_ManForEachCiId( p, Id, i ) Vec_IntWriteEntry( vCuts, Id*nSize, 1 ); Gia_ManForEachCiId( p, Id, i ) Vec_IntWriteEntry( vCuts, Id*nSize+1, Id << 8 ); Vec_IntFill( vTimes, Gia_ManObjNum(p), -Period ); + if ( p->vStopsF ) + Vec_StrForEachEntry( p->vStopsF, Stop, i ) + if ( Stop ) Vec_IntWriteEntry( vTimes, i, 0 ); Vec_IntWriteEntry( vTimes, 0, 0 ); Gia_ManForEachPi( p, pObj, i ) Vec_IntWriteEntry( vTimes, Gia_ObjId(p, pObj), 0 ); @@ -510,6 +513,10 @@ int Gia_ManSifCheckPeriod( Gia_Man_t * p, Vec_Int_t * vCuts, Vec_Int_t * vTimes, Gia_ManForEachObj( p, pObj, i ) if ( Vec_IntEntry(vTimes, Gia_ObjId(p, pObj)) > 2*Period ) return 0; + if ( p->vStopsB ) + Vec_StrForEachEntry( p->vStopsB, Stop, i ) + if ( Stop && Vec_IntEntry(vTimes, i) > Period ) + return 0; } return 0; } diff --git a/src/base/main/abcapis.h b/src/base/main/abcapis.h index d34306baf..e1e05f4c7 100644 --- a/src/base/main/abcapis.h +++ b/src/base/main/abcapis.h @@ -106,6 +106,9 @@ extern ABC_DLL int * Abc_FrameReadBoxes( Abc_Frame_t * pAbc ); extern ABC_DLL int Abc_FrameReadProbStatus( Abc_Frame_t * pAbc ); extern ABC_DLL void * Abc_FrameReadCex( Abc_Frame_t * pAbc ); +// procedure to set retiming data +extern ABC_DLL void Abc_FrameSetRetimingData( Abc_Frame_t * pAbc, int * pRst, int * pSet, int * pEna ); + // procedure to return sequential equivalences extern ABC_DLL int * Abc_FrameReadMiniAigEquivClasses( Abc_Frame_t * pAbc );