/**Function************************************************************* Synopsis [Computes the maximum and minimum levels of the choice nodes.] Description [] SideEffects [] SeeAlso [] ***********************************************************************/ void Map_MappingGetChoiceLevels( Map_Man_t * pMan, Map_Node_t * p1, Map_Node_t * p2, int * pMin, int * pMax ) { Map_NodeVec_t * vNodes; Map_NodeVec_t * vBoundary; Map_Node_t * pNode; int i, Min, Max; vNodes = Map_NodeVecAlloc( 100 ); vBoundary = Map_NodeVecAlloc( 100 ); Map_MappingDfsMarked1_rec( p1, vNodes, 1 ); Map_MappingDfsMarked2_rec( p2, vNodes, vBoundary, 1 ); // clean the marks Min = 100000; Max = -100000; for ( i = 0; i < vBoundary->nSize; i++ ) { pNode = vBoundary->pArray[i]; if ( Min > (int)pNode->Level ) Min = pNode->Level; if ( Max < (int)pNode->Level ) Max = pNode->Level; } Map_NodeVecFree( vBoundary ); for ( i = 0; i < vNodes->nSize; i++ ) { pNode = vNodes->pArray[i]; pNode->fMark0 = pNode->fMark1 = 0; } Map_NodeVecFree( vNodes ); *pMin = Min; *pMax = Max; }
/**Function************************************************************* Synopsis [Create the mapping manager.] Description [The number of inputs and outputs is assumed to be known is advance. It is much simpler to have them fixed upfront. When it comes to representing the object graph in the form of AIG, the resulting manager is similar to the regular AIG manager, except that it does not use reference counting (and therefore does not have garbage collections). It does have table resizing. The data structure is more flexible to represent additional information needed for mapping.] SideEffects [] SeeAlso [] ***********************************************************************/ Map_Man_t * Map_ManCreate( int nInputs, int nOutputs, int fVerbose ) { Map_Man_t * p; int i; // derive the supergate library if ( Abc_FrameReadLibSuper() == NULL ) { printf( "The supergate library is not specified. Use \"read_super\".\n" ); return NULL; } // start the manager p = ABC_ALLOC( Map_Man_t, 1 ); memset( p, 0, sizeof(Map_Man_t) ); p->pSuperLib = (Map_SuperLib_t *)Abc_FrameReadLibSuper(); p->nVarsMax = p->pSuperLib->nVarsMax; p->fVerbose = fVerbose; p->fEpsilon = (float)0.001; assert( p->nVarsMax > 0 ); if ( p->nVarsMax == 5 ) Extra_Truth4VarN( &p->uCanons, &p->uPhases, &p->pCounters, 8 ); // start various data structures Map_TableCreate( p ); Map_MappingSetupTruthTables( p->uTruths ); Map_MappingSetupTruthTablesLarge( p->uTruthsLarge ); // printf( "Node = %d bytes. Cut = %d bytes. Super = %d bytes.\n", sizeof(Map_Node_t), sizeof(Map_Cut_t), sizeof(Map_Super_t) ); p->mmNodes = Extra_MmFixedStart( sizeof(Map_Node_t) ); p->mmCuts = Extra_MmFixedStart( sizeof(Map_Cut_t) ); // make sure the constant node will get index -1 p->nNodes = -1; // create the constant node p->pConst1 = Map_NodeCreate( p, NULL, NULL ); p->vNodesAll = Map_NodeVecAlloc( 100 ); p->vNodesTemp = Map_NodeVecAlloc( 100 ); p->vMapping = Map_NodeVecAlloc( 100 ); p->vVisited = Map_NodeVecAlloc( 100 ); // create the PI nodes p->nInputs = nInputs; p->pInputs = ABC_ALLOC( Map_Node_t *, nInputs ); for ( i = 0; i < nInputs; i++ ) p->pInputs[i] = Map_NodeCreate( p, NULL, NULL ); // create the place for the output nodes p->nOutputs = nOutputs; p->pOutputs = ABC_ALLOC( Map_Node_t *, nOutputs ); memset( p->pOutputs, 0, sizeof(Map_Node_t *) * nOutputs ); return p; }
/**Function************************************************************* Synopsis [] Description [] SideEffects [] SeeAlso [] ***********************************************************************/ Map_NodeVec_t * Map_NodeVecDup( Map_NodeVec_t * p ) { Map_NodeVec_t * pNew = Map_NodeVecAlloc( p->nSize ); memcpy( pNew->pArray, p->pArray, sizeof(int) * p->nSize ); pNew->nSize = p->nSize; return pNew; }
/**Function************************************************************* Synopsis [] Description [] SideEffects [] SeeAlso [] ***********************************************************************/ float Map_MappingGetChoiceVolumes( Map_Man_t * pMan, Map_Node_t * p1, Map_Node_t * p2 ) { Map_NodeVec_t * vNodes; Map_Node_t * pNode; int i, nVolumeTotal, nVolumeUnique; vNodes = Map_NodeVecAlloc( 100 ); Map_MappingDfsMarked3_rec( p1, vNodes ); Map_MappingDfsMarked4_rec( p2, vNodes ); // clean the marks nVolumeTotal = nVolumeUnique = 0; for ( i = 0; i < vNodes->nSize; i++ ) { pNode = vNodes->pArray[i]; if ( !Map_NodeIsAnd(pNode) ) continue; nVolumeTotal++; if ( pNode->fMark0 ^ pNode->fMark1 ) nVolumeUnique++; pNode->fMark0 = pNode->fMark1 = 0; } Map_NodeVecFree( vNodes ); // return ((float)nVolumeUnique)/nVolumeTotal; return (float)nVolumeUnique; }
/**Function************************************************************* Synopsis [Computes the DFS ordering of the nodes.] Description [] SideEffects [] SeeAlso [] ***********************************************************************/ Map_NodeVec_t * Map_MappingDfsNodes( Map_Man_t * pMan, Map_Node_t ** ppCuts, int nNodes, int fEquiv ) { Map_NodeVec_t * vNodes; int i; // perform the traversal vNodes = Map_NodeVecAlloc( 200 ); for ( i = 0; i < nNodes; i++ ) Map_MappingDfs_rec( ppCuts[i], vNodes, fEquiv ); for ( i = 0; i < vNodes->nSize; i++ ) vNodes->pArray[i]->fMark0 = 0; return vNodes; }
Map_NodeVec_t * Map_MappingDfs( Map_Man_t * pMan, int fCollectEquiv ) { Map_NodeVec_t * vNodes; int i; // perform the traversal vNodes = Map_NodeVecAlloc( 100 ); for ( i = 0; i < pMan->nOutputs; i++ ) Map_MappingDfs_rec( Map_Regular(pMan->pOutputs[i]), vNodes, fCollectEquiv ); for ( i = 0; i < vNodes->nSize; i++ ) vNodes->pArray[i]->fMark0 = 0; // for ( i = 0; i < pMan->nOutputs; i++ ) // Map_MappingUnmark_rec( Map_Regular(pMan->pOutputs[i]) ); return vNodes; }