diff --git a/.gitignore b/.gitignore index 203869de1..c745dfb57 100644 --- a/.gitignore +++ b/.gitignore @@ -6,6 +6,7 @@ ReleaseLib/ ReleaseExe/ ReleaseExt/ +_/ _TEST/ lib/abc* lib/m114* diff --git a/src/aig/gia/giaDeep.c b/src/aig/gia/giaDeep.c index 815a546e4..b58169f42 100644 --- a/src/aig/gia/giaDeep.c +++ b/src/aig/gia/giaDeep.c @@ -120,6 +120,7 @@ Gia_Man_t * Gia_ManDeepSynOne( int nNoImpr, int TimeOut, int nAnds, int Seed, in } if ( nTimeToStop && Abc_Clock() > nTimeToStop ) { + if ( !Abc_FrameIsBatchMode() ) printf( "Runtime limit (%d sec) is reached after %d iterations.\n", TimeOut, i ); break; } diff --git a/src/aig/gia/giaSimBase.c b/src/aig/gia/giaSimBase.c index 47f645413..97335d378 100644 --- a/src/aig/gia/giaSimBase.c +++ b/src/aig/gia/giaSimBase.c @@ -3689,6 +3689,58 @@ Vec_Str_t * Gia_ManComputeRange( Gia_Man_t * p ) return vOut; } +/**Function************************************************************* + + Synopsis [] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ +void Gia_ManComparePrint( Gia_Man_t * p, Gia_Man_t * q ) +{ + Vec_Wrd_t * vSimsPi = Vec_WrdStartTruthTables( Gia_ManCiNum(p) ); + Vec_Wrd_t * vSimsP = Gia_ManSimPatSimOut( p, vSimsPi, 0 ); + Vec_Wrd_t * vSimsQ = Gia_ManSimPatSimOut( q, vSimsPi, 0 ); + int i, k, nWords = Vec_WrdSize(vSimsPi) / Gia_ManCiNum(p), Count = 0; + Gia_Obj_t * pObjP, * pObjQ; + Gia_ManSetPhase( p ); + Gia_ManSetPhase( q ); + Gia_ManForEachObj( p, pObjP, i ) { + word * pSim = Vec_WrdEntryP( vSimsP, i * nWords ); + if ( pSim[0] & 1 ) Abc_TtNot( pSim, nWords ); + } + Gia_ManForEachObj( q, pObjQ, i ) { + word * pSim = Vec_WrdEntryP( vSimsQ, i * nWords ); + if ( pSim[0] & 1 ) Abc_TtNot( pSim, nWords ); + } + Gia_ManForEachAnd( q, pObjQ, i ) { + word * pSimQ = Vec_WrdEntryP( vSimsQ, i * nWords ); + int fFirst = 1; + Gia_ManForEachObj( p, pObjP, k ) { + word * pSimP = Vec_WrdEntryP( vSimsP, k * nWords ); + if ( !Abc_TtEqual(pSimQ, pSimP, nWords) ) + continue; + if ( fFirst ) { + printf( "%5d :", i ); + fFirst = 0; + Count++; + } + printf( " %5d(%d)", k, pObjQ->fPhase ^ pObjP->fPhase ); + } + if ( !fFirst ) + printf( "\n"); + } + printf( "Found %d equivalent nodes.\n", Count ); + Vec_WrdFree( vSimsP ); + Vec_WrdFree( vSimsQ ); + Vec_WrdFree( vSimsPi ); +} + + //////////////////////////////////////////////////////////////////////// /// END OF FILE /// //////////////////////////////////////////////////////////////////////// diff --git a/src/aig/gia/giaStoch.c b/src/aig/gia/giaStoch.c index 94f539988..57775b5cc 100644 --- a/src/aig/gia/giaStoch.c +++ b/src/aig/gia/giaStoch.c @@ -22,6 +22,19 @@ #include "base/main/main.h" #include "base/cmd/cmd.h" + +#ifdef ABC_USE_PTHREADS + +#ifdef _WIN32 +#include "../lib/pthread.h" +#else +#include +#include +#endif + +#endif + + ABC_NAMESPACE_IMPL_START //////////////////////////////////////////////////////////////////////// @@ -32,6 +45,169 @@ ABC_NAMESPACE_IMPL_START /// FUNCTION DEFINITIONS /// //////////////////////////////////////////////////////////////////////// +/**Function************************************************************* + + Synopsis [Processing on a single core.] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ +Gia_Man_t * Gia_StochProcessOne( Gia_Man_t * p, char * pScript, int Rand, int TimeSecs ) +{ + Gia_Man_t * pNew; + char FileName[100], Command[1000]; + sprintf( FileName, "%06x.aig", Rand ); + Gia_AigerWrite( p, FileName, 0, 0, 0 ); + sprintf( Command, "./abc -q \"&read %s; %s; &write %s\"", FileName, pScript, FileName ); + if ( system( (char *)Command ) ) + { + fprintf( stderr, "The following command has returned non-zero exit status:\n" ); + fprintf( stderr, "\"%s\"\n", (char *)Command ); + fprintf( stderr, "Sorry for the inconvenience.\n" ); + fflush( stdout ); + unlink( FileName ); + return Gia_ManDup(p); + } + pNew = Gia_AigerRead( FileName, 0, 0, 0 ); + unlink( FileName ); + if ( pNew && Gia_ManAndNum(pNew) < Gia_ManAndNum(p) ) + return pNew; + Gia_ManStopP( &pNew ); + return Gia_ManDup(p); +} +void Gia_StochProcessArray( Vec_Ptr_t * vGias, char * pScript, int TimeSecs, int fVerbose ) +{ + Gia_Man_t * pGia, * pNew; int i; + Vec_Int_t * vRands = Vec_IntAlloc( Vec_PtrSize(vGias) ); + Abc_Random(1); + for ( i = 0; i < Vec_PtrSize(vGias); i++ ) + Vec_IntPush( vRands, Abc_Random(0) % 0x1000000 ); + Vec_PtrForEachEntry( Gia_Man_t *, vGias, pGia, i ) + { + pNew = Gia_StochProcessOne( pGia, pScript, Vec_IntEntry(vRands, i), TimeSecs ); + Gia_ManStop( pGia ); + Vec_PtrWriteEntry( vGias, i, pNew ); + } + Vec_IntFree( vRands ); +} + +/**Function************************************************************* + + Synopsis [Processing on a many cores.] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ +#ifndef ABC_USE_PTHREADS + +void Gia_StochProcess( Vec_Ptr_t * vGias, char * pScript, int nProcs, int TimeSecs, int fVerbose ) +{ + Gia_StochProcessArray( vGias, pScript, TimeSecs, fVerbose ); +} + +#else // pthreads are used + + +#define PAR_THR_MAX 100 +typedef struct Gia_StochThData_t_ +{ + Vec_Ptr_t * vGias; + char * pScript; + int Index; + int Rand; + int nTimeOut; + int fWorking; +} Gia_StochThData_t; + +void * Gia_StochWorkerThread( void * pArg ) +{ + Gia_StochThData_t * pThData = (Gia_StochThData_t *)pArg; + volatile int * pPlace = &pThData->fWorking; + Gia_Man_t * pGia, * pNew; + while ( 1 ) + { + while ( *pPlace == 0 ); + assert( pThData->fWorking ); + if ( pThData->Index == -1 ) + { + pthread_exit( NULL ); + assert( 0 ); + return NULL; + } + pGia = (Gia_Man_t *)Vec_PtrEntry( pThData->vGias, pThData->Index ); + pNew = Gia_StochProcessOne( pGia, pThData->pScript, pThData->Rand, pThData->nTimeOut ); + Gia_ManStop( pGia ); + Vec_PtrWriteEntry( pThData->vGias, pThData->Index, pNew ); + pThData->fWorking = 0; + } + assert( 0 ); + return NULL; +} + +void Gia_StochProcess( Vec_Ptr_t * vGias, char * pScript, int nProcs, int TimeSecs, int fVerbose ) +{ + Gia_StochThData_t ThData[PAR_THR_MAX]; + pthread_t WorkerThread[PAR_THR_MAX]; + int i, k, status; + if ( fVerbose ) + printf( "Running concurrent synthesis with %d processes.\n", nProcs ); + fflush( stdout ); + if ( nProcs < 2 ) + return Gia_StochProcessArray( vGias, pScript, TimeSecs, fVerbose ); + // subtract manager thread + nProcs--; + assert( nProcs >= 1 && nProcs <= PAR_THR_MAX ); + // start threads + Abc_Random(1); + for ( i = 0; i < nProcs; i++ ) + { + ThData[i].vGias = vGias; + ThData[i].pScript = pScript; + ThData[i].Index = -1; + ThData[i].Rand = Abc_Random(0) % 0x1000000; + ThData[i].nTimeOut = TimeSecs; + ThData[i].fWorking = 0; + status = pthread_create( WorkerThread + i, NULL, Gia_StochWorkerThread, (void *)(ThData + i) ); assert( status == 0 ); + } + // look at the threads + for ( k = 0; k < Vec_PtrSize(vGias); k++ ) + { + for ( i = 0; i < nProcs; i++ ) + { + if ( ThData[i].fWorking ) + continue; + ThData[i].Index = k; + ThData[i].fWorking = 1; + break; + } + if ( i == nProcs ) + k--; + } + // wait till threads finish + for ( i = 0; i < nProcs; i++ ) + if ( ThData[i].fWorking ) + i = -1; + // stop threads + for ( i = 0; i < nProcs; i++ ) + { + assert( !ThData[i].fWorking ); + // stop + ThData[i].Index = -1; + ThData[i].fWorking = 1; + } +} + +#endif // pthreads are used + + /**Function************************************************************* Synopsis [] @@ -184,7 +360,7 @@ Gia_Man_t * Gia_ManDupDivideOne( Gia_Man_t * p, Vec_Int_t * vCis, Vec_Int_t * vA pNew->vMapping = vMapping; return pNew; } -Vec_Ptr_t * Gia_ManDupDivide( Gia_Man_t * p, Vec_Wec_t * vCis, Vec_Wec_t * vAnds, Vec_Wec_t * vCos, char * pScript ) +Vec_Ptr_t * Gia_ManDupDivide( Gia_Man_t * p, Vec_Wec_t * vCis, Vec_Wec_t * vAnds, Vec_Wec_t * vCos, char * pScript, int nProcs, int TimeOut ) { Vec_Ptr_t * vAigs = Vec_PtrAlloc( Vec_WecSize(vCis) ); int i; for ( i = 0; i < Vec_WecSize(vCis); i++ ) @@ -192,7 +368,8 @@ Vec_Ptr_t * Gia_ManDupDivide( Gia_Man_t * p, Vec_Wec_t * vCis, Vec_Wec_t * vAnds Gia_ManCollectNodes( p, Vec_WecEntry(vCis, i), Vec_WecEntry(vAnds, i), Vec_WecEntry(vCos, i) ); Vec_PtrPush( vAigs, Gia_ManDupDivideOne(p, Vec_WecEntry(vCis, i), Vec_WecEntry(vAnds, i), Vec_WecEntry(vCos, i)) ); } - Gia_ManStochSynthesis( vAigs, pScript ); + //Gia_ManStochSynthesis( vAigs, pScript ); + Gia_StochProcess( vAigs, pScript, nProcs, TimeOut, 0 ); return vAigs; } Gia_Man_t * Gia_ManDupStitch( Gia_Man_t * p, Vec_Wec_t * vCis, Vec_Wec_t * vAnds, Vec_Wec_t * vCos, Vec_Ptr_t * vAigs, int fHash ) @@ -388,7 +565,7 @@ Vec_Wec_t * Gia_ManStochOutputs( Gia_Man_t * p, Vec_Wec_t * vAnds ) SeeAlso [] ***********************************************************************/ -void Gia_ManStochSyn( int nMaxSize, int nIters, int TimeOut, int Seed, int fVerbose, char * pScript ) +void Gia_ManStochSyn( int nMaxSize, int nIters, int TimeOut, int Seed, int fVerbose, char * pScript, int nProcs ) { abctime nTimeToStop = TimeOut ? Abc_Clock() + TimeOut * CLOCKS_PER_SEC : 0; abctime clkStart = Abc_Clock(); @@ -407,7 +584,7 @@ void Gia_ManStochSyn( int nMaxSize, int nIters, int TimeOut, int Seed, int fVerb Vec_Wec_t * vAnds = Gia_ManStochNodes( pGia, nMaxSize, Abc_Random(0) & 0x7FFFFFFF ); Vec_Wec_t * vIns = Gia_ManStochInputs( pGia, vAnds ); Vec_Wec_t * vOuts = Gia_ManStochOutputs( pGia, vAnds ); - Vec_Ptr_t * vAigs = Gia_ManDupDivide( pGia, vIns, vAnds, vOuts, pScript ); + Vec_Ptr_t * vAigs = Gia_ManDupDivide( pGia, vIns, vAnds, vOuts, pScript, nProcs, TimeOut ); Gia_Man_t * pNew = Gia_ManDupStitchMap( pGia, vIns, vAnds, vOuts, vAigs ); int fMapped = Gia_ManHasMapping(pGia) && Gia_ManHasMapping(pNew); Abc_FrameUpdateGia( Abc_FrameGetGlobalFrame(), pNew ); diff --git a/src/base/abc/abcAig.c b/src/base/abc/abcAig.c index 636fe30ae..94bafb53c 100644 --- a/src/base/abc/abcAig.c +++ b/src/base/abc/abcAig.c @@ -897,6 +897,16 @@ void Abc_AigReplace_int( Abc_Aig_t * pMan, Abc_Obj_t * pOld, Abc_Obj_t * pNew, i { if ( Abc_ObjIsCo(pFanout) ) { + pFanin1 = Abc_ObjRegular( pNew ); + if ( pFanin1->fMarkB ) + Abc_AigRemoveFromLevelStructureR( pMan->vLevelsR, pFanin1 ); + if ( fUpdateLevel && pMan->pNtkAig->vLevelsR ) + { + Abc_ObjSetReverseLevel( pFanin1, Abc_ObjReverseLevel(pOld) ); + assert( pFanin1->fMarkB == 0 ); + pFanin1->fMarkB = 1; + Vec_VecPush( pMan->vLevelsR, Abc_ObjReverseLevel(pFanin1), pFanin1 ); + } Abc_ObjPatchFanin( pFanout, pOld, pNew ); continue; } diff --git a/src/base/abc/abcFunc.c b/src/base/abc/abcFunc.c index 84ecf7bf3..805b91daa 100644 --- a/src/base/abc/abcFunc.c +++ b/src/base/abc/abcFunc.c @@ -1265,6 +1265,42 @@ int Abc_NtkToAig( Abc_Ntk_t * pNtk ) } +/**Function************************************************************* + + Synopsis [] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ +void Abc_ObjFaninSort( Abc_Obj_t * pObj ) +{ + Vec_Int_t * vFanins = Abc_ObjFaninVec( pObj ); + char * pCube, * pSop = (char*)pObj->pData; + int i, j, nVars = Abc_SopGetVarNum( pSop ); + assert( nVars == Vec_IntSize(vFanins) ); + for ( i = 0; i < Vec_IntSize(vFanins); i++ ) + for ( j = i+1; j < Vec_IntSize(vFanins); j++ ) + { + if ( Vec_IntEntry(vFanins, i) < Vec_IntEntry(vFanins, j) ) + continue; + ABC_SWAP( int, Vec_IntArray(vFanins)[i], Vec_IntArray(vFanins)[j] ); + for ( pCube = pSop; *pCube; pCube += nVars + 3 ) { + ABC_SWAP( char, pCube[i], pCube[j] ); + } + } +} +void Abc_NtkFaninSort( Abc_Ntk_t * pNtk ) +{ + Abc_Obj_t * pObj; int i; + assert( Abc_NtkIsSopLogic(pNtk) ); + Abc_NtkForEachNode( pNtk, pObj, i ) + Abc_ObjFaninSort( pObj ); +} + //////////////////////////////////////////////////////////////////////// /// END OF FILE /// //////////////////////////////////////////////////////////////////////// diff --git a/src/base/abci/abc.c b/src/base/abci/abc.c index baf0d7eec..76b56d5f4 100644 --- a/src/base/abci/abc.c +++ b/src/base/abci/abc.c @@ -540,6 +540,7 @@ static int Abc_CommandAbc9PoPart ( Abc_Frame_t * pAbc, int argc, cha static int Abc_CommandAbc9GroupProve ( Abc_Frame_t * pAbc, int argc, char ** argv ); static int Abc_CommandAbc9MultiProve ( Abc_Frame_t * pAbc, int argc, char ** argv ); static int Abc_CommandAbc9SplitProve ( Abc_Frame_t * pAbc, int argc, char ** argv ); +static int Abc_CommandAbc9SplitSat ( Abc_Frame_t * pAbc, int argc, char ** argv ); static int Abc_CommandAbc9Bmc ( Abc_Frame_t * pAbc, int argc, char ** argv ); static int Abc_CommandAbc9SBmc ( Abc_Frame_t * pAbc, int argc, char ** argv ); static int Abc_CommandAbc9ChainBmc ( Abc_Frame_t * pAbc, int argc, char ** argv ); @@ -1300,6 +1301,7 @@ void Abc_Init( Abc_Frame_t * pAbc ) Cmd_CommandAdd( pAbc, "ABC9", "&gprove", Abc_CommandAbc9GroupProve, 0 ); Cmd_CommandAdd( pAbc, "ABC9", "&mprove", Abc_CommandAbc9MultiProve, 0 ); Cmd_CommandAdd( pAbc, "ABC9", "&splitprove", Abc_CommandAbc9SplitProve, 0 ); + Cmd_CommandAdd( pAbc, "ABC9", "&splitsat", Abc_CommandAbc9SplitSat, 0 ); Cmd_CommandAdd( pAbc, "ABC9", "&bmc", Abc_CommandAbc9Bmc, 0 ); Cmd_CommandAdd( pAbc, "ABC9", "&bmcs", Abc_CommandAbc9SBmc, 0 ); Cmd_CommandAdd( pAbc, "ABC9", "&chainbmc", Abc_CommandAbc9ChainBmc, 0 ); @@ -11017,6 +11019,7 @@ usage: ***********************************************************************/ int Abc_CommandSop( Abc_Frame_t * pAbc, int argc, char ** argv ) { + extern void Abc_NtkFaninSort( Abc_Ntk_t * pNtk ); Abc_Ntk_t * pNtk = Abc_FrameReadNtk(pAbc); int c, fCubeSort = 1, fMode = -1, nCubeLimit = 1000000; @@ -11072,6 +11075,8 @@ int Abc_CommandSop( Abc_Frame_t * pAbc, int argc, char ** argv ) Abc_Print( -1, "Converting to SOP has failed.\n" ); return 0; } + if ( !fCubeSort ) + Abc_NtkFaninSort( pNtk ); return 0; usage: @@ -13365,6 +13370,7 @@ int Abc_CommandGen( Abc_Frame_t * pAbc, int argc, char ** argv ) int fFpga; int fOneHot; int fRandom; + int fGraph; int fVerbose; char * FileName; char Command[1000]; @@ -13376,6 +13382,7 @@ int Abc_CommandGen( Abc_Frame_t * pAbc, int argc, char ** argv ) extern void Abc_GenFpga( char * pFileName, int nLutSize, int nLuts, int nVars ); extern void Abc_GenOneHot( char * pFileName, int nVars ); extern void Abc_GenRandom( char * pFileName, int nPis ); + extern void Abc_GenGraph( char * pFileName, int nPis ); extern void Abc_GenAdderTree( char * pFileName, int nArgs, int nBits ); // set defaults @@ -13390,9 +13397,10 @@ int Abc_CommandGen( Abc_Frame_t * pAbc, int argc, char ** argv ) fFpga = 0; fOneHot = 0; fRandom = 0; + fGraph = 0; fVerbose = 0; Extra_UtilGetoptReset(); - while ( ( c = Extra_UtilGetopt( argc, argv, "NAKLatsembfnrvh" ) ) != EOF ) + while ( ( c = Extra_UtilGetopt( argc, argv, "NAKLatsembfnrgvh" ) ) != EOF ) { switch ( c ) { @@ -13467,6 +13475,9 @@ int Abc_CommandGen( Abc_Frame_t * pAbc, int argc, char ** argv ) case 'r': fRandom ^= 1; break; + case 'g': + fGraph ^= 1; + break; case 'v': fVerbose ^= 1; break; @@ -13506,6 +13517,8 @@ int Abc_CommandGen( Abc_Frame_t * pAbc, int argc, char ** argv ) Abc_GenOneHot( FileName, nVars ); else if ( fRandom ) Abc_GenRandom( FileName, nVars ); + else if ( fGraph ) + Abc_GenGraph( FileName, nVars ); else if ( fAdderTree ) { printf( "Generating adder tree with %d arguments and %d bits.\n", nArgs, nVars ); @@ -13525,7 +13538,7 @@ int Abc_CommandGen( Abc_Frame_t * pAbc, int argc, char ** argv ) return 0; usage: - Abc_Print( -2, "usage: gen [-NAKL num] [-atsembfnrvh] \n" ); + Abc_Print( -2, "usage: gen [-NAKL num] [-atsembfnrgvh] \n" ); Abc_Print( -2, "\t generates simple circuits\n" ); Abc_Print( -2, "\t-N num : the number of variables [default = %d]\n", nVars ); Abc_Print( -2, "\t-A num : the number of agruments (for adder tree) [default = %d]\n", nArgs ); @@ -13538,6 +13551,7 @@ usage: Abc_Print( -2, "\t-m : generate a multiplier [default = %s]\n", fMulti? "yes": "no" ); Abc_Print( -2, "\t-b : generate a signed Booth multiplier [default = %s]\n", fBooth? "yes": "no" ); Abc_Print( -2, "\t-f : generate a LUT FPGA structure [default = %s]\n", fFpga? "yes": "no" ); + Abc_Print( -2, "\t-g : generate a graph structure [default = %s]\n", fGraph? "yes": "no" ); Abc_Print( -2, "\t-n : generate one-hotness conditions [default = %s]\n", fOneHot? "yes": "no" ); Abc_Print( -2, "\t-r : generate random single-output function [default = %s]\n", fRandom? "yes": "no" ); Abc_Print( -2, "\t-v : prints verbose information [default = %s]\n", fVerbose? "yes": "no" ); @@ -45032,17 +45046,21 @@ usage: int Abc_CommandAbc9Compare( Abc_Frame_t * pAbc, int argc, char ** argv ) { extern void Gia_Iso4TestTwo( Gia_Man_t * pGia0, Gia_Man_t * pGia1 ); + extern void Gia_ManComparePrint( Gia_Man_t * p, Gia_Man_t * q ); Gia_Man_t * pGia0, * pGia1; char ** pArgvNew; int nArgcNew; - int c, fVerbose = 0; + int c, fFunc = 0, fVerbose = 0; Extra_UtilGetoptReset(); - while ( ( c = Extra_UtilGetopt( argc, argv, "vh" ) ) != EOF ) + while ( ( c = Extra_UtilGetopt( argc, argv, "fvh" ) ) != EOF ) { switch ( c ) { + case 'f': + fFunc ^= 1; + break; case 'v': fVerbose ^= 1; - break; + break; case 'h': goto usage; default: @@ -45063,14 +45081,18 @@ int Abc_CommandAbc9Compare( Abc_Frame_t * pAbc, int argc, char ** argv ) Abc_Print( -1, "Abc_CommandAbc9Compare(): Reading input files did not work.\n" ); return 1; } - Gia_Iso4TestTwo( pGia0, pGia1 ); + if ( fFunc ) + Gia_ManComparePrint( pGia0, pGia1 ); + else + Gia_Iso4TestTwo( pGia0, pGia1 ); Gia_ManStop( pGia0 ); Gia_ManStop( pGia1 ); return 0; usage: - Abc_Print( -2, "usage: &compare [-vh]\n" ); + Abc_Print( -2, "usage: &compare [-fvh]\n" ); Abc_Print( -2, "\t compared two AIGs for structural similarity\n" ); + Abc_Print( -2, "\t-f : toggle functional comparison [default = %s]\n", fFunc? "yes": "no" ); Abc_Print( -2, "\t-v : toggle printing verbose information [default = %s]\n", fVerbose? "yes": "no" ); Abc_Print( -2, "\t-h : print the command usage\n"); return 1; @@ -46062,6 +46084,163 @@ usage: return 1; } +/**Function************************************************************* + + Synopsis [] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ +int Abc_CommandAbc9SplitSat( Abc_Frame_t * pAbc, int argc, char ** argv ) +{ + extern void Cnf_SplitSat( char * pFileName, int iVarBeg, int iVarEnd, int nLits, int Value, int TimeOut, int nProcs, int nIters, int Seed, int fPrepro, int fVerbose ); + int c, iVarBeg = 0, iVarEnd = ABC_INFINITY, nLits = 10, Value = 2, TimeOut = 5, nProcs = 1, nIters = 1, Seed = 0, fPrepro = 0, fVerbose = 0; char * pFileName = NULL; + Extra_UtilGetoptReset(); + while ( ( c = Extra_UtilGetopt( argc, argv, "BENVTPISpvh" ) ) != EOF ) + { + switch ( c ) + { + case 'B': + if ( globalUtilOptind >= argc ) + { + Abc_Print( -1, "Command line switch \"-B\" should be followed by a positive integer.\n" ); + goto usage; + } + iVarBeg = atoi(argv[globalUtilOptind]); + globalUtilOptind++; + if ( iVarBeg < 0 ) + goto usage; + break; + case 'E': + if ( globalUtilOptind >= argc ) + { + Abc_Print( -1, "Command line switch \"-E\" should be followed by a positive integer.\n" ); + goto usage; + } + iVarEnd = atoi(argv[globalUtilOptind]); + globalUtilOptind++; + if ( iVarEnd < 0 ) + goto usage; + break; + case 'N': + if ( globalUtilOptind >= argc ) + { + Abc_Print( -1, "Command line switch \"-N\" should be followed by a positive integer.\n" ); + goto usage; + } + nLits = atoi(argv[globalUtilOptind]); + globalUtilOptind++; + if ( nLits < 0 ) + goto usage; + break; + case 'V': + if ( globalUtilOptind >= argc ) + { + Abc_Print( -1, "Command line switch \"-V\" should be followed by a positive integer.\n" ); + goto usage; + } + Value = atoi(argv[globalUtilOptind]); + globalUtilOptind++; + if ( Value < 0 || Value > 2 ) + goto usage; + break; + case 'T': + if ( globalUtilOptind >= argc ) + { + Abc_Print( -1, "Command line switch \"-T\" should be followed by a positive integer.\n" ); + goto usage; + } + TimeOut = atoi(argv[globalUtilOptind]); + globalUtilOptind++; + if ( TimeOut < 0 ) + goto usage; + break; + case 'P': + if ( globalUtilOptind >= argc ) + { + Abc_Print( -1, "Command line switch \"-P\" should be followed by a positive integer.\n" ); + goto usage; + } + nProcs = atoi(argv[globalUtilOptind]); + globalUtilOptind++; + if ( nProcs <= 0 ) + goto usage; + break; + case 'I': + if ( globalUtilOptind >= argc ) + { + Abc_Print( -1, "Command line switch \"-I\" should be followed by an integer.\n" ); + goto usage; + } + nIters = atoi(argv[globalUtilOptind]); + globalUtilOptind++; + if ( nIters < 0 ) + goto usage; + break; + case 'S': + if ( globalUtilOptind >= argc ) + { + Abc_Print( -1, "Command line switch \"-S\" should be followed by an integer.\n" ); + goto usage; + } + Seed = atoi(argv[globalUtilOptind]); + globalUtilOptind++; + if ( Seed < 0 ) + goto usage; + break; + case 'p': + fPrepro ^= 1; + break; + case 'v': + fVerbose ^= 1; + break; + case 'h': + goto usage; + default: + goto usage; + } + } + // get the file name + if ( argc != globalUtilOptind + 1 ) + { + Abc_Print( -1, "Abc_CommandAbc9SplitSat(): CNF file names should be given on the command line.\n" ); + return 1; + } + { + FILE * pFile; + pFileName = argv[globalUtilOptind]; + pFile = fopen( pFileName, "r" ); + if ( pFile == NULL ) + { + Abc_Print( -1, "Cannot open file \"%s\" with the input test patterns.\n", pFileName ); + return 0; + } + fclose( pFile ); + } + Cnf_SplitSat( pFileName, iVarBeg, iVarEnd, nLits, Value, TimeOut, nProcs, nIters, Seed, fPrepro, fVerbose ); + return 0; + +usage: + Abc_Print( -2, "usage: &splitsat [-BENVTPIS num] [-pvh]\n" ); + Abc_Print( -2, "\t solves CNF-based SAT problem by randomized case-splitting\n" ); + Abc_Print( -2, "\t-B num : the first CNF variable to use for splitting [default = %d]\n", iVarBeg ); + Abc_Print( -2, "\t-E num : the last CNF variable to use for splitting [default = %d]\n", iVarEnd ); + Abc_Print( -2, "\t-N num : the number of CNF variables to use for splitting [default = %d]\n", nLits ); + Abc_Print( -2, "\t-V num : the variable values to use (0, 1, or 2 for \"any\") [default = %d]\n", Value ); + Abc_Print( -2, "\t-T num : the runtime limit in seconds per subproblem [default = %d]\n", TimeOut ); + Abc_Print( -2, "\t-P num : the number of concurrent processes [default = %d]\n", nProcs ); + Abc_Print( -2, "\t-I num : the max number of iterations (0 = infinity) [default = %d]\n", nIters ); + Abc_Print( -2, "\t-S num : the random seed used to generate cofactors [default = %d]\n", Seed ); + Abc_Print( -2, "\t-p : toggle using SatELIte (http://minisat.se/SatELite.html) [default = %s]\n", fPrepro? "yes": "no" ); + Abc_Print( -2, "\t-v : toggle printing verbose information [default = %s]\n", fVerbose? "yes": "no" ); + Abc_Print( -2, "\t-h : print the command usage\n"); + return 1; +} + /**Function************************************************************* Synopsis [] @@ -49418,10 +49597,10 @@ usage: ***********************************************************************/ int Abc_CommandAbc9StochSyn( Abc_Frame_t * pAbc, int argc, char ** argv ) { - extern void Gia_ManStochSyn( int nMaxSize, int nIters, int TimeOut, int Seed, int fVerbose, char * pScript ); - int c, nMaxSize = 1000, nIters = 10, TimeOut = 0, Seed = 0, fVerbose = 0; char * pScript; + extern void Gia_ManStochSyn( int nMaxSize, int nIters, int TimeOut, int Seed, int fVerbose, char * pScript, int nProcs ); + int c, nMaxSize = 1000, nIters = 10, TimeOut = 0, Seed = 0, nProcs = 1, fVerbose = 0; char * pScript; Extra_UtilGetoptReset(); - while ( ( c = Extra_UtilGetopt( argc, argv, "NITSvh" ) ) != EOF ) + while ( ( c = Extra_UtilGetopt( argc, argv, "NITSPvh" ) ) != EOF ) { switch ( c ) { @@ -49469,6 +49648,17 @@ int Abc_CommandAbc9StochSyn( Abc_Frame_t * pAbc, int argc, char ** argv ) if ( Seed < 0 ) goto usage; break; + case 'P': + if ( globalUtilOptind >= argc ) + { + Abc_Print( -1, "Command line switch \"-P\" should be followed by an integer.\n" ); + goto usage; + } + nProcs = atoi(argv[globalUtilOptind]); + globalUtilOptind++; + if ( nProcs < 0 ) + goto usage; + break; case 'v': fVerbose ^= 1; break; @@ -49489,17 +49679,18 @@ int Abc_CommandAbc9StochSyn( Abc_Frame_t * pAbc, int argc, char ** argv ) goto usage; } pScript = Abc_UtilStrsav( argv[globalUtilOptind] ); - Gia_ManStochSyn( nMaxSize, nIters, TimeOut, Seed, fVerbose, pScript ); + Gia_ManStochSyn( nMaxSize, nIters, TimeOut, Seed, fVerbose, pScript, nProcs ); ABC_FREE( pScript ); return 0; usage: - Abc_Print( -2, "usage: &stochsyn [-NITS ] [-tvh]