| /**CFile**************************************************************** |
| |
| FileName [fraigApi.c] |
| |
| PackageName [FRAIG: Functionally reduced AND-INV graphs.] |
| |
| Synopsis [Access APIs for the FRAIG manager and node.] |
| |
| Author [Alan Mishchenko <alanmi@eecs.berkeley.edu>] |
| |
| Affiliation [UC Berkeley] |
| |
| Date [Ver. 2.0. Started - October 1, 2004] |
| |
| Revision [$Id: fraigApi.c,v 1.2 2005/07/08 01:01:30 alanmi Exp $] |
| |
| ***********************************************************************/ |
| |
| #include "fraigInt.h" |
| |
| ABC_NAMESPACE_IMPL_START |
| |
| |
| //////////////////////////////////////////////////////////////////////// |
| /// DECLARATIONS /// |
| //////////////////////////////////////////////////////////////////////// |
| |
| //////////////////////////////////////////////////////////////////////// |
| /// FUNCTION DEFINITIONS /// |
| //////////////////////////////////////////////////////////////////////// |
| |
| /**Function************************************************************* |
| |
| Synopsis [Access functions to read the data members of the manager.] |
| |
| Description [] |
| |
| SideEffects [] |
| |
| SeeAlso [] |
| |
| ***********************************************************************/ |
| Fraig_NodeVec_t * Fraig_ManReadVecInputs( Fraig_Man_t * p ) { return p->vInputs; } |
| Fraig_NodeVec_t * Fraig_ManReadVecOutputs( Fraig_Man_t * p ) { return p->vOutputs; } |
| Fraig_NodeVec_t * Fraig_ManReadVecNodes( Fraig_Man_t * p ) { return p->vNodes; } |
| Fraig_Node_t ** Fraig_ManReadInputs ( Fraig_Man_t * p ) { return p->vInputs->pArray; } |
| Fraig_Node_t ** Fraig_ManReadOutputs( Fraig_Man_t * p ) { return p->vOutputs->pArray; } |
| Fraig_Node_t ** Fraig_ManReadNodes( Fraig_Man_t * p ) { return p->vNodes->pArray; } |
| int Fraig_ManReadInputNum ( Fraig_Man_t * p ) { return p->vInputs->nSize; } |
| int Fraig_ManReadOutputNum( Fraig_Man_t * p ) { return p->vOutputs->nSize; } |
| int Fraig_ManReadNodeNum( Fraig_Man_t * p ) { return p->vNodes->nSize; } |
| Fraig_Node_t * Fraig_ManReadConst1 ( Fraig_Man_t * p ) { return p->pConst1; } |
| Fraig_Node_t * Fraig_ManReadIthNode( Fraig_Man_t * p, int i ) { assert ( i < p->vNodes->nSize ); return p->vNodes->pArray[i]; } |
| char ** Fraig_ManReadInputNames( Fraig_Man_t * p ) { return p->ppInputNames; } |
| char ** Fraig_ManReadOutputNames( Fraig_Man_t * p ) { return p->ppOutputNames; } |
| char * Fraig_ManReadVarsInt( Fraig_Man_t * p ) { return (char *)p->vVarsInt; } |
| char * Fraig_ManReadSat( Fraig_Man_t * p ) { return (char *)p->pSat; } |
| int Fraig_ManReadFuncRed( Fraig_Man_t * p ) { return p->fFuncRed; } |
| int Fraig_ManReadFeedBack( Fraig_Man_t * p ) { return p->fFeedBack; } |
| int Fraig_ManReadDoSparse( Fraig_Man_t * p ) { return p->fDoSparse; } |
| int Fraig_ManReadChoicing( Fraig_Man_t * p ) { return p->fChoicing; } |
| int Fraig_ManReadVerbose( Fraig_Man_t * p ) { return p->fVerbose; } |
| int * Fraig_ManReadModel( Fraig_Man_t * p ) { return p->pModel; } |
| // returns the number of patterns used for random simulation (this number is fixed for the FRAIG run) |
| int Fraig_ManReadPatternNumRandom( Fraig_Man_t * p ) { return p->nWordsRand * 32; } |
| // returns the number of dynamic patterns accumulated at runtime (include SAT solver counter-examples and distance-1 patterns derived from them) |
| int Fraig_ManReadPatternNumDynamic( Fraig_Man_t * p ) { return p->iWordStart * 32; } |
| // returns the number of dynamic patterns proved useful to distinquish some FRAIG nodes (this number is more than 0 after the first garbage collection of patterns) |
| int Fraig_ManReadPatternNumDynamicFiltered( Fraig_Man_t * p ) { return p->iPatsPerm; } |
| // returns the number of times FRAIG package timed out |
| int Fraig_ManReadSatFails( Fraig_Man_t * p ) { return p->nSatFailsReal; } |
| // returns the number of conflicts in the SAT solver |
| int Fraig_ManReadConflicts( Fraig_Man_t * p ) { return p->pSat? Msat_SolverReadBackTracks(p->pSat) : 0; } |
| // returns the number of inspections in the SAT solver |
| int Fraig_ManReadInspects( Fraig_Man_t * p ) { return p->pSat? Msat_SolverReadInspects(p->pSat) : 0; } |
| |
| /**Function************************************************************* |
| |
| Synopsis [Access functions to set the data members of the manager.] |
| |
| Description [] |
| |
| SideEffects [] |
| |
| SeeAlso [] |
| |
| ***********************************************************************/ |
| void Fraig_ManSetFuncRed( Fraig_Man_t * p, int fFuncRed ) { p->fFuncRed = fFuncRed; } |
| void Fraig_ManSetFeedBack( Fraig_Man_t * p, int fFeedBack ) { p->fFeedBack = fFeedBack; } |
| void Fraig_ManSetDoSparse( Fraig_Man_t * p, int fDoSparse ) { p->fDoSparse = fDoSparse; } |
| void Fraig_ManSetChoicing( Fraig_Man_t * p, int fChoicing ) { p->fChoicing = fChoicing; } |
| void Fraig_ManSetTryProve( Fraig_Man_t * p, int fTryProve ) { p->fTryProve = fTryProve; } |
| void Fraig_ManSetVerbose( Fraig_Man_t * p, int fVerbose ) { p->fVerbose = fVerbose; } |
| void Fraig_ManSetOutputNames( Fraig_Man_t * p, char ** ppNames ) { p->ppOutputNames = ppNames; } |
| void Fraig_ManSetInputNames( Fraig_Man_t * p, char ** ppNames ) { p->ppInputNames = ppNames; } |
| |
| /**Function************************************************************* |
| |
| Synopsis [Access functions to read the data members of the node.] |
| |
| Description [] |
| |
| SideEffects [] |
| |
| SeeAlso [] |
| |
| ***********************************************************************/ |
| Fraig_Node_t * Fraig_NodeReadData0( Fraig_Node_t * p ) { return p->pData0; } |
| Fraig_Node_t * Fraig_NodeReadData1( Fraig_Node_t * p ) { return p->pData1; } |
| int Fraig_NodeReadNum( Fraig_Node_t * p ) { return p->Num; } |
| Fraig_Node_t * Fraig_NodeReadOne( Fraig_Node_t * p ) { assert (!Fraig_IsComplement(p)); return p->p1; } |
| Fraig_Node_t * Fraig_NodeReadTwo( Fraig_Node_t * p ) { assert (!Fraig_IsComplement(p)); return p->p2; } |
| Fraig_Node_t * Fraig_NodeReadNextE( Fraig_Node_t * p ) { return p->pNextE; } |
| Fraig_Node_t * Fraig_NodeReadRepr( Fraig_Node_t * p ) { return p->pRepr; } |
| int Fraig_NodeReadNumRefs( Fraig_Node_t * p ) { return p->nRefs; } |
| int Fraig_NodeReadNumFanouts( Fraig_Node_t * p ) { return p->nFanouts; } |
| int Fraig_NodeReadSimInv( Fraig_Node_t * p ) { return p->fInv; } |
| int Fraig_NodeReadNumOnes( Fraig_Node_t * p ) { return p->nOnes; } |
| // returns the pointer to the random simulation patterns (their number is returned by Fraig_ManReadPatternNumRandom) |
| // memory pointed to by this and the following procedure is maintained by the FRAIG package and exists as long as the package runs |
| unsigned * Fraig_NodeReadPatternsRandom( Fraig_Node_t * p ) { return p->puSimR; } |
| // returns the pointer to the dynamic simulation patterns (their number is returned by Fraig_ManReadPatternNumDynamic or Fraig_ManReadPatternNumDynamicFiltered) |
| // if the number of patterns is not evenly divisible by 32, the patterns beyond the given number contain garbage |
| unsigned * Fraig_NodeReadPatternsDynamic( Fraig_Node_t * p ) { return p->puSimD; } |
| |
| /**Function************************************************************* |
| |
| Synopsis [Access functions to set the data members of the node.] |
| |
| Description [] |
| |
| SideEffects [] |
| |
| SeeAlso [] |
| |
| ***********************************************************************/ |
| void Fraig_NodeSetData0( Fraig_Node_t * p, Fraig_Node_t * pData ) { p->pData0 = pData; } |
| void Fraig_NodeSetData1( Fraig_Node_t * p, Fraig_Node_t * pData ) { p->pData1 = pData; } |
| |
| /**Function************************************************************* |
| |
| Synopsis [Checks the type of the node.] |
| |
| Description [] |
| |
| SideEffects [] |
| |
| SeeAlso [] |
| |
| ***********************************************************************/ |
| int Fraig_NodeIsConst( Fraig_Node_t * p ) { return (Fraig_Regular(p))->Num == 0; } |
| int Fraig_NodeIsVar( Fraig_Node_t * p ) { return (Fraig_Regular(p))->NumPi >= 0; } |
| int Fraig_NodeIsAnd( Fraig_Node_t * p ) { return (Fraig_Regular(p))->NumPi < 0 && (Fraig_Regular(p))->Num > 0; } |
| int Fraig_NodeComparePhase( Fraig_Node_t * p1, Fraig_Node_t * p2 ) { assert( !Fraig_IsComplement(p1) ); assert( !Fraig_IsComplement(p2) ); return p1->fInv ^ p2->fInv; } |
| |
| /**Function************************************************************* |
| |
| Synopsis [Returns a new primary input node.] |
| |
| Description [If the node with this number does not exist, |
| create a new PI node with this number.] |
| |
| SideEffects [] |
| |
| SeeAlso [] |
| |
| ***********************************************************************/ |
| Fraig_Node_t * Fraig_ManReadIthVar( Fraig_Man_t * p, int i ) |
| { |
| int k; |
| if ( i < 0 ) |
| { |
| printf( "Requesting a PI with a negative number\n" ); |
| return NULL; |
| } |
| // create the PIs to fill in the interval |
| if ( i >= p->vInputs->nSize ) |
| for ( k = p->vInputs->nSize; k <= i; k++ ) |
| Fraig_NodeCreatePi( p ); |
| return p->vInputs->pArray[i]; |
| } |
| |
| /**Function************************************************************* |
| |
| Synopsis [Creates a new PO node.] |
| |
| Description [This procedure may take a complemented node.] |
| |
| SideEffects [] |
| |
| SeeAlso [] |
| |
| ***********************************************************************/ |
| void Fraig_ManSetPo( Fraig_Man_t * p, Fraig_Node_t * pNode ) |
| { |
| // internal node may be a PO two times |
| Fraig_Regular(pNode)->fNodePo = 1; |
| Fraig_NodeVecPush( p->vOutputs, pNode ); |
| } |
| |
| /**Function************************************************************* |
| |
| Synopsis [Perfoms the AND operation with functional hashing.] |
| |
| Description [] |
| |
| SideEffects [] |
| |
| SeeAlso [] |
| |
| ***********************************************************************/ |
| Fraig_Node_t * Fraig_NodeAnd( Fraig_Man_t * p, Fraig_Node_t * p1, Fraig_Node_t * p2 ) |
| { |
| return Fraig_NodeAndCanon( p, p1, p2 ); |
| } |
| |
| /**Function************************************************************* |
| |
| Synopsis [Perfoms the OR operation with functional hashing.] |
| |
| Description [] |
| |
| SideEffects [] |
| |
| SeeAlso [] |
| |
| ***********************************************************************/ |
| Fraig_Node_t * Fraig_NodeOr( Fraig_Man_t * p, Fraig_Node_t * p1, Fraig_Node_t * p2 ) |
| { |
| return Fraig_Not( Fraig_NodeAndCanon( p, Fraig_Not(p1), Fraig_Not(p2) ) ); |
| } |
| |
| /**Function************************************************************* |
| |
| Synopsis [Perfoms the EXOR operation with functional hashing.] |
| |
| Description [] |
| |
| SideEffects [] |
| |
| SeeAlso [] |
| |
| ***********************************************************************/ |
| Fraig_Node_t * Fraig_NodeExor( Fraig_Man_t * p, Fraig_Node_t * p1, Fraig_Node_t * p2 ) |
| { |
| return Fraig_NodeMux( p, p1, Fraig_Not(p2), p2 ); |
| } |
| |
| /**Function************************************************************* |
| |
| Synopsis [Perfoms the MUX operation with functional hashing.] |
| |
| Description [] |
| |
| SideEffects [] |
| |
| SeeAlso [] |
| |
| ***********************************************************************/ |
| Fraig_Node_t * Fraig_NodeMux( Fraig_Man_t * p, Fraig_Node_t * pC, Fraig_Node_t * pT, Fraig_Node_t * pE ) |
| { |
| Fraig_Node_t * pAnd1, * pAnd2, * pRes; |
| pAnd1 = Fraig_NodeAndCanon( p, pC, pT ); Fraig_Ref( pAnd1 ); |
| pAnd2 = Fraig_NodeAndCanon( p, Fraig_Not(pC), pE ); Fraig_Ref( pAnd2 ); |
| pRes = Fraig_NodeOr( p, pAnd1, pAnd2 ); |
| Fraig_RecursiveDeref( p, pAnd1 ); |
| Fraig_RecursiveDeref( p, pAnd2 ); |
| Fraig_Deref( pRes ); |
| return pRes; |
| } |
| |
| |
| /**Function************************************************************* |
| |
| Synopsis [Sets the node to be equivalent to the given one.] |
| |
| Description [This procedure is a work-around for the equivalence check. |
| Does not verify the equivalence. Use at the user's risk.] |
| |
| SideEffects [] |
| |
| SeeAlso [] |
| |
| ***********************************************************************/ |
| void Fraig_NodeSetChoice( Fraig_Man_t * pMan, Fraig_Node_t * pNodeOld, Fraig_Node_t * pNodeNew ) |
| { |
| // assert( pMan->fChoicing ); |
| pNodeNew->pNextE = pNodeOld->pNextE; |
| pNodeOld->pNextE = pNodeNew; |
| pNodeNew->pRepr = pNodeOld; |
| } |
| |
| //////////////////////////////////////////////////////////////////////// |
| /// END OF FILE /// |
| //////////////////////////////////////////////////////////////////////// |
| |
| |
| ABC_NAMESPACE_IMPL_END |
| |