Beispiel #1
0
/**Function*************************************************************

  Synopsis    [Derives the miter of two sequential networks.]

  Description [Assumes that the networks are strashed.]
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
Abc_Ntk_t * Abc_NtkMiterInt( Abc_Ntk_t * pNtk1, Abc_Ntk_t * pNtk2, int fComb, int nPartSize, int fImplic, int fMulti )
{
    char Buffer[1000];
    Abc_Ntk_t * pNtkMiter;

    assert( Abc_NtkIsStrash(pNtk1) );
    assert( Abc_NtkIsStrash(pNtk2) );

    // start the new network
    pNtkMiter = Abc_NtkAlloc( ABC_NTK_STRASH, ABC_FUNC_AIG, 1 );
    sprintf( Buffer, "%s_%s_miter", pNtk1->pName, pNtk2->pName );
    pNtkMiter->pName = Extra_UtilStrsav(Buffer);

    // perform strashing
    Abc_NtkMiterPrepare( pNtk1, pNtk2, pNtkMiter, fComb, nPartSize, fMulti );
    Abc_NtkMiterAddOne( pNtk1, pNtkMiter );
    Abc_NtkMiterAddOne( pNtk2, pNtkMiter );
    Abc_NtkMiterFinalize( pNtk1, pNtk2, pNtkMiter, fComb, nPartSize, fImplic, fMulti );
    Abc_AigCleanup((Abc_Aig_t *)pNtkMiter->pManFunc);

    // make sure that everything is okay
    if ( !Abc_NtkCheck( pNtkMiter ) )
    {
        printf( "Abc_NtkMiter: The network check has failed.\n" );
        Abc_NtkDelete( pNtkMiter );
        return NULL;
    }
    return pNtkMiter;
}
Beispiel #2
0
/**Function*************************************************************

  Synopsis    []

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
Abc_Ntk_t * Wlc_NtkGetInv( Wlc_Ntk_t * pNtk, Vec_Int_t * vInv, Vec_Str_t * vSop, int fVerbose )
{
    Wlc_Obj_t * pObj;
    int i, k, nNum, nRange, nBits = 0;
    Abc_Ntk_t * pMainNtk = NULL;
    Abc_Obj_t * pMainObj, * pMainTemp;
    char Buffer[5000];
    // start the network
    pMainNtk = Abc_NtkAlloc( ABC_NTK_LOGIC, ABC_FUNC_SOP, 1 );
    // duplicate the name and the spec
    pMainNtk->pName = Extra_UtilStrsav(pNtk->pName);
    // create primary inputs
    Wlc_NtkForEachCi( pNtk, pObj, i )
    {
        if ( pObj->Type != WLC_OBJ_FO )
            continue;
        nRange = Wlc_ObjRange(pObj);
        for ( k = 0; k < nRange; k++ )
        {
            nNum = Vec_IntEntry(vInv, nBits + k);
            if ( nNum )
                break;
        }
        if ( k == nRange )
        {
            nBits += nRange;
            continue;
        }
        //printf( "%s[%d:%d] : ", Wlc_ObjName(pNtk, Wlc_ObjId(pNtk, pObj)), pObj->End, pObj->Beg );
        for ( k = 0; k < nRange; k++ )
        {
            nNum = Vec_IntEntry( vInv, nBits + k );
            if ( nNum == 0 )
                continue;
            //printf( "  [%d] -> %d", k, nNum );
            pMainObj = Abc_NtkCreatePi( pMainNtk );
            sprintf( Buffer, "%s[%d]", Wlc_ObjName(pNtk, Wlc_ObjId(pNtk, pObj)), k );
            Abc_ObjAssignName( pMainObj, Buffer, NULL );

        }
        //printf( "\n");
        nBits += nRange;
    }
    //printf( "%d %d\n", Vec_IntSize(vInv), nBits );
    assert( Vec_IntSize(vInv) == nBits );
    // create node
    pMainObj = Abc_NtkCreateNode( pMainNtk );
    Abc_NtkForEachPi( pMainNtk, pMainTemp, i )
        Abc_ObjAddFanin( pMainObj, pMainTemp );
    pMainObj->pData = Abc_SopRegister( (Mem_Flex_t *)pMainNtk->pManFunc, Vec_StrArray(vSop) );
    // create PO
    pMainTemp = Abc_NtkCreatePo( pMainNtk );
    Abc_ObjAddFanin( pMainTemp, pMainObj );
    Abc_ObjAssignName( pMainTemp, "inv", NULL );
    return pMainNtk;
}
Beispiel #3
0
/**Function*************************************************************

  Synopsis    [Constructs the network isomorphic to the given BDD.]

  Description [Assumes that the BDD depends on the variables whose indexes
  correspond to the names in the array (pNamesPi). Otherwise, returns NULL.
  The resulting network comes with one node, whose functionality is
  equal to the given BDD. To decompose this BDD into the network of
  multiplexers use Abc_NtkBddToMuxes(). To decompose this BDD into
  an And-Inverter Graph, use Abc_NtkStrash().]
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
Abc_Ntk_t * Abc_NtkDeriveFromBdd( void * dd0, void * bFunc, char * pNamePo, Vec_Ptr_t * vNamesPi )
{
    DdManager * dd = (DdManager *)dd0;
    Abc_Ntk_t * pNtk; 
    Vec_Ptr_t * vNamesPiFake = NULL;
    Abc_Obj_t * pNode, * pNodePi, * pNodePo;
    DdNode * bSupp, * bTemp;
    char * pName;
    int i;

    // supply fake names if real names are not given
    if ( pNamePo == NULL )
        pNamePo = "F";
    if ( vNamesPi == NULL )
    {
        vNamesPiFake = Abc_NodeGetFakeNames( dd->size );
        vNamesPi = vNamesPiFake;
    }

    // make sure BDD depends on the variables whose index 
    // does not exceed the size of the array with PI names
    bSupp = Cudd_Support( dd, (DdNode *)bFunc );   Cudd_Ref( bSupp );
    for ( bTemp = bSupp; bTemp != Cudd_ReadOne(dd); bTemp = cuddT(bTemp) )
        if ( (int)Cudd_NodeReadIndex(bTemp) >= Vec_PtrSize(vNamesPi) )
            break;
    Cudd_RecursiveDeref( dd, bSupp );
    if ( bTemp != Cudd_ReadOne(dd) )
        return NULL;

    // start the network
    pNtk = Abc_NtkAlloc( ABC_NTK_LOGIC, ABC_FUNC_BDD, 1 );
    pNtk->pName = Extra_UtilStrsav(pNamePo);
    // make sure the new manager has enough inputs
    Cudd_bddIthVar( (DdManager *)pNtk->pManFunc, Vec_PtrSize(vNamesPi) );
    // add the PIs corresponding to the names
    Vec_PtrForEachEntry( char *, vNamesPi, pName, i )
        Abc_ObjAssignName( Abc_NtkCreatePi(pNtk), pName, NULL );
    // create the node
    pNode = Abc_NtkCreateNode( pNtk );
    pNode->pData = (DdNode *)Cudd_bddTransfer( dd, (DdManager *)pNtk->pManFunc, (DdNode *)bFunc ); Cudd_Ref((DdNode *)pNode->pData);
    Abc_NtkForEachPi( pNtk, pNodePi, i )
        Abc_ObjAddFanin( pNode, pNodePi );
    // create the only PO
    pNodePo = Abc_NtkCreatePo( pNtk );
    Abc_ObjAddFanin( pNodePo, pNode );
    Abc_ObjAssignName( pNodePo, pNamePo, NULL );
    // make the network minimum base
    Abc_NtkMinimumBase( pNtk );
    if ( vNamesPiFake )
        Abc_NodeFreeNames( vNamesPiFake );
    if ( !Abc_NtkCheck( pNtk ) )
        fprintf( stdout, "Abc_NtkDeriveFromBdd(): Network check has failed.\n" );
    return pNtk;
}
/**Function*************************************************************

  Synopsis    [Converts combinational AIG with latches into sequential AIG.]

  Description [The const/PI/PO nodes are duplicated. The internal
  nodes are duplicated in the topological order. The dangling nodes
  are not duplicated. The choice nodes are duplicated.]
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
Abc_Ntk_t * Abc_NtkAigToSeq( Abc_Ntk_t * pNtk )
{
    Abc_Ntk_t * pNtkNew;
    Abc_Obj_t * pObj, * pFaninNew;
    Vec_Int_t * vInitValues;
    Abc_InitType_t Init;
    int i, k, RetValue;

    // make sure it is an AIG without self-feeding latches
    assert( Abc_NtkIsStrash(pNtk) );
    assert( Abc_NtkIsDfsOrdered(pNtk) );

    if ( RetValue = Abc_NtkRemoveSelfFeedLatches(pNtk) )
        printf( "Modified %d self-feeding latches. The result will not verify.\n", RetValue );
    assert( Abc_NtkCountSelfFeedLatches(pNtk) == 0 );

    // start the network
    pNtkNew = Abc_NtkAlloc( ABC_NTK_SEQ, ABC_FUNC_AIG, 1 );
    // duplicate the name and the spec
    pNtkNew->pName = Extra_UtilStrsav(pNtk->pName);
    pNtkNew->pSpec = Extra_UtilStrsav(pNtk->pSpec);

    // map the constant nodes
    Abc_NtkCleanCopy( pNtk );
    Abc_AigConst1(pNtk)->pCopy = Abc_AigConst1(pNtkNew);

    // copy all objects, except the latches and constant
    Vec_PtrFill( pNtkNew->vObjs, Abc_NtkObjNumMax(pNtk), NULL );
    Vec_PtrWriteEntry( pNtkNew->vObjs, 0, Abc_AigConst1(pNtk)->pCopy );
    Abc_NtkForEachObj( pNtk, pObj, i )
    {
        if ( i == 0 || Abc_ObjIsLatch(pObj) )
            continue;
        pObj->pCopy = Abc_ObjAlloc( pNtkNew, pObj->Type );
        pObj->pCopy->Id     = pObj->Id;      // the ID is the same for both
        pObj->pCopy->fPhase = pObj->fPhase;  // used to work with choices
        pObj->pCopy->Level  = pObj->Level;   // used for upper bound on clock cycle
        Vec_PtrWriteEntry( pNtkNew->vObjs, pObj->pCopy->Id, pObj->pCopy );
        pNtkNew->nObjs++;
    }
    pNtkNew->nObjCounts[ABC_OBJ_NODE] = pNtk->nObjCounts[ABC_OBJ_NODE];

    // create PI/PO and their names
    Abc_NtkForEachPi( pNtk, pObj, i )
    {
        Vec_PtrPush( pNtkNew->vPis, pObj->pCopy );
        Vec_PtrPush( pNtkNew->vCis, pObj->pCopy );
        Abc_ObjAssignName( pObj->pCopy, Abc_ObjName(pObj), NULL );
    }
Beispiel #5
0
/**Fnction*************************************************************

  Synopsis    [Constructs AIG in ABC from the manager.]

  Description [The ABC network is started, as well as the array vCopy,
  which will map the new ID of each object in the BBLIF manager into
  the ponter ot the corresponding AIG object in the ABC. For each internal
  node in a topological oder the AIG representation is created
  by factoring the SOP representation of the BBLIF object. Finally,
  the CO objects are created, and the dummy names are assigned because 
  ABC requires each CI/CO to have a name.]
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
Abc_Ntk_t * Bbl_ManToAig( Bbl_Man_t * p )
{
    extern int Bbl_ManFncSize( Bbl_Man_t * p );
    extern int Bbl_ObjFncHandle( Bbl_Obj_t * p );
    extern Abc_Obj_t * Dec_GraphToAig( Abc_Ntk_t * pNtk, Dec_Graph_t * pFForm, Vec_Ptr_t * vFaninAigs );
    int fVerbose = 0;
    Abc_Ntk_t * pNtk;
    Abc_Obj_t * pObjNew;
    Bbl_Obj_t * pObj, * pFanin;
    Vec_Ptr_t * vCopy, * vNodes, * vFaninAigs;
    Dec_Graph_t ** pFForms;
    int i;
    clock_t clk;
clk = clock();
    // map SOP handles into factored forms
    pFForms = ABC_CALLOC( Dec_Graph_t *, Bbl_ManFncSize(p) );
    Bbl_ManForEachObj( p, pObj )
        if ( pFForms[Bbl_ObjFncHandle(pObj)] == NULL )
            pFForms[Bbl_ObjFncHandle(pObj)] = Dec_Factor( Bbl_ObjSop(p, pObj) );
if ( fVerbose )
ABC_PRT( "Fct", clock() - clk );
    // start the network
    pNtk = Abc_NtkAlloc( ABC_NTK_STRASH, ABC_FUNC_AIG, 1 );
    pNtk->pName = Extra_UtilStrsav( Bbl_ManName(p) );
    vCopy = Vec_PtrStart( 1000 );
    // create CIs
    Bbl_ManForEachObj( p, pObj )
    {
        if ( !Bbl_ObjIsInput(pObj) )
            continue;
        Vec_PtrSetEntry( vCopy, Bbl_ObjId(pObj), Abc_NtkCreatePi(pNtk) );
    }
clk = clock();
    // create internal nodes
    vNodes = Bbl_ManDfs( p );
    vFaninAigs = Vec_PtrAlloc( 100 );
    Vec_PtrForEachEntry( Bbl_Obj_t *, vNodes, pObj, i )
    {
        // collect fanin AIGs
        Vec_PtrClear( vFaninAigs );
        Bbl_ObjForEachFanin( pObj, pFanin )
            Vec_PtrPush( vFaninAigs, Vec_PtrEntry( vCopy, Bbl_ObjId(pFanin) ) );
        // create the new node
        pObjNew = Dec_GraphToAig( pNtk, pFForms[Bbl_ObjFncHandle(pObj)], vFaninAigs );
        Vec_PtrSetEntry( vCopy, Bbl_ObjId(pObj), pObjNew );
    }
Beispiel #6
0
Abc_Ntk_t * Abc_NtkFromMiniAig( Mini_Aig_t * p )
{
    Abc_Ntk_t * pNtk;
    Abc_Obj_t * pObj;
    Vec_Int_t * vCopies;
    int i, nNodes;
    // get the number of nodes
    nNodes = Mini_AigNodeNum(p);
    // create ABC network
    pNtk = Abc_NtkAlloc( ABC_NTK_STRASH, ABC_FUNC_AIG, 1 );
    pNtk->pName = Abc_UtilStrsav( "MiniAig" );
    // create mapping from MiniAIG objects into ABC objects
    vCopies = Vec_IntAlloc( nNodes );
    Vec_IntPush( vCopies, Abc_LitNot(Abc_ObjToLit(Abc_AigConst1(pNtk))) );
    // iterate through the objects
    for ( i = 1; i < nNodes; i++ )
    {
        if ( Mini_AigNodeIsPi( p, i ) )
            pObj = Abc_NtkCreatePi(pNtk);
        else if ( Mini_AigNodeIsPo( p, i ) )
            Abc_ObjAddFanin( (pObj = Abc_NtkCreatePo(pNtk)), Abc_NodeFanin0Copy(pNtk, vCopies, p, i) );
        else if ( Mini_AigNodeIsAnd( p, i ) )
            pObj = Abc_AigAnd((Abc_Aig_t *)pNtk->pManFunc, Abc_NodeFanin0Copy(pNtk, vCopies, p, i), Abc_NodeFanin1Copy(pNtk, vCopies, p, i));
        else assert( 0 );
        Vec_IntPush( vCopies, Abc_ObjToLit(pObj) );
    }
    assert( Vec_IntSize(vCopies) == nNodes );
    Abc_AigCleanup( (Abc_Aig_t *)pNtk->pManFunc );
    Vec_IntFree( vCopies );
    Abc_NtkAddDummyPiNames( pNtk );
    Abc_NtkAddDummyPoNames( pNtk );
    if ( !Abc_NtkCheck( pNtk ) )
        fprintf( stdout, "Abc_NtkFromMini(): Network check has failed.\n" );
    // add latches
    if ( Mini_AigRegNum(p) > 0 )
    {
        extern Abc_Ntk_t * Abc_NtkRestrashWithLatches( Abc_Ntk_t * pNtk, int nLatches );
        Abc_Ntk_t * pTemp;
        pNtk = Abc_NtkRestrashWithLatches( pTemp = pNtk, Mini_AigRegNum(p) );
        Abc_NtkDelete( pTemp );
    }
    return pNtk;
}
Beispiel #7
0
/**Function*************************************************************

  Synopsis    [Creates a new manager.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
ABC_Manager ABC_InitManager()
{
    ABC_Manager_t * mng;
    Abc_Start();
    mng = ABC_ALLOC( ABC_Manager_t, 1 );
    memset( mng, 0, sizeof(ABC_Manager_t) );
    mng->pNtk = Abc_NtkAlloc( ABC_NTK_LOGIC, ABC_FUNC_SOP, 1 );
    mng->pNtk->pName = Extra_UtilStrsav("csat_network");
    mng->tName2Node = stmm_init_table(strcmp, stmm_strhash);
    mng->tNode2Name = stmm_init_table(stmm_ptrcmp, stmm_ptrhash);
    mng->pMmNames   = Mem_FlexStart();
    mng->vNodes     = Vec_PtrAlloc( 100 );
    mng->vValues    = Vec_IntAlloc( 100 );
    mng->mode       = 0; // set "resource-aware integration" as the default mode
    // set default parameters for CEC
    Prove_ParamsSetDefault( &mng->Params );
    // set infinite resource limit for the final mitering
//    mng->Params.nMiteringLimitLast = ABC_INFINITY;
    return mng;
}
Beispiel #8
0
/**Function*************************************************************

  Synopsis    [Starts a new network using existing network as a model.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
Abc_Ntk_t * Abc_NtkStartFromNoLatches( Abc_Ntk_t * pNtk, Abc_NtkType_t Type, Abc_NtkFunc_t Func )
{
    Abc_Ntk_t * pNtkNew; 
    Abc_Obj_t * pObj;
    int i;
    if ( pNtk == NULL )
        return NULL;
    assert( Type != ABC_NTK_NETLIST );
    // start the network
    pNtkNew = Abc_NtkAlloc( Type, Func, 1 );
    // duplicate the name and the spec
    pNtkNew->pName = Extra_UtilStrsav(pNtk->pName);
    pNtkNew->pSpec = Extra_UtilStrsav(pNtk->pSpec);
    // clean the node copy fields
    Abc_NtkCleanCopy( pNtk );
    // map the constant nodes
    if ( Abc_NtkIsStrash(pNtk) && Abc_NtkIsStrash(pNtkNew) )
        Abc_AigConst1(pNtk)->pCopy = Abc_AigConst1(pNtkNew);
    // clone CIs/CIs/boxes
    Abc_NtkForEachPi( pNtk, pObj, i )
        Abc_NtkDupObj( pNtkNew, pObj, 1 );
    Abc_NtkForEachPo( pNtk, pObj, i )
        Abc_NtkDupObj( pNtkNew, pObj, 1 );
    Abc_NtkForEachAssert( pNtk, pObj, i )
        Abc_NtkDupObj( pNtkNew, pObj, 1 );
    Abc_NtkForEachBox( pNtk, pObj, i )
    {
        if ( Abc_ObjIsLatch(pObj) )
            continue;
        Abc_NtkDupBox(pNtkNew, pObj, 1);
    }
    // transfer the names
//    Abc_NtkTrasferNamesNoLatches( pNtk, pNtkNew );
    Abc_ManTimeDup( pNtk, pNtkNew );
    // check that the CI/CO/latches are copied correctly
    assert( Abc_NtkPiNum(pNtk) == Abc_NtkPiNum(pNtkNew) );
    assert( Abc_NtkPoNum(pNtk) == Abc_NtkPoNum(pNtkNew) );
    return pNtkNew;
}
Beispiel #9
0
/**Function*************************************************************

  Synopsis    [Creates miter for the sensitivity analysis.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
Abc_Ntk_t * Abc_NtkSensitivityMiter( Abc_Ntk_t * pNtk, int iVar )
{
    Abc_Ntk_t * pMiter;
    Vec_Ptr_t * vNodes;
    Abc_Obj_t * pObj, * pNext, * pFanin, * pOutput, * pObjNew;
    int i;
    assert( Abc_NtkIsStrash(pNtk) );
    assert( iVar < Abc_NtkCiNum(pNtk) );

    // duplicate the network
    pMiter = Abc_NtkAlloc( ABC_NTK_STRASH, ABC_FUNC_AIG, 1 );
    pMiter->pName = Extra_UtilStrsav(pNtk->pName);
    pMiter->pSpec = Extra_UtilStrsav(pNtk->pSpec);

    // assign the PIs
    Abc_NtkCleanCopy( pNtk );
    Abc_AigConst1(pNtk)->pCopy = Abc_AigConst1(pMiter);
    Abc_AigConst1(pNtk)->pData = Abc_AigConst1(pMiter);
    Abc_NtkForEachCi( pNtk, pObj, i )
    {
        pObj->pCopy = Abc_NtkCreatePi( pMiter );
        pObj->pData = pObj->pCopy;
    }
Beispiel #10
0
/**Function*************************************************************

  Synopsis    [Structurally hashes the given window.]

  Description [The first PO is the observability condition. The second 
  is the node's function. The remaining POs are the candidate divisors.]
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
Abc_Ntk_t * Res_WndStrash( Res_Win_t * p )
{
    Vec_Ptr_t * vPairs;
    Abc_Ntk_t * pAig;
    Abc_Obj_t * pObj, * pMiter;
    int i;
    assert( Abc_NtkHasAig(p->pNode->pNtk) );
//    Abc_NtkCleanCopy( p->pNode->pNtk );
    // create the network
    pAig = Abc_NtkAlloc( ABC_NTK_STRASH, ABC_FUNC_AIG, 1 );
    pAig->pName = Extra_UtilStrsav( "window" );
    // create the inputs
    Vec_PtrForEachEntry( Abc_Obj_t *, p->vLeaves, pObj, i )
        pObj->pCopy = Abc_NtkCreatePi( pAig );
    Vec_PtrForEachEntry( Abc_Obj_t *, p->vBranches, pObj, i )
        pObj->pCopy = Abc_NtkCreatePi( pAig );
    // go through the nodes in the topological order
    Vec_PtrForEachEntry( Abc_Obj_t *, p->vNodes, pObj, i )
    {
        pObj->pCopy = Abc_ConvertAigToAig( pAig, pObj );
        if ( pObj == p->pNode )
            pObj->pCopy = Abc_ObjNot( pObj->pCopy );
    }
    // collect the POs
    vPairs = Vec_PtrAlloc( 2 * Vec_PtrSize(p->vRoots) );
    Vec_PtrForEachEntry( Abc_Obj_t *, p->vRoots, pObj, i )
    {
        Vec_PtrPush( vPairs, pObj->pCopy );
        Vec_PtrPush( vPairs, NULL );
    }
    // mark the TFO of the node
    Abc_NtkIncrementTravId( p->pNode->pNtk );
    Res_WinSweepLeafTfo_rec( p->pNode, (int)p->pNode->Level + p->nWinTfoMax );
    // update strashing of the node
    p->pNode->pCopy = Abc_ObjNot( p->pNode->pCopy );
    Abc_NodeSetTravIdPrevious( p->pNode );
    // redo strashing in the TFO
    Vec_PtrForEachEntry( Abc_Obj_t *, p->vNodes, pObj, i )
    {
        if ( Abc_NodeIsTravIdCurrent(pObj) )
            pObj->pCopy = Abc_ConvertAigToAig( pAig, pObj );
    }
    // collect the POs
    Vec_PtrForEachEntry( Abc_Obj_t *, p->vRoots, pObj, i )
        Vec_PtrWriteEntry( vPairs, 2 * i + 1, pObj->pCopy );
    // add the miter
    pMiter = Abc_AigMiter( (Abc_Aig_t *)pAig->pManFunc, vPairs, 0 );
    Abc_ObjAddFanin( Abc_NtkCreatePo(pAig), pMiter );
    Vec_PtrFree( vPairs );
    // add the node
    Abc_ObjAddFanin( Abc_NtkCreatePo(pAig), p->pNode->pCopy );
    // add the fanins
    Abc_ObjForEachFanin( p->pNode, pObj, i )
        Abc_ObjAddFanin( Abc_NtkCreatePo(pAig), pObj->pCopy );
    // add the divisors
    Vec_PtrForEachEntry( Abc_Obj_t *, p->vDivs, pObj, i )
        Abc_ObjAddFanin( Abc_NtkCreatePo(pAig), pObj->pCopy );
    // add the names
    Abc_NtkAddDummyPiNames( pAig );
    Abc_NtkAddDummyPoNames( pAig );
    // check the resulting network
    if ( !Abc_NtkCheck( pAig ) )
        fprintf( stdout, "Res_WndStrash(): Network check has failed.\n" );
    return pAig;
}
Beispiel #11
0
    Abc_NtkForEachNet( pNtk, pObj, i )
    {
        nValues = Abc_ObjMvVarNum(pObj);
        if ( nValuesMax < nValues )
            nValuesMax = nValues;
    }
    nBits = Extra_Base2Log( nValuesMax );
    pBits = ABC_ALLOC( Abc_Obj_t *, nBits );

    // clean the node copy fields
    Abc_NtkCleanCopy( pNtk );
    // collect the nodes
    vNodes = Abc_NtkDfs( pNtk, 0 );

    // start the network
    pNtkNew = Abc_NtkAlloc( ABC_NTK_STRASH, ABC_FUNC_AIG, 1 );
    // duplicate the name and the spec
    pNtkNew->pName = Extra_UtilStrsav( pNtk->pName );
//    pNtkNew->pSpec = Extra_UtilStrsav( pNtk->pName );

    nCount1 = nCount2 = 0;
    // encode the CI nets
    Abc_NtkIncrementTravId( pNtk );
    if ( fUsePositional )
    {
        Abc_NtkForEachCi( pNtk, pObj, i )
        {
            if ( !Abc_ObjIsPi(pObj) )
                continue;
            pNet = Abc_ObjFanout0(pObj);
            nValues = Abc_ObjMvVarNum(pNet);
Beispiel #12
0
/**Function*************************************************************

  Synopsis    [Reads one (main or exdc) network from the BLIF file.]

  Description []
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
Abc_Ntk_t * Io_ReadBlifNetworkOne( Io_ReadBlif_t * p )
{
    ProgressBar * pProgress = NULL;
    Abc_Ntk_t * pNtk;
    char * pDirective;
    int iLine, fTokensReady, fStatus;

    // make sure the tokens are present
    assert( p->vTokens != NULL );

    // create the new network
    p->pNtkCur = pNtk = Abc_NtkAlloc( ABC_NTK_NETLIST, ABC_FUNC_SOP, 1 );
    // read the model name
    if ( strcmp( (char *)p->vTokens->pArray[0], ".model" ) == 0 )
    {
        char * pToken, * pPivot;
        if ( Vec_PtrSize(p->vTokens) != 2 )
        {
            p->LineCur = Extra_FileReaderGetLineNumber(p->pReader, 0);
            sprintf( p->sError, "The .model line does not have exactly two entries." );
            Io_ReadBlifPrintErrorMessage( p );
            return NULL;
        }
        for ( pPivot = pToken = (char *)Vec_PtrEntry(p->vTokens, 1); *pToken; pToken++ )
            if ( *pToken == '/' || *pToken == '\\' )
                pPivot = pToken+1;
        pNtk->pName = Extra_UtilStrsav( pPivot );
    }
    else if ( strcmp( (char *)p->vTokens->pArray[0], ".exdc" ) != 0 ) 
    {
        printf( "%s: File parsing skipped after line %d (\"%s\").\n", p->pFileName, 
            Extra_FileReaderGetLineNumber(p->pReader, 0), (char*)p->vTokens->pArray[0] );
        Abc_NtkDelete(pNtk);
        p->pNtkCur = NULL;
        return NULL;
    }

    // read the inputs/outputs
    if ( p->pNtkMaster == NULL )
        pProgress = Extra_ProgressBarStart( stdout, Extra_FileReaderGetFileSize(p->pReader) );
    fTokensReady = fStatus = 0;
    for ( iLine = 0; fTokensReady || (p->vTokens = Io_ReadBlifGetTokens(p)); iLine++ )
    {
        if ( p->pNtkMaster == NULL && iLine % 1000 == 0 )
            Extra_ProgressBarUpdate( pProgress, Extra_FileReaderGetCurPosition(p->pReader), NULL );

        // consider different line types
        fTokensReady = 0;
        pDirective = (char *)p->vTokens->pArray[0];
        if ( !strcmp( pDirective, ".names" ) )
            { fStatus = Io_ReadBlifNetworkNames( p, &p->vTokens ); fTokensReady = 1; }
        else if ( !strcmp( pDirective, ".gate" ) )
            fStatus = Io_ReadBlifNetworkGate( p, p->vTokens );
        else if ( !strcmp( pDirective, ".latch" ) )
            fStatus = Io_ReadBlifNetworkLatch( p, p->vTokens );
        else if ( !strcmp( pDirective, ".inputs" ) )
            fStatus = Io_ReadBlifNetworkInputs( p, p->vTokens );
        else if ( !strcmp( pDirective, ".outputs" ) )
            fStatus = Io_ReadBlifNetworkOutputs( p, p->vTokens );
        else if ( !strcmp( pDirective, ".input_arrival" ) )
            fStatus = Io_ReadBlifNetworkInputArrival( p, p->vTokens );
        else if ( !strcmp( pDirective, ".output_required" ) )
            fStatus = Io_ReadBlifNetworkOutputRequired( p, p->vTokens );
        else if ( !strcmp( pDirective, ".default_input_arrival" ) )
            fStatus = Io_ReadBlifNetworkDefaultInputArrival( p, p->vTokens );
        else if ( !strcmp( pDirective, ".default_output_required" ) )
            fStatus = Io_ReadBlifNetworkDefaultOutputRequired( p, p->vTokens );
        else if ( !strcmp( pDirective, ".and_gate_delay" ) )
            fStatus = Io_ReadBlifNetworkAndGateDelay( p, p->vTokens );
//        else if ( !strcmp( pDirective, ".subckt" ) )
//            fStatus = Io_ReadBlifNetworkSubcircuit( p, p->vTokens );
        else if ( !strcmp( pDirective, ".exdc" ) )
            break;
        else if ( !strcmp( pDirective, ".end" ) )
        {
            p->vTokens = Io_ReadBlifGetTokens(p);
            break;
        }
        else if ( !strcmp( pDirective, ".blackbox" ) )
        {
            pNtk->ntkType = ABC_NTK_NETLIST;
            pNtk->ntkFunc = ABC_FUNC_BLACKBOX;
            Mem_FlexStop( (Mem_Flex_t *)pNtk->pManFunc, 0 );
            pNtk->pManFunc = NULL;
        }
        else
            printf( "%s (line %d): Skipping directive \"%s\".\n", p->pFileName, 
                Extra_FileReaderGetLineNumber(p->pReader, 0), pDirective );
        if ( p->vTokens == NULL ) // some files do not have ".end" in the end
            break;
        if ( fStatus == 1 )
        {
            Extra_ProgressBarStop( pProgress );
            Abc_NtkDelete( pNtk );
            return NULL;
        }
    }
    if ( p->pNtkMaster == NULL )
        Extra_ProgressBarStop( pProgress );
    return pNtk;
}
/**Function*************************************************************

  Synopsis    [Implements the given retiming on the sequential AIG.]

  Description [Returns 0 of initial state computation fails.]
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
int Seq_NtkImplementRetimingBackward( Abc_Ntk_t * pNtk, Vec_Ptr_t * vMoves, int fVerbose )
{
    Seq_RetEdge_t RetEdge;
    stmm_table * tTable;
    stmm_generator * gen;
    Vec_Int_t * vValues;
    Abc_Ntk_t * pNtkProb, * pNtkMiter, * pNtkCnf;
    Abc_Obj_t * pNode, * pNodeNew;
    int * pModel, RetValue, i, clk;

    // return if the retiming is trivial
    if ( Vec_PtrSize(vMoves) == 0 )
        return 1;

    // create the network for the initial state computation
    // start the table and the array of PO values
    pNtkProb = Abc_NtkAlloc( ABC_NTK_LOGIC, ABC_FUNC_SOP, 1 );
    tTable   = stmm_init_table( stmm_numcmp, stmm_numhash );
    vValues  = Vec_IntAlloc( 100 );

    // perform the backward moves and build the network for initial state computation
    RetValue = 0;
    Vec_PtrForEachEntry( vMoves, pNode, i )
        RetValue |= Abc_ObjRetimeBackward( pNode, pNtkProb, tTable, vValues );

    // add the PIs corresponding to the white spots
    stmm_foreach_item( tTable, gen, (char **)&RetEdge, (char **)&pNodeNew )
        Abc_ObjAddFanin( pNodeNew, Abc_NtkCreatePi(pNtkProb) );

    // add the PI/PO names
    Abc_NtkAddDummyPiNames( pNtkProb );
    Abc_NtkAddDummyPoNames( pNtkProb );
    Abc_NtkAddDummyAssertNames( pNtkProb );

    // make sure everything is okay with the network structure
    if ( !Abc_NtkDoCheck( pNtkProb ) )
    {
        printf( "Seq_NtkImplementRetimingBackward: The internal network check has failed.\n" );
        Abc_NtkRetimeSetInitialValues( pNtk, tTable, NULL );
        Abc_NtkDelete( pNtkProb );
        stmm_free_table( tTable );
        Vec_IntFree( vValues );
        return 0;
    }

    // check if conflict is found
    if ( RetValue )
    {
        printf( "Seq_NtkImplementRetimingBackward: A top level conflict is detected. DC latch values are used.\n" );
        Abc_NtkRetimeSetInitialValues( pNtk, tTable, NULL );
        Abc_NtkDelete( pNtkProb );
        stmm_free_table( tTable );
        Vec_IntFree( vValues );
        return 0;
    }

    // get the miter cone
    pNtkMiter = Abc_NtkCreateTarget( pNtkProb, pNtkProb->vCos, vValues );
    Abc_NtkDelete( pNtkProb );
    Vec_IntFree( vValues );

    if ( fVerbose )
    printf( "The number of ANDs in the AIG = %5d.\n", Abc_NtkNodeNum(pNtkMiter) );

    // transform the miter into a logic network for efficient CNF construction
//    pNtkCnf = Abc_Ntk_Renode( pNtkMiter, 0, 100, 1, 0, 0 );
//    Abc_NtkDelete( pNtkMiter );
    pNtkCnf = pNtkMiter;

    // solve the miter
clk = clock();
//    RetValue = Abc_NtkMiterSat_OldAndRusty( pNtkCnf, 30, 0 );
    RetValue = Abc_NtkMiterSat( pNtkCnf, (sint64)500000, (sint64)50000000, 0, 0, NULL, NULL );
if ( fVerbose )
if ( clock() - clk > 100 )
{
PRT( "SAT solving time", clock() - clk );
}
    pModel = pNtkCnf->pModel;  pNtkCnf->pModel = NULL;
    Abc_NtkDelete( pNtkCnf );

    // analyze the result
    if ( RetValue == -1 || RetValue == 1 )
    {
        Abc_NtkRetimeSetInitialValues( pNtk, tTable, NULL );
        if ( RetValue == 1 )
            printf( "Seq_NtkImplementRetimingBackward: The problem is unsatisfiable. DC latch values are used.\n" );
        else
            printf( "Seq_NtkImplementRetimingBackward: The SAT problem timed out. DC latch values are used.\n" );
        stmm_free_table( tTable );
        return 0;
    }

    // set the values of the latches
    Abc_NtkRetimeSetInitialValues( pNtk, tTable, pModel );
    stmm_free_table( tTable );
    free( pModel );
    return 1;
}
Beispiel #14
0
ABC_NAMESPACE_IMPL_START


// For description of Binary BLIF format, refer to "abc/src/aig/bbl/bblif.h"

////////////////////////////////////////////////////////////////////////
///                        DECLARATIONS                              ///
////////////////////////////////////////////////////////////////////////

////////////////////////////////////////////////////////////////////////
///                     FUNCTION DEFINITIONS                         ///
////////////////////////////////////////////////////////////////////////

/**Fnction*************************************************************

  Synopsis    [Constructs ABC network from the manager.]

  Description [The ABC network is started, as well as the array vCopy,
  which will map the new ID of each object in the BBLIF manager into
  the ponter ot the corresponding object in the ABC. For each internal
  node, determined by Bbl_ObjIsLut(), the SOP representation is created
  by retrieving the SOP representation of the BBLIF object. Finally,
  the objects are connected using fanin/fanout creation, and the dummy
  names are assigned because ABC requires each CI/CO to have a name.]
               
  SideEffects []

  SeeAlso     []

***********************************************************************/
Abc_Ntk_t * Bbl_ManToAbc( Bbl_Man_t * p )
{
    Abc_Ntk_t * pNtk;
    Abc_Obj_t * pObjNew;
    Bbl_Obj_t * pObj, * pFanin;
    Vec_Ptr_t * vCopy;
    // start the network
    pNtk = Abc_NtkAlloc( ABC_NTK_LOGIC, ABC_FUNC_SOP, 1 );
    pNtk->pName = Extra_UtilStrsav( Bbl_ManName(p) );
    // create objects
    vCopy = Vec_PtrStart( 1000 );
    Bbl_ManForEachObj( p, pObj )
    {
        if ( Bbl_ObjIsInput(pObj) )
            pObjNew = Abc_NtkCreatePi( pNtk );
        else if ( Bbl_ObjIsOutput(pObj) )
            pObjNew = Abc_NtkCreatePo( pNtk );
        else if ( Bbl_ObjIsLut(pObj) )
            pObjNew = Abc_NtkCreateNode( pNtk );
        else assert( 0 );
        if ( Bbl_ObjIsLut(pObj) )
            pObjNew->pData = Abc_SopRegister( (Mem_Flex_t *)pNtk->pManFunc, Bbl_ObjSop(p, pObj) );
        Vec_PtrSetEntry( vCopy, Bbl_ObjId(pObj), pObjNew );
    }
    // connect objects
    Bbl_ManForEachObj( p, pObj )
        Bbl_ObjForEachFanin( pObj, pFanin )
            Abc_ObjAddFanin( (Abc_Obj_t *)Vec_PtrEntry(vCopy, Bbl_ObjId(pObj)), (Abc_Obj_t *)Vec_PtrEntry(vCopy, Bbl_ObjId(pFanin)) );
    // finalize
    Vec_PtrFree( vCopy );
    Abc_NtkAddDummyPiNames( pNtk );
    Abc_NtkAddDummyPoNames( pNtk );
    if ( !Abc_NtkCheck( pNtk ) )
        printf( "Bbl_ManToAbc(): Network check has failed.\n" );
    return pNtk;
}
Beispiel #15
0
/**Function*************************************************************

  Synopsis    [Starts the record for the given network.]

  Description []

  SideEffects []

  SeeAlso     []

***********************************************************************/
void Abc_NtkRecStart( Abc_Ntk_t * pNtk, int nVars, int nCuts )
{
    Abc_ManRec_t * p;
    Abc_Obj_t * pObj, ** ppSpot;
    char Buffer[10];
    unsigned * pTruth;
    int i, RetValue;
    int clkTotal = clock(), clk;

    assert( s_pMan == NULL );
    if ( pNtk == NULL )
    {
        assert( nVars > 2 && nVars <= 16 );
        pNtk = Abc_NtkAlloc( ABC_NTK_STRASH, ABC_FUNC_AIG, 1 );
        pNtk->pName = Extra_UtilStrsav( "record" );
    }
    else
    {
        if ( Abc_NtkGetChoiceNum(pNtk) > 0 )
        {
            printf( "The starting record should be a network without choice nodes.\n" );
            return;
        }
        if ( Abc_NtkPiNum(pNtk) > 16 )
        {
            printf( "The starting record should be a network with no more than %d primary inputs.\n", 16 );
            return;
        }
        if ( Abc_NtkPiNum(pNtk) > nVars )
            printf( "The starting record has %d inputs (warning only).\n", Abc_NtkPiNum(pNtk) );
        pNtk = Abc_NtkDup( pNtk );
    }
    // create the primary inputs
    for ( i = Abc_NtkPiNum(pNtk); i < nVars; i++ )
    {
        pObj = Abc_NtkCreatePi( pNtk );
        Buffer[0] = 'a' + i;
        Buffer[1] = 0;
        Abc_ObjAssignName( pObj, Buffer, NULL );
    }
    Abc_NtkCleanCopy( pNtk );
    Abc_NtkCleanEquiv( pNtk );

    // start the manager
    p = ABC_ALLOC( Abc_ManRec_t, 1 );
    memset( p, 0, sizeof(Abc_ManRec_t) );
    p->pNtk = pNtk;
    p->nVars = Abc_NtkPiNum(pNtk);
    p->nWords = Kit_TruthWordNum( p->nVars );
    p->nCuts = nCuts;
    p->nVarsInit = nVars;

    // create elementary truth tables
    p->vTtElems = Vec_PtrAlloc( 0 );
    assert( p->vTtElems->pArray == NULL );
    p->vTtElems->nSize = p->nVars;
    p->vTtElems->nCap = p->nVars;
    p->vTtElems->pArray = (void *)Extra_TruthElementary( p->nVars );

    // allocate room for node truth tables
    if ( Abc_NtkObjNum(pNtk) > (1<<14) )
        p->vTtNodes = Vec_PtrAllocSimInfo( 2 * Abc_NtkObjNum(pNtk), p->nWords );
    else
        p->vTtNodes = Vec_PtrAllocSimInfo( 1<<14, p->nWords );

    // create hash table
    p->nBins = 50011;
    p->pBins = ABC_ALLOC( Abc_Obj_t *, p->nBins );
    memset( p->pBins, 0, sizeof(Abc_Obj_t *) * p->nBins );

    // set elementary tables
    Kit_TruthFill( Vec_PtrEntry(p->vTtNodes, 0), p->nVars );
    Abc_NtkForEachPi( pNtk, pObj, i )
    Kit_TruthCopy( Vec_PtrEntry(p->vTtNodes, pObj->Id), Vec_PtrEntry(p->vTtElems, i), p->nVars );

    // compute the tables
    clk = clock();
    Abc_AigForEachAnd( pNtk, pObj, i )
    {
        RetValue = Abc_NtkRecComputeTruth( pObj, p->vTtNodes, p->nVars );
        assert( RetValue );
    }