Commit a8db621d by Alan Mishchenko

Version abc70703

parent d6804597
......@@ -42,7 +42,7 @@ RSC=rc.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c
# ADD CPP /nologo /W3 /GX /O2 /I "src\base\abc" /I "src\base\abci" /I "src\base\abcs" /I "src\base\seq" /I "src\base\cmd" /I "src\base\io" /I "src\base\main" /I "src\bdd\cudd" /I "src\bdd\epd" /I "src\bdd\mtr" /I "src\bdd\parse" /I "src\bdd\dsd" /I "src\bdd\reo" /I "src\sop\ft" /I "src\sat\asat" /I "src\sat\bsat" /I "src\sat\msat" /I "src\sat\fraig" /I "src\opt\cut" /I "src\opt\dec" /I "src\opt\fxu" /I "src\opt\sim" /I "src\opt\rwr" /I "src\opt\kit" /I "src\opt\res" /I "src\map\fpga" /I "src\map\if" /I "src\map\mapper" /I "src\map\mio" /I "src\map\super" /I "src\misc\extra" /I "src\misc\st" /I "src\misc\mvc" /I "src\misc\util" /I "src\misc\npn" /I "src\misc\vec" /I "src\misc\espresso" /I "src\misc\nm" /I "src\misc\hash" /I "src\aig\ivy" /I "src\aig\hop" /I "src\aig\rwt" /I "src\aig\deco" /I "src\aig\mem" /I "src\aig\dar" /I "src\temp\esop" /I "src\phys\place" /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /D "__STDC__" /FR /YX /FD /c
# ADD CPP /nologo /W3 /GX /O2 /I "src\base\abc" /I "src\base\abci" /I "src\base\abcs" /I "src\base\seq" /I "src\base\cmd" /I "src\base\io" /I "src\base\main" /I "src\bdd\cudd" /I "src\bdd\epd" /I "src\bdd\mtr" /I "src\bdd\parse" /I "src\bdd\dsd" /I "src\bdd\reo" /I "src\sop\ft" /I "src\sat\asat" /I "src\sat\bsat" /I "src\sat\msat" /I "src\sat\fraig" /I "src\opt\cut" /I "src\opt\dec" /I "src\opt\fxu" /I "src\opt\sim" /I "src\opt\rwr" /I "src\opt\kit" /I "src\opt\res" /I "src\map\fpga" /I "src\map\if" /I "src\map\mapper" /I "src\map\mio" /I "src\map\super" /I "src\misc\extra" /I "src\misc\st" /I "src\misc\mvc" /I "src\misc\util" /I "src\misc\npn" /I "src\misc\vec" /I "src\misc\espresso" /I "src\misc\nm" /I "src\misc\hash" /I "src\aig\ivy" /I "src\aig\hop" /I "src\aig\rwt" /I "src\aig\deco" /I "src\aig\mem" /I "src\aig\dar" /I "src\aig\cnf" /I "src\aig\fra" /I "src\temp\esop" /I "src\phys\place" /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /D "__STDC__" /FR /YX /FD /c
# ADD BASE RSC /l 0x409 /d "NDEBUG"
# ADD RSC /l 0x409 /d "NDEBUG"
BSC32=bscmake.exe
......@@ -66,7 +66,7 @@ LINK32=link.exe
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /GZ /c
# ADD CPP /nologo /W3 /Gm /GX /ZI /Od /I "src\base\abc" /I "src\base\abci" /I "src\base\abcs" /I "src\base\seq" /I "src\base\cmd" /I "src\base\io" /I "src\base\main" /I "src\bdd\cudd" /I "src\bdd\epd" /I "src\bdd\mtr" /I "src\bdd\parse" /I "src\bdd\dsd" /I "src\bdd\reo" /I "src\sop\ft" /I "src\sat\asat" /I "src\sat\bsat" /I "src\sat\msat" /I "src\sat\fraig" /I "src\opt\cut" /I "src\opt\dec" /I "src\opt\fxu" /I "src\opt\sim" /I "src\opt\rwr" /I "src\opt\kit" /I "src\opt\res" /I "src\map\fpga" /I "src\map\if" /I "src\map\mapper" /I "src\map\mio" /I "src\map\super" /I "src\misc\extra" /I "src\misc\st" /I "src\misc\mvc" /I "src\misc\util" /I "src\misc\npn" /I "src\misc\vec" /I "src\misc\espresso" /I "src\misc\nm" /I "src\misc\hash" /I "src\aig\ivy" /I "src\aig\hop" /I "src\aig\rwt" /I "src\aig\deco" /I "src\aig\mem" /I "src\aig\dar" /I "src\temp\esop" /I "src\phys\place" /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /D "__STDC__" /FR /YX /FD /GZ /c
# ADD CPP /nologo /W3 /Gm /GX /ZI /Od /I "src\base\abc" /I "src\base\abci" /I "src\base\abcs" /I "src\base\seq" /I "src\base\cmd" /I "src\base\io" /I "src\base\main" /I "src\bdd\cudd" /I "src\bdd\epd" /I "src\bdd\mtr" /I "src\bdd\parse" /I "src\bdd\dsd" /I "src\bdd\reo" /I "src\sop\ft" /I "src\sat\asat" /I "src\sat\bsat" /I "src\sat\msat" /I "src\sat\fraig" /I "src\opt\cut" /I "src\opt\dec" /I "src\opt\fxu" /I "src\opt\sim" /I "src\opt\rwr" /I "src\opt\kit" /I "src\opt\res" /I "src\map\fpga" /I "src\map\if" /I "src\map\mapper" /I "src\map\mio" /I "src\map\super" /I "src\misc\extra" /I "src\misc\st" /I "src\misc\mvc" /I "src\misc\util" /I "src\misc\npn" /I "src\misc\vec" /I "src\misc\espresso" /I "src\misc\nm" /I "src\misc\hash" /I "src\aig\ivy" /I "src\aig\hop" /I "src\aig\rwt" /I "src\aig\deco" /I "src\aig\mem" /I "src\aig\dar" /I "src\aig\cnf" /I "src\aig\fra" /I "src\temp\esop" /I "src\phys\place" /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /D "__STDC__" /FR /YX /FD /GZ /c
# SUBTRACT CPP /X
# ADD BASE RSC /l 0x409 /d "_DEBUG"
# ADD RSC /l 0x409 /d "_DEBUG"
......@@ -822,10 +822,6 @@ SOURCE=.\src\aig\dar\darCheck.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\dar\darCnf.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\dar\darCore.c
# End Source File
# Begin Source File
......@@ -838,10 +834,6 @@ SOURCE=.\src\aig\dar\darData.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\dar\darData2.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\dar\darDfs.c
# End Source File
# Begin Source File
......@@ -881,6 +873,82 @@ SOURCE=.\src\aig\dar\darTruth.c
SOURCE=.\src\aig\dar\darUtil.c
# End Source File
# End Group
# Begin Group "fra"
# PROP Default_Filter ""
# Begin Source File
SOURCE=.\src\aig\fra\fra.h
# End Source File
# Begin Source File
SOURCE=.\src\aig\fra\fraAnd.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\fra\fraClass.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\fra\fraCnf.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\fra\fraCore.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\fra\fraMan.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\fra\fraSat.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\fra\fraSim.c
# End Source File
# End Group
# Begin Group "cnf"
# PROP Default_Filter ""
# Begin Source File
SOURCE=.\src\aig\cnf\cnf.h
# End Source File
# Begin Source File
SOURCE=.\src\aig\cnf\cnfCore.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\cnf\cnfCut.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\cnf\cnfData.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\cnf\cnfMan.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\cnf\cnfMap.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\cnf\cnfPost.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\cnf\cnfUtil.c
# End Source File
# Begin Source File
SOURCE=.\src\aig\cnf\cnfWrite.c
# End Source File
# End Group
# End Group
# Begin Group "bdd"
......
......@@ -80,6 +80,7 @@ alias u undo
alias w write
alias wa write_aiger
alias wb write_bench
alias wc write_cnf
alias wh write_hie
alias wl write_blif
alias wp write_pla
......@@ -141,7 +142,7 @@ alias qsA "qvar -I 96 -u; qvar -I 97 -u; qvar -I 98 -u; qvar -I 99 -u; qvar
alias chnew "st; haig_start; resyn2; haig_use"
alias chnewrs "st; haig_start; resyn2rs; haig_use"
alias t "read_dsd a*(b+(c*d)+e); clp -r; print_dsd"
alias t0 "read_dsd a*(b+(c*d)+e); clp -r; print_dsd"
alias t1 "read_dsd a*(b+(c*d)); clp -r; print_dsd"
alias t2 "read_dsd 56BA(a,b,c,d); clp -r; print_dsd"
alias t3 "read_dsd 56BA(a,b*c,e,d); clp -r; print_dsd"
......@@ -167,3 +168,7 @@ alias tst6 "r i10_if6.blif; st; ps; r x/rec6_16_.blif; st; rec_start; r i10_
alias bug "r pj1_if3.blif; lp"
alias table "r lutexp.baf; test"
alias t "r c.blif; st; wc c.cnf"
/**CFile****************************************************************
FileName [cnf.h]
SystemName [ABC: Logic synthesis and verification system.]
PackageName [DAG-aware AIG rewriting.]
Synopsis [External declarations.]
Author [Alan Mishchenko]
Affiliation [UC Berkeley]
Date [Ver. 1.0. Started - April 28, 2007.]
Revision [$Id: cnf.h,v 1.00 2007/04/28 00:00:00 alanmi Exp $]
***********************************************************************/
#ifndef __CNF_H__
#define __CNF_H__
#ifdef __cplusplus
extern "C" {
#endif
////////////////////////////////////////////////////////////////////////
/// INCLUDES ///
////////////////////////////////////////////////////////////////////////
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#include <time.h>
#include "vec.h"
#include "dar.h"
////////////////////////////////////////////////////////////////////////
/// PARAMETERS ///
////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////
/// BASIC TYPES ///
////////////////////////////////////////////////////////////////////////
typedef struct Cnf_Man_t_ Cnf_Man_t;
typedef struct Cnf_Dat_t_ Cnf_Dat_t;
typedef struct Cnf_Cut_t_ Cnf_Cut_t;
// the CNF asserting outputs of AIG to be 1
struct Cnf_Dat_t_
{
Dar_Man_t * pMan; // the AIG manager, for which CNF is computed
int nVars; // the number of variables
int nLiterals; // the number of CNF literals
int nClauses; // the number of CNF clauses
int ** pClauses; // the CNF clauses
int * pVarNums; // the number of CNF variable for each node ID (-1 if unused)
};
// the cut used to represent node in the AIG
struct Cnf_Cut_t_
{
char nFanins; // the number of leaves
char Cost; // the cost of this cut
short nWords; // the number of words in truth table
Vec_Int_t * vIsop[2]; // neg/pos ISOPs
int pFanins[0]; // the fanins (followed by the truth table)
};
// the CNF computation manager
struct Cnf_Man_t_
{
Dar_Man_t * pManAig; // the underlying AIG manager
char * pSopSizes; // sizes of SOPs for 4-variable functions
char ** pSops; // the SOPs for 4-variable functions
int aArea; // the area of the mapping
Dar_MmFlex_t * pMemCuts; // memory manager for cuts
int nMergeLimit; // the limit on the size of merged cut
unsigned * pTruths[4]; // temporary truth tables
Vec_Int_t * vMemory; // memory for intermediate ISOP representation
};
static inline int Cnf_CutLeaveNum( Cnf_Cut_t * pCut ) { return pCut->nFanins; }
static inline int * Cnf_CutLeaves( Cnf_Cut_t * pCut ) { return pCut->pFanins; }
static inline unsigned * Cnf_CutTruth( Cnf_Cut_t * pCut ) { return (unsigned *)(pCut->pFanins + pCut->nFanins); }
static inline Cnf_Cut_t * Cnf_ObjBestCut( Dar_Obj_t * pObj ) { return pObj->pData; }
static inline void Cnf_ObjSetBestCut( Dar_Obj_t * pObj, Cnf_Cut_t * pCut ) { pObj->pData = pCut; }
////////////////////////////////////////////////////////////////////////
/// MACRO DEFINITIONS ///
////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////
/// ITERATORS ///
////////////////////////////////////////////////////////////////////////
// iterator over leaves of the cut
#define Cnf_CutForEachLeaf( p, pCut, pLeaf, i ) \
for ( i = 0; (i < (int)(pCut)->nFanins) && ((pLeaf) = Dar_ManObj(p, (pCut)->pFanins[i])); i++ )
////////////////////////////////////////////////////////////////////////
/// FUNCTION DECLARATIONS ///
////////////////////////////////////////////////////////////////////////
/*=== cnfCore.c ========================================================*/
extern Cnf_Dat_t * Cnf_Derive( Cnf_Man_t * p, Dar_Man_t * pAig );
/*=== cnfCut.c ========================================================*/
extern Cnf_Cut_t * Cnf_CutCreate( Cnf_Man_t * p, Dar_Obj_t * pObj );
extern void Cnf_CutPrint( Cnf_Cut_t * pCut );
extern void Cnf_CutFree( Cnf_Cut_t * pCut );
extern void Cnf_CutUpdateRefs( Cnf_Man_t * p, Cnf_Cut_t * pCut, Cnf_Cut_t * pCutFan, Cnf_Cut_t * pCutRes );
extern Cnf_Cut_t * Cnf_CutCompose( Cnf_Man_t * p, Cnf_Cut_t * pCut, Cnf_Cut_t * pCutFan, int iFan );
/*=== cnfData.c ========================================================*/
extern void Cnf_ReadMsops( char ** ppSopSizes, char *** ppSops );
/*=== cnfMan.c ========================================================*/
extern Cnf_Man_t * Cnf_ManStart();
extern void Cnf_ManStop( Cnf_Man_t * p );
extern void Cnf_DataFree( Cnf_Dat_t * p );
extern void Cnf_DataWriteIntoFile( Cnf_Dat_t * p, char * pFileName );
void * Cnf_DataWriteIntoSolver( Cnf_Dat_t * p );
/*=== cnfMap.c ========================================================*/
extern int Cnf_ManMapForCnf( Cnf_Man_t * p );
/*=== cnfPost.c ========================================================*/
extern void Cnf_ManTransferCuts( Cnf_Man_t * p );
extern void Cnf_ManFreeCuts( Cnf_Man_t * p );
extern void Cnf_ManPostprocess( Cnf_Man_t * p );
/*=== cnfUtil.c ========================================================*/
extern Vec_Ptr_t * Dar_ManScanMapping( Cnf_Man_t * p, int fCollect );
extern Vec_Ptr_t * Cnf_ManScanMapping( Cnf_Man_t * p, int fCollect );
/*=== cnfWrite.c ========================================================*/
extern void Cnf_SopConvertToVector( char * pSop, int nCubes, Vec_Int_t * vCover );
extern Cnf_Dat_t * Cnf_ManWriteCnf( Cnf_Man_t * p, Vec_Ptr_t * vMapped );
#ifdef __cplusplus
}
#endif
#endif
////////////////////////////////////////////////////////////////////////
/// END OF FILE ///
////////////////////////////////////////////////////////////////////////
/**CFile****************************************************************
FileName [cnfCore.c]
SystemName [ABC: Logic synthesis and verification system.]
PackageName [AIG-to-CNF conversion.]
Synopsis []
Author [Alan Mishchenko]
Affiliation [UC Berkeley]
Date [Ver. 1.0. Started - April 28, 2007.]
Revision [$Id: cnfCore.c,v 1.00 2007/04/28 00:00:00 alanmi Exp $]
***********************************************************************/
#include "cnf.h"
////////////////////////////////////////////////////////////////////////
/// DECLARATIONS ///
////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////
/// FUNCTION DEFINITIONS ///
////////////////////////////////////////////////////////////////////////
/**Function*************************************************************
Synopsis []
Description []
SideEffects []
SeeAlso []
***********************************************************************/
Cnf_Dat_t * Cnf_Derive( Cnf_Man_t * p, Dar_Man_t * pAig )
{
Cnf_Dat_t * pCnf = NULL;
Vec_Ptr_t * vMapped;
int nIters = 2;
int clk;
// connect the managers
pAig->pManCnf = p;
p->pManAig = pAig;
// generate cuts for all nodes, assign cost, and find best cuts
clk = clock();
Dar_ManComputeCuts( pAig );
PRT( "Cuts", clock() - clk );
/*
// iteratively improve area flow
for ( i = 0; i < nIters; i++ )
{
clk = clock();
Cnf_ManScanMapping( p, 0 );
Cnf_ManMapForCnf( p );
PRT( "iter ", clock() - clk );
}
*/
// write the file
vMapped = Dar_ManScanMapping( p, 1 );
Vec_PtrFree( vMapped );
clk = clock();
Cnf_ManTransferCuts( p );
Cnf_ManPostprocess( p );
Cnf_ManScanMapping( p, 0 );
/*
Cnf_ManPostprocess( p );
Cnf_ManScanMapping( p, 0 );
Cnf_ManPostprocess( p );
Cnf_ManScanMapping( p, 0 );
*/
PRT( "Ext ", clock() - clk );
/*
vMapped = Cnf_ManScanMapping( p, 1 );
pCnf = Cnf_ManWriteCnf( p, vMapped );
Vec_PtrFree( vMapped );
// clean up
Cnf_ManFreeCuts( p );
Dar_ManCutsFree( pAig );
return pCnf;
*/
return NULL;
}
////////////////////////////////////////////////////////////////////////
/// END OF FILE ///
////////////////////////////////////////////////////////////////////////
/**CFile****************************************************************
FileName [dar_.c]
FileName [cnfData.c]
SystemName [ABC: Logic synthesis and verification system.]
PackageName [DAG-aware AIG rewriting.]
PackageName [AIG-to-CNF conversion.]
Synopsis []
......@@ -14,11 +14,11 @@
Date [Ver. 1.0. Started - April 28, 2007.]
Revision [$Id: dar_.c,v 1.00 2007/04/28 00:00:00 alanmi Exp $]
Revision [$Id: cnfData.c,v 1.00 2007/04/28 00:00:00 alanmi Exp $]
***********************************************************************/
#include "dar.h"
#include "cnf.h"
////////////////////////////////////////////////////////////////////////
/// DECLARATIONS ///
......@@ -4531,7 +4531,7 @@ NULL
SeeAlso []
***********************************************************************/
void Dar_LibReadMsops( char ** ppSopSizes, char *** ppSops )
void Cnf_ReadMsops( char ** ppSopSizes, char *** ppSops )
{
unsigned uMasks[4][2] = {
{ 0x5555, 0xAAAA },
......@@ -4566,6 +4566,7 @@ void Dar_LibReadMsops( char ** ppSopSizes, char *** ppSops )
// set pointers and compute SOP sizes
pSopSizes = ALLOC( char, 65536 );
pSops = ALLOC( char *, 65536 );
pSopSizes[0] = 0;
pSops[0] = NULL;
pPrev = pMemory;
for ( k = 0, i = 1; i < 65536; k++ )
......
/**CFile****************************************************************
FileName [cnfMan.c]
SystemName [ABC: Logic synthesis and verification system.]
PackageName [AIG-to-CNF conversion.]
Synopsis []
Author [Alan Mishchenko]
Affiliation [UC Berkeley]
Date [Ver. 1.0. Started - April 28, 2007.]
Revision [$Id: cnfMan.c,v 1.00 2007/04/28 00:00:00 alanmi Exp $]
***********************************************************************/
#include "cnf.h"
#include "satSolver.h"
////////////////////////////////////////////////////////////////////////
/// DECLARATIONS ///
////////////////////////////////////////////////////////////////////////
static inline int Cnf_Lit2Var( int Lit ) { return (Lit & 1)? -(Lit >> 1)-1 : (Lit >> 1)+1; }
////////////////////////////////////////////////////////////////////////
/// FUNCTION DEFINITIONS ///
////////////////////////////////////////////////////////////////////////
/**Function*************************************************************
Synopsis [Starts the fraiging manager.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
Cnf_Man_t * Cnf_ManStart()
{
Cnf_Man_t * p;
int i;
// allocate the manager
p = ALLOC( Cnf_Man_t, 1 );
memset( p, 0, sizeof(Cnf_Man_t) );
// derive internal data structures
Cnf_ReadMsops( &p->pSopSizes, &p->pSops );
// allocate memory manager for cuts
p->pMemCuts = Dar_MmFlexStart();
p->nMergeLimit = 10;
// allocate temporary truth tables
p->pTruths[0] = ALLOC( unsigned, 4 * Dar_TruthWordNum(p->nMergeLimit) );
for ( i = 1; i < 4; i++ )
p->pTruths[i] = p->pTruths[i-1] + Dar_TruthWordNum(p->nMergeLimit);
p->vMemory = Vec_IntAlloc( 1 << 18 );
return p;
}
/**Function*************************************************************
Synopsis [Stops the fraiging manager.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Cnf_ManStop( Cnf_Man_t * p )
{
Vec_IntFree( p->vMemory );
free( p->pTruths[0] );
Dar_MmFlexStop( p->pMemCuts, 0 );
free( p->pSopSizes );
free( p->pSops[1] );
free( p->pSops );
free( p );
}
/**Function*************************************************************
Synopsis []
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Cnf_DataFree( Cnf_Dat_t * p )
{
if ( p == NULL )
return;
free( p->pClauses[0] );
free( p->pClauses );
free( p->pVarNums );
free( p );
}
/**Function*************************************************************
Synopsis [Writes CNF into a file.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Cnf_DataWriteIntoFile( Cnf_Dat_t * p, char * pFileName )
{
FILE * pFile;
int * pLit, * pStop, i;
pFile = fopen( pFileName, "w" );
if ( pFile == NULL )
{
printf( "Cnf_WriteIntoFile(): Output file cannot be opened.\n" );
return;
}
fprintf( pFile, "c Result of efficient AIG-to-CNF conversion using package CNF\n" );
fprintf( pFile, "p %d %d\n", p->nVars, p->nClauses );
for ( i = 0; i < p->nClauses; i++ )
{
for ( pLit = p->pClauses[i], pStop = p->pClauses[i+1]; pLit < pStop; pLit++ )
fprintf( pFile, "%d ", Cnf_Lit2Var(*pLit) );
fprintf( pFile, "0\n" );
}
fprintf( pFile, "\n" );
fclose( pFile );
}
/**Function*************************************************************
Synopsis [Writes CNF into a file.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void * Cnf_DataWriteIntoSolver( Cnf_Dat_t * p )
{
sat_solver * pSat;
int i;
pSat = sat_solver_new();
sat_solver_setnvars( pSat, p->nVars );
for ( i = 0; i < p->nClauses; i++ )
{
if ( !sat_solver_addclause( pSat, p->pClauses[i], p->pClauses[i+1] ) )
{
sat_solver_delete( pSat );
return NULL;
}
}
return pSat;
}
////////////////////////////////////////////////////////////////////////
/// END OF FILE ///
////////////////////////////////////////////////////////////////////////
/**CFile****************************************************************
FileName [cnfMap.c]
SystemName [ABC: Logic synthesis and verification system.]
PackageName [AIG-to-CNF conversion.]
Synopsis []
Author [Alan Mishchenko]
Affiliation [UC Berkeley]
Date [Ver. 1.0. Started - April 28, 2007.]
Revision [$Id: cnfMap.c,v 1.00 2007/04/28 00:00:00 alanmi Exp $]
***********************************************************************/
#include "cnf.h"
////////////////////////////////////////////////////////////////////////
/// DECLARATIONS ///
////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////
/// FUNCTION DEFINITIONS ///
////////////////////////////////////////////////////////////////////////
/**Function*************************************************************
Synopsis [Computes area of the first level.]
Description [The cut need to be derefed.]
SideEffects []
SeeAlso []
***********************************************************************/
void Dar_CutDeref( Dar_Man_t * p, Dar_Cut_t * pCut )
{
Dar_Obj_t * pLeaf;
int i;
Dar_CutForEachLeaf( p, pCut, pLeaf, i )
{
assert( pLeaf->nRefs > 0 );
if ( --pLeaf->nRefs > 0 || !Dar_ObjIsAnd(pLeaf) )
continue;
Dar_CutDeref( p, Dar_ObjBestCut(pLeaf) );
}
}
/**Function*************************************************************
Synopsis [Computes area of the first level.]
Description [The cut need to be derefed.]
SideEffects []
SeeAlso []
***********************************************************************/
int Dar_CutRef( Dar_Man_t * p, Dar_Cut_t * pCut )
{
Dar_Obj_t * pLeaf;
int i, Area = pCut->Cost;
Dar_CutForEachLeaf( p, pCut, pLeaf, i )
{
assert( pLeaf->nRefs >= 0 );
if ( pLeaf->nRefs++ > 0 || !Dar_ObjIsAnd(pLeaf) )
continue;
Area += Dar_CutRef( p, Dar_ObjBestCut(pLeaf) );
}
return Area;
}
/**Function*************************************************************
Synopsis [Computes exact area of the cut.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
int Cnf_CutArea( Dar_Man_t * p, Dar_Cut_t * pCut )
{
int Area;
Area = Dar_CutRef( p, pCut );
Dar_CutDeref( p, pCut );
return Area;
}
/**Function*************************************************************
Synopsis [Returns 1 if the second cut is better.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
static inline int Cnf_CutCompare( Dar_Cut_t * pC0, Dar_Cut_t * pC1 )
{
if ( pC0->Area < pC1->Area - 0.0001 )
return -1;
if ( pC0->Area > pC1->Area + 0.0001 ) // smaller area flow is better
return 1;
// if ( pC0->NoRefs < pC1->NoRefs )
// return -1;
// if ( pC0->NoRefs > pC1->NoRefs ) // fewer non-referenced fanins is better
// return 1;
// if ( pC0->FanRefs / pC0->nLeaves > pC1->FanRefs / pC1->nLeaves )
// return -1;
// if ( pC0->FanRefs / pC0->nLeaves < pC1->FanRefs / pC1->nLeaves )
// return 1; // larger average fanin ref-counter is better
// return 0;
return 1;
}
/**Function*************************************************************
Synopsis [Returns the cut with the smallest area flow.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
Dar_Cut_t * Cnf_ObjFindBestCut( Dar_Obj_t * pObj )
{
Dar_Cut_t * pCut, * pCutBest;
int i;
pCutBest = NULL;
Dar_ObjForEachCut( pObj, pCut, i )
if ( pCutBest == NULL || Cnf_CutCompare(pCutBest, pCut) == 1 )
pCutBest = pCut;
return pCutBest;
}
/**Function*************************************************************
Synopsis [Computes area flow of the cut.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Cnf_CutAssignAreaFlow( Cnf_Man_t * p, Dar_Cut_t * pCut )
{
Dar_Obj_t * pLeaf;
int i;
pCut->Cost = p->pSopSizes[pCut->uTruth] + p->pSopSizes[0xFFFF & ~pCut->uTruth];
pCut->Area = (float)pCut->Cost;
pCut->NoRefs = 0;
pCut->FanRefs = 0;
Dar_CutForEachLeaf( p->pManAig, pCut, pLeaf, i )
{
if ( !Dar_ObjIsNode(pLeaf) )
continue;
if ( pLeaf->nRefs == 0 )
{
pCut->Area += Dar_ObjBestCut(pLeaf)->Area;
pCut->NoRefs++;
}
else
{
pCut->Area += Dar_ObjBestCut(pLeaf)->Area / pLeaf->nRefs;
if ( pCut->FanRefs + pLeaf->nRefs > 15 )
pCut->FanRefs = 15;
else
pCut->FanRefs += pLeaf->nRefs;
}
}
}
/**Function*************************************************************
Synopsis [Computes area flow of the cut.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Cnf_CutAssignArea( Cnf_Man_t * p, Dar_Cut_t * pCut )
{
Dar_Obj_t * pLeaf;
int i;
pCut->Area = (float)pCut->Cost;
pCut->NoRefs = 0;
pCut->FanRefs = 0;
Dar_CutForEachLeaf( p->pManAig, pCut, pLeaf, i )
{
if ( !Dar_ObjIsNode(pLeaf) )
continue;
if ( pLeaf->nRefs == 0 )
{
pCut->Area += Dar_ObjBestCut(pLeaf)->Cost;
pCut->NoRefs++;
}
else
{
if ( pCut->FanRefs + pLeaf->nRefs > 15 )
pCut->FanRefs = 15;
else
pCut->FanRefs += pLeaf->nRefs;
}
}
}
/**Function*************************************************************
Synopsis [Performs one round of "area recovery" using exact local area.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
int Cnf_ManMapForCnf( Cnf_Man_t * p )
{
Dar_Obj_t * pObj;
Dar_Cut_t * pCut, * pCutBest;
int i, k;
// visit the nodes in the topological order and update their best cuts
Dar_ManForEachNode( p->pManAig, pObj, i )
{
// find the old best cut
pCutBest = Dar_ObjBestCut(pObj);
Dar_ObjClearBestCut(pCutBest);
// if the node is used, dereference its cut
if ( pObj->nRefs )
Dar_CutDeref( p->pManAig, pCutBest );
// evaluate the cuts of this node
Dar_ObjForEachCut( pObj, pCut, k )
// Cnf_CutAssignAreaFlow( p, pCut );
pCut->Area = (float)Cnf_CutArea( p->pManAig, pCut );
// find the new best cut
pCutBest = Cnf_ObjFindBestCut(pObj);
Dar_ObjSetBestCut( pCutBest );
// if the node is used, reference its cut
if ( pObj->nRefs )
Dar_CutRef( p->pManAig, pCutBest );
}
return 1;
}
////////////////////////////////////////////////////////////////////////
/// END OF FILE ///
////////////////////////////////////////////////////////////////////////
/**CFile****************************************************************
FileName [cnfPost.c]
SystemName [ABC: Logic synthesis and verification system.]
PackageName [AIG-to-CNF conversion.]
Synopsis []
Author [Alan Mishchenko]
Affiliation [UC Berkeley]
Date [Ver. 1.0. Started - April 28, 2007.]
Revision [$Id: cnfPost.c,v 1.00 2007/04/28 00:00:00 alanmi Exp $]
***********************************************************************/
#include "cnf.h"
////////////////////////////////////////////////////////////////////////
/// DECLARATIONS ///
////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////
/// FUNCTION DEFINITIONS ///
////////////////////////////////////////////////////////////////////////
/**Function*************************************************************
Synopsis []
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Cnf_ManPostprocess_old( Cnf_Man_t * p )
{
extern int Dar_ManLargeCutEval( Dar_Man_t * p, Dar_Obj_t * pRoot, Dar_Cut_t * pCutR, Dar_Cut_t * pCutL, int Leaf );
int nNew, Gain, nGain = 0, nVars = 0;
Dar_Obj_t * pObj, * pFan;
Dar_Cut_t * pCutBest, * pCut;
int i, k;//, a, b, Counter;
Dar_ManForEachObj( p->pManAig, pObj, i )
{
if ( !Dar_ObjIsNode(pObj) )
continue;
if ( pObj->nRefs == 0 )
continue;
pCutBest = Dar_ObjBestCut(pObj);
Dar_CutForEachLeaf( p->pManAig, pCutBest, pFan, k )
{
if ( !Dar_ObjIsNode(pFan) )
continue;
assert( pFan->nRefs != 0 );
if ( pFan->nRefs != 1 )
continue;
pCut = Dar_ObjBestCut(pFan);
/*
// find how many common variable they have
Counter = 0;
for ( a = 0; a < (int)pCut->nLeaves; a++ )
{
for ( b = 0; b < (int)pCutBest->nLeaves; b++ )
if ( pCut->pLeaves[a] == pCutBest->pLeaves[b] )
break;
if ( b == (int)pCutBest->nLeaves )
continue;
Counter++;
}
printf( "%d ", Counter );
*/
// find the new truth table after collapsing these two cuts
nNew = Dar_ManLargeCutEval( p->pManAig, pObj, pCutBest, pCut, pFan->Id );
// printf( "%d+%d=%d:%d(%d) ", pCutBest->Cost, pCut->Cost,
// pCutBest->Cost+pCut->Cost, nNew, pCutBest->Cost+pCut->Cost-nNew );
Gain = pCutBest->Cost+pCut->Cost-nNew;
if ( Gain > 0 )
{
nGain += Gain;
nVars++;
}
}
}
printf( "Total gain = %d. Vars = %d.\n", nGain, nVars );
}
/**Function*************************************************************
Synopsis [Transfers cuts of the mapped nodes into internal representation.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Cnf_ManTransferCuts( Cnf_Man_t * p )
{
Dar_Obj_t * pObj;
int i;
Dar_MmFlexRestart( p->pMemCuts );
Dar_ManForEachObj( p->pManAig, pObj, i )
{
if ( Dar_ObjIsNode(pObj) && pObj->nRefs > 0 )
pObj->pData = Cnf_CutCreate( p, pObj );
else
pObj->pData = NULL;
}
}
/**Function*************************************************************
Synopsis [Transfers cuts of the mapped nodes into internal representation.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Cnf_ManFreeCuts( Cnf_Man_t * p )
{
Dar_Obj_t * pObj;
int i;
Dar_ManForEachObj( p->pManAig, pObj, i )
if ( pObj->pData )
{
Cnf_CutFree( pObj->pData );
pObj->pData = NULL;
}
}
/**Function*************************************************************
Synopsis []
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Cnf_ManPostprocess( Cnf_Man_t * p )
{
Cnf_Cut_t * pCut, * pCutFan, * pCutRes;
Dar_Obj_t * pObj, * pFan;
int Order[16], Costs[16];
int i, k, fChanges;
Dar_ManForEachNode( p->pManAig, pObj, i )
{
if ( pObj->nRefs == 0 )
continue;
pCut = Cnf_ObjBestCut(pObj);
// sort fanins according to their size
Cnf_CutForEachLeaf( p->pManAig, pCut, pFan, k )
{
Order[k] = k;
Costs[k] = Dar_ObjIsNode(pFan)? Cnf_ObjBestCut(pFan)->Cost : 0;
}
// sort the cuts by Weight
do {
int Temp;
fChanges = 0;
for ( k = 0; k < pCut->nFanins - 1; k++ )
{
if ( Costs[Order[k]] <= Costs[Order[k+1]] )
continue;
Temp = Order[k];
Order[k] = Order[k+1];
Order[k+1] = Temp;
fChanges = 1;
}
} while ( fChanges );
// Cnf_CutForEachLeaf( p->pManAig, pCut, pFan, k )
for ( k = 0; (k < (int)(pCut)->nFanins) && ((pFan) = Dar_ManObj(p->pManAig, (pCut)->pFanins[Order[k]])); k++ )
{
if ( !Dar_ObjIsNode(pFan) )
continue;
assert( pFan->nRefs != 0 );
if ( pFan->nRefs != 1 )
continue;
pCutFan = Cnf_ObjBestCut(pFan);
// try composing these two cuts
// Cnf_CutPrint( pCut );
pCutRes = Cnf_CutCompose( p, pCut, pCutFan, pFan->Id );
// Cnf_CutPrint( pCut );
// printf( "\n" );
// check if the cost if reduced
if ( pCutRes == NULL || pCutRes->Cost == 127 || pCutRes->Cost > pCut->Cost + pCutFan->Cost )
{
if ( pCutRes )
Cnf_CutFree( pCutRes );
continue;
}
// update the cut
Cnf_ObjSetBestCut( pObj, pCutRes );
Cnf_ObjSetBestCut( pFan, NULL );
Cnf_CutUpdateRefs( p, pCut, pCutFan, pCutRes );
assert( pFan->nRefs == 0 );
Cnf_CutFree( pCut );
Cnf_CutFree( pCutFan );
break;
}
}
}
////////////////////////////////////////////////////////////////////////
/// END OF FILE ///
////////////////////////////////////////////////////////////////////////
/**CFile****************************************************************
FileName [cnfUtil.c]
SystemName [ABC: Logic synthesis and verification system.]
PackageName [AIG-to-CNF conversion.]
Synopsis []
Author [Alan Mishchenko]
Affiliation [UC Berkeley]
Date [Ver. 1.0. Started - April 28, 2007.]
Revision [$Id: cnfUtil.c,v 1.00 2007/04/28 00:00:00 alanmi Exp $]
***********************************************************************/
#include "cnf.h"
////////////////////////////////////////////////////////////////////////
/// DECLARATIONS ///
////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////
/// FUNCTION DEFINITIONS ///
////////////////////////////////////////////////////////////////////////
/**Function*************************************************************
Synopsis [Computes area, references, and nodes used in the mapping.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
int Dar_ManScanMapping_rec( Cnf_Man_t * p, Dar_Obj_t * pObj, Vec_Ptr_t * vMapped )
{
Dar_Obj_t * pLeaf;
Dar_Cut_t * pCutBest;
int aArea, i;
if ( pObj->nRefs++ || Dar_ObjIsPi(pObj) || Dar_ObjIsConst1(pObj) )
return 0;
assert( Dar_ObjIsAnd(pObj) );
// collect the node first to derive pre-order
if ( vMapped )
Vec_PtrPush( vMapped, pObj );
// visit the transitive fanin of the selected cut
pCutBest = Dar_ObjBestCut(pObj);
aArea = pCutBest->Cost;
Dar_CutForEachLeaf( p->pManAig, pCutBest, pLeaf, i )
aArea += Dar_ManScanMapping_rec( p, pLeaf, vMapped );
return aArea;
}
/**Function*************************************************************
Synopsis [Computes area, references, and nodes used in the mapping.]
Description [Collects the nodes in reverse topological order.]
SideEffects []
SeeAlso []
***********************************************************************/
Vec_Ptr_t * Dar_ManScanMapping( Cnf_Man_t * p, int fCollect )
{
Vec_Ptr_t * vMapped = NULL;
Dar_Obj_t * pObj;
int i;
// clean all references
Dar_ManForEachObj( p->pManAig, pObj, i )
pObj->nRefs = 0;
// allocate the array
if ( fCollect )
vMapped = Vec_PtrAlloc( 1000 );
// collect nodes reachable from POs in the DFS order through the best cuts
p->aArea = 0;
Dar_ManForEachPo( p->pManAig, pObj, i )
p->aArea += Dar_ManScanMapping_rec( p, Dar_ObjFanin0(pObj), vMapped );
printf( "Variables = %6d. Clauses = %8d.\n", vMapped? Vec_PtrSize(vMapped) : 0, p->aArea );
return vMapped;
}
/**Function*************************************************************
Synopsis [Computes area, references, and nodes used in the mapping.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
int Cnf_ManScanMapping_rec( Cnf_Man_t * p, Dar_Obj_t * pObj, Vec_Ptr_t * vMapped )
{
Dar_Obj_t * pLeaf;
Cnf_Cut_t * pCutBest;
int aArea, i;
if ( pObj->nRefs++ || Dar_ObjIsPi(pObj) || Dar_ObjIsConst1(pObj) )
return 0;
assert( Dar_ObjIsAnd(pObj) );
assert( pObj->pData != NULL );
// visit the transitive fanin of the selected cut
pCutBest = pObj->pData;
assert( pCutBest->Cost < 127 );
aArea = pCutBest->Cost;
Cnf_CutForEachLeaf( p->pManAig, pCutBest, pLeaf, i )
aArea += Cnf_ManScanMapping_rec( p, pLeaf, vMapped );
// collect the node first to derive pre-order
if ( vMapped )
Vec_PtrPush( vMapped, pObj );
return aArea;
}
/**Function*************************************************************
Synopsis [Computes area, references, and nodes used in the mapping.]
Description [Collects the nodes in reverse topological order.]
SideEffects []
SeeAlso []
***********************************************************************/
Vec_Ptr_t * Cnf_ManScanMapping( Cnf_Man_t * p, int fCollect )
{
Vec_Ptr_t * vMapped = NULL;
Dar_Obj_t * pObj;
int i;
// clean all references
Dar_ManForEachObj( p->pManAig, pObj, i )
pObj->nRefs = 0;
// allocate the array
if ( fCollect )
vMapped = Vec_PtrAlloc( 1000 );
// collect nodes reachable from POs in the DFS order through the best cuts
p->aArea = 0;
Dar_ManForEachPo( p->pManAig, pObj, i )
p->aArea += Cnf_ManScanMapping_rec( p, Dar_ObjFanin0(pObj), vMapped );
printf( "Variables = %6d. Clauses = %8d.\n", vMapped? Vec_PtrSize(vMapped) : 0, p->aArea );
return vMapped;
}
////////////////////////////////////////////////////////////////////////
/// END OF FILE ///
////////////////////////////////////////////////////////////////////////
/**CFile****************************************************************
FileName [cnf_.c]
SystemName [ABC: Logic synthesis and verification system.]
PackageName [AIG-to-CNF conversion.]
Synopsis []
Author [Alan Mishchenko]
Affiliation [UC Berkeley]
Date [Ver. 1.0. Started - April 28, 2007.]
Revision [$Id: cnf_.c,v 1.00 2007/04/28 00:00:00 alanmi Exp $]
***********************************************************************/
#include "cnf.h"
////////////////////////////////////////////////////////////////////////
/// DECLARATIONS ///
////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////
/// FUNCTION DEFINITIONS ///
////////////////////////////////////////////////////////////////////////
/**Function*************************************************************
Synopsis []
Description []
SideEffects []
SeeAlso []
***********************************************************************/
////////////////////////////////////////////////////////////////////////
/// END OF FILE ///
////////////////////////////////////////////////////////////////////////
SRC += src/aig/cnf/cnfCore.c \
src/aig/cnf/cnfCut.c \
src/aig/cnf/cnfData.c \
src/aig/cnf/cnfMan.c \
src/aig/cnf/cnfMap.c \
src/aig/cnf/cnfPost.c \
src/aig/cnf/cnfUtil.c \
src/aig/cnf/cnfWrite.c
......@@ -84,10 +84,11 @@ struct Dar_Cut_t_ // 8 words
{
unsigned uSign;
unsigned uTruth : 16; // the truth table of the cut function
unsigned Cost : 6; // the cost of the cut in terms of CNF clauses
unsigned Cost : 5; // the cost of the cut in terms of CNF clauses
unsigned FanRefs : 4; // the average number of fanin references
unsigned NoRefs : 3; // the average number of fanin references
unsigned nLeaves : 3; // the number of leaves
unsigned fBest : 1; // marks the best cut
int pLeaves[4]; // the array of leaves
// unsigned char pIndices[4];
float Area; // the area flow or exact area of the cut
......@@ -139,6 +140,7 @@ struct Dar_Man_t_
int nNodesInit; // the original number of nodes
Vec_Ptr_t * vLeavesBest; // the best set of leaves
int OutBest; // the best output (in the library)
int OutNumBest; // the best number of the output
int GainBest; // the best gain
int LevelBest; // the level of node with the best gain
int ClassBest; // the equivalence class of the best replacement
......@@ -146,6 +148,7 @@ struct Dar_Man_t_
int ClassTimes[222];// the runtimes for each class
int ClassGains[222];// the gains for each class
int ClassSubgs[222];// the graphs for each class
int nCutMemUsed; // memory used for cuts
// various data members
Dar_MmFixed_t * pMemObjs; // memory manager for objects
Dar_MmFlex_t * pMemCuts; // memory manager for cuts
......@@ -155,9 +158,7 @@ struct Dar_Man_t_
int nTravIds; // the current traversal ID
int fCatchExor; // enables EXOR nodes
// CNF mapping
char * pSopSizes; // sizes of SOPs for 4-variable functions
char ** pSops; // the SOPs for 4-variable functions
int aArea; // the area of the mapping
void * pManCnf; // CNF conversion manager
// rewriting statistics
int nCutsBad;
int nCutsGood;
......@@ -274,8 +275,16 @@ static inline int Dar_ObjFanoutC( Dar_Obj_t * pObj, Dar_Obj_t * pFanout
if ( Dar_ObjFanin1(pFanout) == pObj ) return Dar_ObjFaninC1(pObj);
assert(0); return -1;
}
static inline Dar_Cut_t * Dar_ObjBestCut( Dar_Obj_t * pObj ) { return (Dar_Cut_t *)pObj->pNext; }
static inline void Dar_ObjSetBestCut( Dar_Obj_t * pObj, Dar_Cut_t * pCut ) { pObj->pNext = (Dar_Obj_t *)pCut; }
static inline Dar_Cut_t * Dar_ObjBestCut( Dar_Obj_t * pObj )
{
Dar_Cut_t * pCut; int i;
for ( pCut = pObj->pData, i = 0; i < (int)pObj->nCuts; i++, pCut++ )
if ( pCut->fBest )
return pCut;
return NULL;
}
static inline void Dar_ObjSetBestCut( Dar_Cut_t * pCut ) { assert( !pCut->fBest ); pCut->fBest = 1; }
static inline void Dar_ObjClearBestCut( Dar_Cut_t * pCut ) { assert( pCut->fBest ); pCut->fBest = 0; }
// create the ghost of the new node
static inline Dar_Obj_t * Dar_ObjCreateGhost( Dar_Man_t * p, Dar_Obj_t * p0, Dar_Obj_t * p1, Dar_Type_t Type )
......@@ -333,6 +342,9 @@ static inline void Dar_ManRecycleMemory( Dar_Man_t * p, Dar_Obj_t * pEntry )
// iterator over all objects, including those currently not used
#define Dar_ManForEachObj( p, pObj, i ) \
Vec_PtrForEachEntry( p->vObjs, pObj, i ) if ( (pObj) == NULL ) {} else
// iterator over all nodes
#define Dar_ManForEachNode( p, pObj, i ) \
Vec_PtrForEachEntry( p->vObjs, pObj, i ) if ( (pObj) == NULL || !Dar_ObjIsNode(pObj) ) {} else
// iterator over all cuts of the node
#define Dar_ObjForEachCut( pObj, pCut, i ) \
for ( pCut = pObj->pData, i = 0; i < (int)pObj->nCuts; i++, pCut++ ) if ( i==0 ) {} else
......@@ -383,6 +395,7 @@ extern void Dar_LibEval( Dar_Man_t * p, Dar_Obj_t * pRoot, Dar_Cut_t
extern Dar_Obj_t * Dar_LibBuildBest( Dar_Man_t * p );
/*=== darMan.c ==========================================================*/
extern Dar_Man_t * Dar_ManStart();
extern Dar_Man_t * Dar_ManStartFrom( Dar_Man_t * p );
extern Dar_Man_t * Dar_ManDup( Dar_Man_t * p );
extern void Dar_ManStop( Dar_Man_t * p );
extern int Dar_ManCleanup( Dar_Man_t * p );
......
......@@ -106,11 +106,15 @@ p->timeCuts += clock() - clk;
// count gains of this class
p->ClassGains[p->ClassBest] += nNodeBefore - nNodeAfter;
// if ( p->ClassBest == 29 )
// printf( "%d ", p->OutNumBest );
}
p->timeTotal = clock() - clkStart;
p->timeOther = p->timeTotal - p->timeCuts - p->timeEval;
Extra_ProgressBarStop( pProgress );
p->nCutMemUsed = Dar_MmFlexReadMemUsage(p->pMemCuts)/(1<<20);
Dar_ManCutsFree( p );
// put the nodes into the DFS order and reassign their IDs
// Dar_NtkReassignIds( p );
......@@ -161,7 +165,6 @@ int Dar_ManComputeCuts( Dar_Man_t * p )
Dar_ManNodeNum(p), nCutsTotal, nCutsMax, (float)nCutsTotal/Dar_ManNodeNum(p),
p->nCutsFiltered, p->nCutsFiltered+nCutsTotal+Dar_ManNodeNum(p)+Dar_ManPiNum(p) );
PRT( "Time", clock() - clkStart );
// free the cuts
// Dar_ManCutsFree( p );
return 1;
......
......@@ -65,7 +65,7 @@ static inline int Dar_CutCheckDominance( Dar_Cut_t * pDom, Dar_Cut_t * pCut )
SeeAlso []
***********************************************************************/
int Dar_CutFilter( Dar_Man_t * p, Dar_Cut_t * pCut )
static inline int Dar_CutFilter( Dar_Man_t * p, Dar_Cut_t * pCut )
{
Dar_Cut_t * pTemp;
int i, k;
......@@ -213,7 +213,7 @@ static inline int Dar_CutMergeOrdered( Dar_Cut_t * pC, Dar_Cut_t * pC0, Dar_Cut_
SeeAlso []
***********************************************************************/
int Dar_CutMerge( Dar_Cut_t * pCut, Dar_Cut_t * pCut0, Dar_Cut_t * pCut1 )
static inline int Dar_CutMerge( Dar_Cut_t * pCut, Dar_Cut_t * pCut0, Dar_Cut_t * pCut1 )
{
// merge the nodes
if ( pCut0->nLeaves <= pCut1->nLeaves )
......@@ -347,7 +347,7 @@ static inline unsigned Dar_CutTruthShrink( unsigned uTruth, int nVars, unsigned
SeeAlso []
***********************************************************************/
unsigned Dar_CutTruth( Dar_Cut_t * pCut, Dar_Cut_t * pCut0, Dar_Cut_t * pCut1, int fCompl0, int fCompl1 )
static inline unsigned Dar_CutTruth( Dar_Cut_t * pCut, Dar_Cut_t * pCut0, Dar_Cut_t * pCut1, int fCompl0, int fCompl1 )
{
unsigned uTruth0 = fCompl0 ? ~pCut0->uTruth : pCut0->uTruth;
unsigned uTruth1 = fCompl1 ? ~pCut1->uTruth : pCut1->uTruth;
......@@ -367,7 +367,7 @@ unsigned Dar_CutTruth( Dar_Cut_t * pCut, Dar_Cut_t * pCut0, Dar_Cut_t * pCut1, i
SeeAlso []
***********************************************************************/
int Dar_CutSuppMinimize( Dar_Cut_t * pCut )
static inline int Dar_CutSuppMinimize( Dar_Cut_t * pCut )
{
unsigned uMasks[4][2] = {
{ 0x5555, 0xAAAA },
......@@ -420,7 +420,7 @@ void Dar_ObjSetupTrivial( Dar_Obj_t * pObj )
{
Dar_Cut_t * pCut;
pCut = pObj->pData;
pCut->Cost = 0;
memset( pCut, 0, sizeof(Dar_Cut_t) );
pCut->nLeaves = 1;
pCut->pLeaves[0] = pObj->Id;
// pCut->pIndices[0] = 0;
......@@ -464,10 +464,7 @@ void Dar_ManSetupPis( Dar_Man_t * p )
***********************************************************************/
void Dar_ManCutsFree( Dar_Man_t * p )
{
Dar_Obj_t * pObj;
int i;
Dar_ManForEachObj( p, pObj, i )
pObj->pData = NULL;
// Dar_ManCleanData( p );
Dar_MmFlexStop( p->pMemCuts, 0 );
p->pMemCuts = NULL;
}
......@@ -519,11 +516,11 @@ Dar_Cut_t * Dar_ObjComputeCuts( Dar_Man_t * p, Dar_Obj_t * pObj )
continue;
}
// CNF mapping: assign the cut cost if needed
if ( p->pSopSizes )
// CNF mapping: assign the cut cost
if ( p->pManCnf )
{
pCut->Cost = p->pSopSizes[pCut->uTruth] + p->pSopSizes[0xFFFF & ~pCut->uTruth];
Dar_CutAssignAreaFlow( p, pCut );
extern void Cnf_CutAssignAreaFlow( void * pManCnf, Dar_Cut_t * pCut );
Cnf_CutAssignAreaFlow( p->pManCnf, pCut );
}
// increment the number of cuts
......@@ -538,9 +535,12 @@ Dar_Cut_t * Dar_ObjComputeCuts( Dar_Man_t * p, Dar_Obj_t * pObj )
for ( i = 0; i < p->nCutsUsed; i++ )
*++pCut = *(p->pBaseCuts[i]);
// CNF mapping: assign the best cut if needed
if ( p->pSopSizes )
Dar_ObjSetBestCut( pObj, Dar_ObjFindBestCut(pObj) );
// CNF mapping: assign the best cut
if ( p->pManCnf )
{
extern Dar_Cut_t * Cnf_ObjFindBestCut( Dar_Obj_t * pObj );
Dar_ObjSetBestCut( Cnf_ObjFindBestCut(pObj) );
}
return pObj->pData;
}
......
......@@ -273,6 +273,7 @@ void Dar_LibSetup( Dar_Lib_t * p, Vec_Int_t * vOuts )
for ( k = 0; k < p->nSubgr[i]; k++ )
Dar_LibSetup_rec( p, Dar_LibObj(p, p->pSubgr[i][k]), i );
nNodesTotal += p->nNodes[i];
//printf( "Class %3d : Subgraphs = %4d. Nodes = %5d.\n", i, p->nSubgr[i], p->nNodes[i] );
}
assert( nNodesTotal == p->pNodesTotal );
// prepare the number of the PI nodes
......@@ -604,6 +605,8 @@ void Dar_LibEval( Dar_Man_t * p, Dar_Obj_t * pRoot, Dar_Cut_t * pCut, int Requir
int i, k, Class, nNodesSaved, nNodesAdded, nNodesGained, clk;
if ( pCut->nLeaves != 4 )
return;
// if ( s_DarLib->nSubgr[ s_DarLib->pMap[pCut->uTruth] ] > 100 )
// return;
clk = clock();
/*
for ( k = 0; k < 4; k++ )
......@@ -643,10 +646,11 @@ void Dar_LibEval( Dar_Man_t * p, Dar_Obj_t * pRoot, Dar_Cut_t * pCut, int Requir
Vec_PtrClear( p->vLeavesBest );
for ( k = 0; k < 4; k++ )
Vec_PtrPush( p->vLeavesBest, s_DarLib->pDatas[k].pFunc );
p->OutBest = s_DarLib->pSubgr[Class][i];
p->LevelBest = s_DarLib->pDatas[pObj->Num].Level;
p->GainBest = nNodesGained;
p->ClassBest = Class;
p->OutBest = s_DarLib->pSubgr[Class][i];
p->OutNumBest = i;
p->LevelBest = s_DarLib->pDatas[pObj->Num].Level;
p->GainBest = nNodesGained;
p->ClassBest = Class;
}
clk = clock() - clk;
p->ClassTimes[Class] += clk;
......
......@@ -79,6 +79,68 @@ Dar_Man_t * Dar_ManStart( int nNodesMax )
/**Function*************************************************************
Synopsis [Duplicates the AIG manager.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
Dar_Man_t * Dar_ManStartFrom( Dar_Man_t * p )
{
Dar_Man_t * pNew;
Dar_Obj_t * pObj;
int i;
// create the new manager
pNew = Dar_ManStart();
// create the PIs
Dar_ManConst1(p)->pData = Dar_ManConst1(pNew);
Dar_ManForEachPi( p, pObj, i )
pObj->pData = Dar_ObjCreatePi(pNew);
return pNew;
}
/**Function*************************************************************
Synopsis [Duplicates the AIG manager.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
Dar_Man_t * Dar_ManDup( Dar_Man_t * p )
{
Dar_Man_t * pNew;
Dar_Obj_t * pObj;
int i;
// create the new manager
pNew = Dar_ManStart();
// create the PIs
Dar_ManConst1(p)->pData = Dar_ManConst1(pNew);
Dar_ManForEachPi( p, pObj, i )
pObj->pData = Dar_ObjCreatePi(pNew);
// duplicate internal nodes
Dar_ManForEachObj( p, pObj, i )
if ( Dar_ObjIsBuf(pObj) )
pObj->pData = Dar_ObjChild0Copy(pObj);
else if ( Dar_ObjIsNode(pObj) )
pObj->pData = Dar_And( pNew, Dar_ObjChild0Copy(pObj), Dar_ObjChild1Copy(pObj) );
// add the POs
Dar_ManForEachPo( p, pObj, i )
Dar_ObjCreatePo( pNew, Dar_ObjChild0Copy(pObj) );
// check the resulting network
if ( !Dar_ManCheck(pNew) )
printf( "Dar_ManDup(): The check has failed.\n" );
return pNew;
}
/**Function*************************************************************
Synopsis [Stops the AIG manager.]
Description []
......@@ -107,13 +169,6 @@ void Dar_ManStop( Dar_Man_t * p )
if ( p->vRequired ) Vec_IntFree( p->vRequired );
if ( p->vLeavesBest ) Vec_PtrFree( p->vLeavesBest );
free( p->pTable );
// free CNF mapping data
if ( p->pSopSizes )
{
free( p->pSopSizes );
free( p->pSops[1] );
free( p->pSops );
}
free( p );
}
......@@ -185,7 +240,8 @@ void Dar_ManPrintStats( Dar_Man_t * p )
void Dar_ManPrintRuntime( Dar_Man_t * p )
{
int i, Gain;
printf( "Good cuts = %d. Bad cuts = %d.\n", p->nCutsGood, p->nCutsBad );
printf( "Good cuts = %d. Bad cuts = %d. Cut mem = %d Mb\n",
p->nCutsGood, p->nCutsBad, p->nCutMemUsed );
PRT( "Cuts ", p->timeCuts );
PRT( "Eval ", p->timeEval );
PRT( "Other ", p->timeOther );
......
/**CFile****************************************************************
FileName [fraAnd.c]
SystemName [ABC: Logic synthesis and verification system.]
PackageName [Fraig FRAIG package.]
Synopsis []
Author [Alan Mishchenko]
Affiliation [UC Berkeley]
Date [Ver. 1.0. Started - June 30, 2007.]
Revision [$Id: fraAnd.c,v 1.00 2007/06/30 00:00:00 alanmi Exp $]
***********************************************************************/
#include "fra.h"
////////////////////////////////////////////////////////////////////////
/// DECLARATIONS ///
////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////
/// FUNCTION DEFINITIONS ///
////////////////////////////////////////////////////////////////////////
/**Function*************************************************************
Synopsis [Performs fraiging for one node.]
Description [Returns the fraiged node.]
SideEffects []
SeeAlso []
***********************************************************************/
Dar_Obj_t * Fra_And( Fra_Man_t * p, Dar_Obj_t * pObjOld )
{
Dar_Obj_t * pObjOldRepr, * pObjFraig, * pFanin0Fraig, * pFanin1Fraig, * pObjOldReprFraig;
int RetValue;
assert( !Dar_IsComplement(pObjOld) );
assert( Dar_ObjIsNode(pObjOld) );
// get the fraiged fanins
pFanin0Fraig = Fra_ObjChild0Fra(pObjOld);
pFanin1Fraig = Fra_ObjChild1Fra(pObjOld);
// get the fraiged node
pObjFraig = Dar_And( p->pManFraig, pFanin0Fraig, pFanin1Fraig );
// get representative of this class
pObjOldRepr = Fra_ObjRepr(pObjOld);
if ( pObjOldRepr == NULL || // this is a unique node
(!p->pPars->fDoSparse && pObjOldRepr == Dar_ManConst1(p->pManAig)) ) // this is a sparse node
{
assert( Dar_Regular(pFanin0Fraig) != Dar_Regular(pFanin1Fraig) );
assert( pObjFraig != Dar_Regular(pFanin0Fraig) );
assert( pObjFraig != Dar_Regular(pFanin1Fraig) );
return pObjFraig;
}
// get the fraiged representative
pObjOldReprFraig = Fra_ObjFraig(pObjOldRepr);
// if the fraiged nodes are the same, return
if ( Dar_Regular(pObjFraig) == Dar_Regular(pObjOldReprFraig) )
return pObjFraig;
assert( Dar_Regular(pObjFraig) != Dar_ManConst1(p->pManFraig) );
// if they are proved different, the c-ex will be in p->pPatWords
RetValue = Fra_NodesAreEquiv( p, Dar_Regular(pObjOldReprFraig), Dar_Regular(pObjFraig) );
if ( RetValue == 1 ) // proved equivalent
{
pObjOld->fMarkA = 1;
return Dar_NotCond( pObjOldReprFraig, pObjOld->fPhase ^ pObjOldRepr->fPhase );
}
if ( RetValue == -1 ) // failed
{
if ( !p->pPars->fSpeculate )
return pObjFraig;
// substitute the node
pObjOld->fMarkB = 1;
return Dar_NotCond( pObjOldReprFraig, pObjOld->fPhase ^ pObjOldRepr->fPhase );
}
// simulate the counter-example and return the Fraig node
Fra_Resimulate( p );
return pObjFraig;
}
/**Function*************************************************************
Synopsis [Performs fraiging for the internal nodes.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Fra_Sweep( Fra_Man_t * p )
{
Dar_Obj_t * pObj, * pObjNew;
int i, k = 0;
p->nClassesZero = Vec_PtrSize(p->vClasses1);
p->nClassesBeg = Vec_PtrSize(p->vClasses);
// duplicate internal nodes
// p->pProgress = Extra_ProgressBarStart( stdout, Dar_ManNodeNum(p->pManAig) );
Dar_ManForEachNode( p->pManAig, pObj, i )
{
// Extra_ProgressBarUpdate( p->pProgress, k++, NULL );
// default to simple strashing if simulation detected a counter-example for a PO
if ( p->pManFraig->pData )
pObjNew = Dar_And( p->pManFraig, Fra_ObjChild0Fra(pObj), Fra_ObjChild1Fra(pObj) );
else
pObjNew = Fra_And( p, pObj ); // pObjNew can be complemented
assert( Fra_ObjFraig(pObj) != NULL );
Fra_ObjSetFraig( pObj, pObjNew );
}
// Extra_ProgressBarStop( p->pProgress );
p->nClassesEnd = Vec_PtrSize(p->vClasses);
// try to prove the outputs of the miter
p->nNodesMiter = Dar_ManNodeNum(p->pManFraig);
// Fra_MiterStatus( p->pManFraig );
// if ( p->pPars->fProve && p->pManFraig->pData == NULL )
// Fra_MiterProve( p );
// add the POs
Dar_ManForEachPo( p->pManAig, pObj, i )
Dar_ObjCreatePo( p->pManFraig, Fra_ObjChild0Fra(pObj) );
// remove dangling nodes
Dar_ManCleanup( p->pManFraig );
}
////////////////////////////////////////////////////////////////////////
/// END OF FILE ///
////////////////////////////////////////////////////////////////////////
/**CFile****************************************************************
FileName [fraCnf.c]
SystemName [ABC: Logic synthesis and verification system.]
PackageName [New FRAIG package.]
Synopsis []
Author [Alan Mishchenko]
Affiliation [UC Berkeley]
Date [Ver. 1.0. Started - June 30, 2007.]
Revision [$Id: fraCnf.c,v 1.00 2007/06/30 00:00:00 alanmi Exp $]
***********************************************************************/
#include "fra.h"
////////////////////////////////////////////////////////////////////////
/// DECLARATIONS ///
////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////
/// FUNCTION DEFINITIONS ///
////////////////////////////////////////////////////////////////////////
/**Function*************************************************************
Synopsis [Addes clauses to the solver.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Fra_AddClausesMux( Fra_Man_t * p, Dar_Obj_t * pNode )
{
Dar_Obj_t * pNodeI, * pNodeT, * pNodeE;
int pLits[4], RetValue, VarF, VarI, VarT, VarE, fCompT, fCompE;
assert( !Dar_IsComplement( pNode ) );
assert( Dar_ObjIsMuxType( pNode ) );
// get nodes (I = if, T = then, E = else)
pNodeI = Dar_ObjRecognizeMux( pNode, &pNodeT, &pNodeE );
// get the variable numbers
VarF = Fra_ObjSatNum(pNode);
VarI = Fra_ObjSatNum(pNodeI);
VarT = Fra_ObjSatNum(Dar_Regular(pNodeT));
VarE = Fra_ObjSatNum(Dar_Regular(pNodeE));
// get the complementation flags
fCompT = Dar_IsComplement(pNodeT);
fCompE = Dar_IsComplement(pNodeE);
// f = ITE(i, t, e)
// i' + t' + f
// i' + t + f'
// i + e' + f
// i + e + f'
// create four clauses
pLits[0] = toLitCond(VarI, 1);
pLits[1] = toLitCond(VarT, 1^fCompT);
pLits[2] = toLitCond(VarF, 0);
RetValue = sat_solver_addclause( p->pSat, pLits, pLits + 3 );
assert( RetValue );
pLits[0] = toLitCond(VarI, 1);
pLits[1] = toLitCond(VarT, 0^fCompT);
pLits[2] = toLitCond(VarF, 1);
RetValue = sat_solver_addclause( p->pSat, pLits, pLits + 3 );
assert( RetValue );
pLits[0] = toLitCond(VarI, 0);
pLits[1] = toLitCond(VarE, 1^fCompE);
pLits[2] = toLitCond(VarF, 0);
RetValue = sat_solver_addclause( p->pSat, pLits, pLits + 3 );
assert( RetValue );
pLits[0] = toLitCond(VarI, 0);
pLits[1] = toLitCond(VarE, 0^fCompE);
pLits[2] = toLitCond(VarF, 1);
RetValue = sat_solver_addclause( p->pSat, pLits, pLits + 3 );
assert( RetValue );
// two additional clauses
// t' & e' -> f'
// t & e -> f
// t + e + f'
// t' + e' + f
if ( VarT == VarE )
{
// assert( fCompT == !fCompE );
return;
}
pLits[0] = toLitCond(VarT, 0^fCompT);
pLits[1] = toLitCond(VarE, 0^fCompE);
pLits[2] = toLitCond(VarF, 1);
RetValue = sat_solver_addclause( p->pSat, pLits, pLits + 3 );
assert( RetValue );
pLits[0] = toLitCond(VarT, 1^fCompT);
pLits[1] = toLitCond(VarE, 1^fCompE);
pLits[2] = toLitCond(VarF, 0);
RetValue = sat_solver_addclause( p->pSat, pLits, pLits + 3 );
assert( RetValue );
}
/**Function*************************************************************
Synopsis [Addes clauses to the solver.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Fra_AddClausesSuper( Fra_Man_t * p, Dar_Obj_t * pNode, Vec_Ptr_t * vSuper )
{
Dar_Obj_t * pFanin;
int * pLits, nLits, RetValue, i;
assert( !Dar_IsComplement(pNode) );
assert( Dar_ObjIsNode( pNode ) );
// create storage for literals
nLits = Vec_PtrSize(vSuper) + 1;
pLits = ALLOC( int, nLits );
// suppose AND-gate is A & B = C
// add !A => !C or A + !C
Vec_PtrForEachEntry( vSuper, pFanin, i )
{
pLits[0] = toLitCond(Fra_ObjSatNum(Dar_Regular(pFanin)), Dar_IsComplement(pFanin));
pLits[1] = toLitCond(Fra_ObjSatNum(pNode), 1);
RetValue = sat_solver_addclause( p->pSat, pLits, pLits + 2 );
assert( RetValue );
}
// add A & B => C or !A + !B + C
Vec_PtrForEachEntry( vSuper, pFanin, i )
pLits[i] = toLitCond(Fra_ObjSatNum(Dar_Regular(pFanin)), !Dar_IsComplement(pFanin));
pLits[nLits-1] = toLitCond(Fra_ObjSatNum(pNode), 0);
RetValue = sat_solver_addclause( p->pSat, pLits, pLits + nLits );
assert( RetValue );
free( pLits );
}
/**Function*************************************************************
Synopsis [Collects the supergate.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Fra_CollectSuper_rec( Dar_Obj_t * pObj, Vec_Ptr_t * vSuper, int fFirst, int fUseMuxes )
{
// if the new node is complemented or a PI, another gate begins
if ( Dar_IsComplement(pObj) || Dar_ObjIsPi(pObj) || (!fFirst && Dar_ObjRefs(pObj) > 1) ||
(fUseMuxes && Dar_ObjIsMuxType(pObj)) )
{
Vec_PtrPushUnique( vSuper, pObj );
return;
}
// go through the branches
Fra_CollectSuper_rec( Dar_ObjChild0(pObj), vSuper, 0, fUseMuxes );
Fra_CollectSuper_rec( Dar_ObjChild1(pObj), vSuper, 0, fUseMuxes );
}
/**Function*************************************************************
Synopsis [Collects the supergate.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
Vec_Ptr_t * Fra_CollectSuper( Dar_Obj_t * pObj, int fUseMuxes )
{
Vec_Ptr_t * vSuper;
assert( !Dar_IsComplement(pObj) );
assert( !Dar_ObjIsPi(pObj) );
vSuper = Vec_PtrAlloc( 4 );
Fra_CollectSuper_rec( pObj, vSuper, 1, fUseMuxes );
return vSuper;
}
/**Function*************************************************************
Synopsis [Updates the solver clause database.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Fra_ObjAddToFrontier( Fra_Man_t * p, Dar_Obj_t * pObj, Vec_Ptr_t * vFrontier )
{
assert( !Dar_IsComplement(pObj) );
if ( Fra_ObjSatNum(pObj) )
return;
assert( Fra_ObjSatNum(pObj) == 0 );
assert( Fra_ObjFaninVec(pObj) == NULL );
if ( Dar_ObjIsConst1(pObj) )
return;
//printf( "Assigning node %d number %d\n", pObj->Id, p->nSatVars );
Fra_ObjSetSatNum( pObj, p->nSatVars++ );
if ( Dar_ObjIsNode(pObj) )
Vec_PtrPush( vFrontier, pObj );
}
/**Function*************************************************************
Synopsis [Updates the solver clause database.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Fra_NodeAddToSolver( Fra_Man_t * p, Dar_Obj_t * pOld, Dar_Obj_t * pNew )
{
Vec_Ptr_t * vFrontier, * vFanins;
Dar_Obj_t * pNode, * pFanin;
int i, k, fUseMuxes = 1;
assert( pOld || pNew );
// quit if CNF is ready
if ( (!pOld || Fra_ObjFaninVec(pOld)) && (!pNew || Fra_ObjFaninVec(pNew)) )
return;
// start the frontier
vFrontier = Vec_PtrAlloc( 100 );
if ( pOld ) Fra_ObjAddToFrontier( p, pOld, vFrontier );
if ( pNew ) Fra_ObjAddToFrontier( p, pNew, vFrontier );
// explore nodes in the frontier
Vec_PtrForEachEntry( vFrontier, pNode, i )
{
// create the supergate
assert( Fra_ObjSatNum(pNode) );
assert( Fra_ObjFaninVec(pNode) == NULL );
if ( fUseMuxes && Dar_ObjIsMuxType(pNode) )
{
vFanins = Vec_PtrAlloc( 4 );
Vec_PtrPushUnique( vFanins, Dar_ObjFanin0( Dar_ObjFanin0(pNode) ) );
Vec_PtrPushUnique( vFanins, Dar_ObjFanin0( Dar_ObjFanin1(pNode) ) );
Vec_PtrPushUnique( vFanins, Dar_ObjFanin1( Dar_ObjFanin0(pNode) ) );
Vec_PtrPushUnique( vFanins, Dar_ObjFanin1( Dar_ObjFanin1(pNode) ) );
Vec_PtrForEachEntry( vFanins, pFanin, k )
Fra_ObjAddToFrontier( p, Dar_Regular(pFanin), vFrontier );
Fra_AddClausesMux( p, pNode );
}
else
{
vFanins = Fra_CollectSuper( pNode, fUseMuxes );
Vec_PtrForEachEntry( vFanins, pFanin, k )
Fra_ObjAddToFrontier( p, Dar_Regular(pFanin), vFrontier );
Fra_AddClausesSuper( p, pNode, vFanins );
}
assert( Vec_PtrSize(vFanins) > 1 );
Fra_ObjSetFaninVec( pNode, vFanins );
}
Vec_PtrFree( vFrontier );
}
////////////////////////////////////////////////////////////////////////
/// END OF FILE ///
////////////////////////////////////////////////////////////////////////
/**CFile****************************************************************
FileName [fraCore.c]
SystemName [ABC: Logic synthesis and verification system.]
PackageName [New FRAIG package.]
Synopsis []
Author [Alan Mishchenko]
Affiliation [UC Berkeley]
Date [Ver. 1.0. Started - June 30, 2007.]
Revision [$Id: fraCore.c,v 1.00 2007/06/30 00:00:00 alanmi Exp $]
***********************************************************************/
#include "fra.h"
////////////////////////////////////////////////////////////////////////
/// DECLARATIONS ///
////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////
/// FUNCTION DEFINITIONS ///
////////////////////////////////////////////////////////////////////////
/**Function*************************************************************
Synopsis [Performs fraiging of the AIG.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
Dar_Man_t * Fra_Perform( Dar_Man_t * pManAig, Fra_Par_t * pPars )
{
Fra_Man_t * p;
Dar_Man_t * pManAigNew;
int clk;
if ( Dar_ManNodeNum(pManAig) == 0 )
return Dar_ManDup(pManAig);
clk = clock();
assert( Dar_ManLatchNum(pManAig) == 0 );
p = Fra_ManStart( pManAig, pPars );
Fra_Simulate( p );
Fra_Sweep( p );
pManAigNew = p->pManFraig;
p->timeTotal = clock() - clk;
Fra_ManStop( p );
return pManAigNew;
}
////////////////////////////////////////////////////////////////////////
/// END OF FILE ///
////////////////////////////////////////////////////////////////////////
/**CFile****************************************************************
FileName [fraMan.c]
SystemName [ABC: Logic synthesis and verification system.]
PackageName [New FRAIG package.]
Synopsis [Starts the FRAIG manager.]
Author [Alan Mishchenko]
Affiliation [UC Berkeley]
Date [Ver. 1.0. Started - June 30, 2007.]
Revision [$Id: fraMan.c,v 1.00 2007/06/30 00:00:00 alanmi Exp $]
***********************************************************************/
#include "fra.h"
////////////////////////////////////////////////////////////////////////
/// DECLARATIONS ///
////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////
/// FUNCTION DEFINITIONS ///
////////////////////////////////////////////////////////////////////////
/**Function*************************************************************
Synopsis [Sets the default solving parameters.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Fra_ParamsDefault( Fra_Par_t * pPars )
{
memset( pPars, 0, sizeof(Fra_Par_t) );
pPars->nSimWords = 32; // the number of words in the simulation info
pPars->dSimSatur = 0.005; // the ratio of refined classes when saturation is reached
pPars->fPatScores = 0; // enables simulation pattern scoring
pPars->MaxScore = 25; // max score after which resimulation is used
pPars->fDoSparse = 1; // skips sparse functions
// pPars->dActConeRatio = 0.05; // the ratio of cone to be bumped
// pPars->dActConeBumpMax = 5.0; // the largest bump of activity
pPars->dActConeRatio = 0.3; // the ratio of cone to be bumped
pPars->dActConeBumpMax = 10.0; // the largest bump of activity
pPars->nBTLimitNode = 100; // conflict limit at a node
pPars->nBTLimitMiter = 500000; // conflict limit at an output
}
/**Function*************************************************************
Synopsis [Starts the fraiging manager.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
Fra_Man_t * Fra_ManStart( Dar_Man_t * pManAig, Fra_Par_t * pPars )
{
Fra_Man_t * p;
Dar_Obj_t * pObj;
int i;
// allocate the fraiging manager
p = ALLOC( Fra_Man_t, 1 );
memset( p, 0, sizeof(Fra_Man_t) );
p->pPars = pPars;
p->pManAig = pManAig;
p->pManFraig = Dar_ManStartFrom( pManAig );
assert( Dar_ManPiNum(p->pManAig) == Dar_ManPiNum(p->pManFraig) );
// allocate simulation info
p->nSimWords = pPars->nSimWords;
p->pSimWords = ALLOC( unsigned, (Dar_ManObjIdMax(pManAig) + 1) * p->nSimWords );
// clean simulation info of the constant node
memset( p->pSimWords, 0, p->nSimWords * sizeof(unsigned) );
// allocate storage for sim pattern
p->nPatWords = Dar_BitWordNum( Dar_ManPiNum(pManAig) );
p->pPatWords = ALLOC( unsigned, p->nPatWords );
p->pPatScores = ALLOC( int, 32 * p->nSimWords );
p->vPiVars = Vec_PtrAlloc( 100 );
p->vClasses = Vec_PtrAlloc( 100 );
// allocate other members
p->nSizeAlloc = Dar_ManObjIdMax(pManAig) + 1;
p->pMemFraig = ALLOC( Dar_Obj_t *, p->nSizeAlloc );
memset( p->pMemFraig, 0, p->nSizeAlloc * sizeof(Dar_Obj_t *) );
p->pMemRepr = ALLOC( Dar_Obj_t *, p->nSizeAlloc );
memset( p->pMemRepr, 0, p->nSizeAlloc * sizeof(Dar_Obj_t *) );
p->pMemFanins = ALLOC( Vec_Ptr_t *, p->nSizeAlloc );
memset( p->pMemFanins, 0, p->nSizeAlloc * sizeof(Vec_Ptr_t *) );
p->pMemSatNums = ALLOC( int, p->nSizeAlloc );
memset( p->pMemSatNums, 0xff, p->nSizeAlloc * sizeof(int) );
// set the pointers to the available fraig nodes
Fra_ObjSetFraig( Dar_ManConst1(p->pManAig), Dar_ManConst1(p->pManFraig) );
Dar_ManForEachPi( p->pManAig, pObj, i )
Fra_ObjSetFraig( pObj, Dar_ManPi(p->pManFraig, i) );
// set the pointers to the manager
Dar_ManForEachObj( p->pManFraig, pObj, i )
pObj->pData = p->pManFraig;
// set random number generator
srand( 0xABCABC );
return p;
}
/**Function*************************************************************
Synopsis [Stops the fraiging manager.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Fra_ManStop( Fra_Man_t * p )
{
int i;
for ( i = 0; i < p->nSizeAlloc; i++ )
if ( p->pMemFanins[i] )
Vec_PtrFree( p->pMemFanins[i] );
if ( p->pPars->fVerbose )
Fra_ManPrint( p );
if ( p->vClassesTemp ) Vec_PtrFree( p->vClassesTemp );
if ( p->vClassNew ) Vec_PtrFree( p->vClassNew );
if ( p->vClassOld ) Vec_PtrFree( p->vClassOld );
if ( p->vClasses1 ) Vec_PtrFree( p->vClasses1 );
if ( p->vClasses ) Vec_PtrFree( p->vClasses );
if ( p->vPiVars ) Vec_PtrFree( p->vPiVars );
if ( p->pSat ) sat_solver_delete( p->pSat );
FREE( p->pMemSatNums );
FREE( p->pMemFanins );
FREE( p->pMemRepr );
FREE( p->pMemFraig );
FREE( p->pMemClasses );
FREE( p->pPatScores );
FREE( p->pPatWords );
FREE( p->pSimWords );
free( p );
}
/**Function*************************************************************
Synopsis [Prints stats for the fraiging manager.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Fra_ManPrint( Fra_Man_t * p )
{
double nMemory = 1.0*Dar_ManObjIdMax(p->pManAig)*((p->nSimWords+2)*sizeof(unsigned)+6*sizeof(void*))/(1<<20);
printf( "SimWords = %d. Rounds = %d. Mem = %0.2f Mb. ", p->nSimWords, p->nSimRounds, nMemory );
printf( "Classes: Beg = %d. End = %d.\n", p->nClassesBeg, p->nClassesEnd );
printf( "Limits: BTNode = %d. BTMiter = %d.\n", p->pPars->nBTLimitNode, p->pPars->nBTLimitMiter );
printf( "Proof = %d. Counter-example = %d. Fail = %d. FailReal = %d. Zero = %d.\n",
p->nSatProof, p->nSatCallsSat, p->nSatFails, p->nSatFailsReal, p->nClassesZero );
printf( "Final = %d. Miter = %d. Total = %d. Mux = %d. (Exor = %d.) SatVars = %d.\n",
Dar_ManNodeNum(p->pManFraig), p->nNodesMiter, Dar_ManNodeNum(p->pManAig), 0, 0, p->nSatVars );
if ( p->pSat ) Sat_SolverPrintStats( stdout, p->pSat );
PRT( "AIG simulation ", p->timeSim );
PRT( "AIG traversal ", p->timeTrav );
PRT( "SAT solving ", p->timeSat );
PRT( " Unsat ", p->timeSatUnsat );
PRT( " Sat ", p->timeSatSat );
PRT( " Fail ", p->timeSatFail );
PRT( "Class refining ", p->timeRef );
PRT( "TOTAL RUNTIME ", p->timeTotal );
if ( p->time1 ) { PRT( "time1 ", p->time1 ); }
}
////////////////////////////////////////////////////////////////////////
/// END OF FILE ///
////////////////////////////////////////////////////////////////////////
/**CFile****************************************************************
FileName [fra_.c]
SystemName [ABC: Logic synthesis and verification system.]
PackageName [New FRAIG package.]
Synopsis []
Author [Alan Mishchenko]
Affiliation [UC Berkeley]
Date [Ver. 1.0. Started - June 30, 2007.]
Revision [$Id: fra_.c,v 1.00 2007/06/30 00:00:00 alanmi Exp $]
***********************************************************************/
#include "fra.h"
////////////////////////////////////////////////////////////////////////
/// DECLARATIONS ///
////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////
/// FUNCTION DEFINITIONS ///
////////////////////////////////////////////////////////////////////////
/**Function*************************************************************
Synopsis []
Description []
SideEffects []
SeeAlso []
***********************************************************************/
////////////////////////////////////////////////////////////////////////
/// END OF FILE ///
////////////////////////////////////////////////////////////////////////
SRC += src/aig/fra/fraAnd.c \
src/aig/fra/fraClass.c \
src/aig/fra/fraCnf.c \
src/aig/fra/fraCore.c \
src/aig/fra/fraMan.c \
src/aig/fra/fraSat.c \
src/aig/fra/fraSim.c
......@@ -331,7 +331,10 @@ void Abc_Init( Abc_Frame_t * pAbc )
// Kit_TruthCountMintermsPrecomp();
// Kit_DsdPrecompute4Vars();
Dar_LibStart();
{
extern void Dar_LibStart();
Dar_LibStart();
}
}
/**Function*************************************************************
......@@ -347,7 +350,10 @@ void Abc_Init( Abc_Frame_t * pAbc )
***********************************************************************/
void Abc_End()
{
Dar_LibStop();
{
extern void Dar_LibStop();
Dar_LibStop();
}
Abc_NtkFraigStoreClean();
// Rwt_Man4ExplorePrint();
......@@ -2915,7 +2921,7 @@ int Abc_CommandLutpack( Abc_Frame_t * pAbc, int argc, char ** argv )
memset( pPars, 0, sizeof(Lut_Par_t) );
pPars->nLutsMax = 4; // (N) the maximum number of LUTs in the structure
pPars->nLutsOver = 3; // (Q) the maximum number of LUTs not in the MFFC
pPars->nVarsShared = 0; // (S) the maximum number of shared variables (crossbars)
pPars->nVarsShared = 3; // (S) the maximum number of shared variables (crossbars)
pPars->nGrowthLevel = 1;
pPars->fSatur = 1;
pPars->fZeroCost = 0;
......@@ -5942,6 +5948,7 @@ int Abc_CommandTest( Abc_Frame_t * pAbc, int argc, char ** argv )
extern void Abc_NtkCompareSupports( Abc_Ntk_t * pNtk );
extern void Abc_NtkCompareCones( Abc_Ntk_t * pNtk );
extern Abc_Ntk_t * Abc_NtkDar( Abc_Ntk_t * pNtk );
extern Abc_Ntk_t * Abc_NtkDarToCnf( Abc_Ntk_t * pNtk, char * pFileName );
pNtk = Abc_FrameReadNtk(pAbc);
pOut = Abc_FrameReadOut(pAbc);
......@@ -6057,7 +6064,8 @@ int Abc_CommandTest( Abc_Frame_t * pAbc, int argc, char ** argv )
fprintf( pErr, "Network should be strashed. Command has failed.\n" );
return 1;
}
pNtkRes = Abc_NtkDar( pNtk );
// pNtkRes = Abc_NtkDar( pNtk );
pNtkRes = Abc_NtkDarToCnf( pNtk, "any.cnf" );
if ( pNtkRes == NULL )
{
fprintf( pErr, "Command has failed.\n" );
......
......@@ -20,6 +20,7 @@
#include "abc.h"
#include "dar.h"
#include "cnf.h"
////////////////////////////////////////////////////////////////////////
/// DECLARATIONS ///
......@@ -317,6 +318,130 @@ Dar_CnfFree( pCnf );
}
/**Function*************************************************************
Synopsis [Gives the current ABC network to AIG manager for processing.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
Abc_Ntk_t * Abc_NtkConstructFromCnf( Abc_Ntk_t * pNtk, Cnf_Man_t * p, Vec_Ptr_t * vMapped )
{
Abc_Ntk_t * pNtkNew;
Abc_Obj_t * pNode, * pNodeNew;
Dar_Obj_t * pObj, * pLeaf;
Cnf_Cut_t * pCut;
Vec_Int_t * vCover;
unsigned uTruth;
int i, k, nDupGates;
// create the new network
pNtkNew = Abc_NtkStartFrom( pNtk, ABC_NTK_LOGIC, ABC_FUNC_SOP );
// make the mapper point to the new network
Dar_ManConst1(p->pManAig)->pData = Abc_NtkCreateNodeConst1(pNtkNew);
Abc_NtkForEachCi( pNtk, pNode, i )
Dar_ManPi(p->pManAig, i)->pData = pNode->pCopy;
// process the nodes in topological order
vCover = Vec_IntAlloc( 1 << 16 );
Vec_PtrForEachEntry( vMapped, pObj, i )
{
// create new node
pNodeNew = Abc_NtkCreateNode( pNtkNew );
// add fanins according to the cut
pCut = pObj->pData;
Cnf_CutForEachLeaf( p->pManAig, pCut, pLeaf, k )
Abc_ObjAddFanin( pNodeNew, pLeaf->pData );
// add logic function
if ( pCut->nFanins < 5 )
{
uTruth = 0xFFFF & *Cnf_CutTruth(pCut);
Cnf_SopConvertToVector( p->pSops[uTruth], p->pSopSizes[uTruth], vCover );
pNodeNew->pData = Abc_SopCreateFromIsop( pNtkNew->pManFunc, pCut->nFanins, vCover );
}
else
pNodeNew->pData = Abc_SopCreateFromIsop( pNtkNew->pManFunc, pCut->nFanins, pCut->vIsop[1] );
// save the node
pObj->pData = pNodeNew;
}
Vec_IntFree( vCover );
// add the CO drivers
Abc_NtkForEachCo( pNtk, pNode, i )
{
pObj = Dar_ManPo(p->pManAig, i);
pNodeNew = Abc_ObjNotCond( Dar_ObjFanin0(pObj)->pData, Dar_ObjFaninC0(pObj) );
Abc_ObjAddFanin( pNode->pCopy, pNodeNew );
}
// remove the constant node if not used
pNodeNew = (Abc_Obj_t *)Dar_ManConst1(p->pManAig)->pData;
if ( Abc_ObjFanoutNum(pNodeNew) == 0 )
Abc_NtkDeleteObj( pNodeNew );
// minimize the node
// Abc_NtkSweep( pNtkNew, 0 );
// decouple the PO driver nodes to reduce the number of levels
nDupGates = Abc_NtkLogicMakeSimpleCos( pNtkNew, 1 );
// if ( nDupGates && If_ManReadVerbose(pIfMan) )
// printf( "Duplicated %d gates to decouple the CO drivers.\n", nDupGates );
if ( !Abc_NtkCheck( pNtkNew ) )
fprintf( stdout, "Abc_NtkConstructFromCnf(): Network check has failed.\n" );
return pNtkNew;
}
/**Function*************************************************************
Synopsis [Gives the current ABC network to AIG manager for processing.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
Abc_Ntk_t * Abc_NtkDarToCnf( Abc_Ntk_t * pNtk, char * pFileName )
{
Abc_Ntk_t * pNtkNew = NULL;
Cnf_Man_t * pCnf;
Dar_Man_t * pMan;
Cnf_Dat_t * pData;
assert( Abc_NtkIsStrash(pNtk) );
// convert to the AIG manager
pMan = Abc_NtkToDar( pNtk );
if ( pMan == NULL )
return NULL;
if ( !Dar_ManCheck( pMan ) )
{
printf( "Abc_NtkDarToCnf: AIG check has failed.\n" );
Dar_ManStop( pMan );
return NULL;
}
// perform balance
Dar_ManPrintStats( pMan );
// derive CNF
pCnf = Cnf_ManStart();
pData = Cnf_Derive( pCnf, pMan );
{
Vec_Ptr_t * vMapped;
vMapped = Cnf_ManScanMapping( pCnf, 1 );
pNtkNew = Abc_NtkConstructFromCnf( pNtk, pCnf, vMapped );
Vec_PtrFree( vMapped );
}
Dar_ManStop( pMan );
Cnf_ManStop( pCnf );
// write CNF into a file
// Cnf_DataWriteIntoFile( pData, pFileName );
Cnf_DataFree( pData );
return pNtkNew;
}
////////////////////////////////////////////////////////////////////////
/// END OF FILE ///
......
......@@ -1414,13 +1414,19 @@ int IoCommandWriteCnf( Abc_Frame_t * pAbc, int argc, char **argv )
char * pFileName;
int c;
int fAllPrimes;
int fNewAlgo;
extern Abc_Ntk_t * Abc_NtkDarToCnf( Abc_Ntk_t * pNtk, char * pFileName );
fNewAlgo = 1;
fAllPrimes = 0;
Extra_UtilGetoptReset();
while ( ( c = Extra_UtilGetopt( argc, argv, "ph" ) ) != EOF )
while ( ( c = Extra_UtilGetopt( argc, argv, "nph" ) ) != EOF )
{
switch ( c )
{
case 'n':
fNewAlgo ^= 1;
break;
case 'p':
fAllPrimes ^= 1;
break;
......@@ -1441,15 +1447,18 @@ int IoCommandWriteCnf( Abc_Frame_t * pAbc, int argc, char **argv )
printf( "Warning: Selected option to write all primes has no effect when deriving CNF from AIG.\n" );
}
// call the corresponding file writer
if ( fAllPrimes )
if ( fNewAlgo )
Abc_NtkDarToCnf( pAbc->pNtkCur, pFileName );
else if ( fAllPrimes )
Io_WriteCnf( pAbc->pNtkCur, pFileName, 1 );
else
Io_Write( pAbc->pNtkCur, pFileName, IO_FILE_CNF );
return 0;
usage:
fprintf( pAbc->Err, "usage: write_cnf [-ph] <file>\n" );
fprintf( pAbc->Err, "usage: write_cnf [-nph] <file>\n" );
fprintf( pAbc->Err, "\t write the miter cone into a CNF file\n" );
fprintf( pAbc->Err, "\t-n : toggle using new algorithm [default = %s]\n", fNewAlgo? "yes" : "no" );
fprintf( pAbc->Err, "\t-p : toggle using all primes to enhance implicativity [default = %s]\n", fAllPrimes? "yes" : "no" );
fprintf( pAbc->Err, "\t-h : print the help massage\n" );
fprintf( pAbc->Err, "\tfile : the name of the file to write\n" );
......
......@@ -337,6 +337,7 @@ extern If_Obj_t * If_ManCreateCi( If_Man_t * p );
extern If_Obj_t * If_ManCreateCo( If_Man_t * p, If_Obj_t * pDriver, int fCompl0 );
extern If_Obj_t * If_ManCreateAnd( If_Man_t * p, If_Obj_t * pFan0, int fCompl0, If_Obj_t * pFan1, int fCompl1 );
extern If_Obj_t * If_ManCreateXnor( If_Man_t * p, If_Obj_t * pFan0, If_Obj_t * pFan1 );
extern If_Obj_t * If_ManCreateMnux( If_Man_t * p, If_Obj_t * pFan0, If_Obj_t * pFan1, If_Obj_t * pCtrl );
extern void If_ManCreateChoice( If_Man_t * p, If_Obj_t * pRepr );
extern void If_ManSetupCutTriv( If_Man_t * p, If_Cut_t * pCut, int ObjId );
extern void If_ManSetupCiCutSets( If_Man_t * p );
......
......@@ -237,6 +237,25 @@ If_Obj_t * If_ManCreateXnor( If_Man_t * p, If_Obj_t * pFan0, If_Obj_t * pFan1 )
/**Function*************************************************************
Synopsis [Create the new node assuming it does not exist.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
If_Obj_t * If_ManCreateMnux( If_Man_t * p, If_Obj_t * pFan0, If_Obj_t * pFan1, If_Obj_t * pCtrl )
{
If_Obj_t * pRes1, * pRes2;
pRes1 = If_ManCreateAnd( p, pFan0, 0, pCtrl, 1 );
pRes2 = If_ManCreateAnd( p, pFan1, 0, pCtrl, 0 );
return If_ManCreateAnd( p, pRes1, 1, pRes2, 1 );
}
/**Function*************************************************************
Synopsis [Creates the choice node.]
Description [Should be called after the equivalence class nodes are linked.]
......
......@@ -405,6 +405,8 @@ extern void ** Extra_ArrayAlloc( int nCols, int nRows, int Size );
extern unsigned short ** Extra_TruthPerm43();
extern unsigned ** Extra_TruthPerm53();
extern unsigned ** Extra_TruthPerm54();
/* bubble sort for small number of entries */
extern void Extra_BubbleSort( int Order[], int Costs[], int nSize, int fIncreasing );
/* for independence from CUDD */
extern unsigned int Cudd_PrimeCopy( unsigned int p );
......
......@@ -2070,6 +2070,55 @@ unsigned ** Extra_Truths8()
/**Function*************************************************************
Synopsis [Bubble-sorts components by scores in increasing order.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Extra_BubbleSort( int Order[], int Costs[], int nSize, int fIncreasing )
{
int i, Temp, fChanges;
assert( nSize < 1000 );
for ( i = 0; i < nSize; i++ )
Order[i] = i;
if ( fIncreasing )
{
do {
fChanges = 0;
for ( i = 0; i < nSize - 1; i++ )
{
if ( Costs[Order[i]] <= Costs[Order[i+1]] )
continue;
Temp = Order[i];
Order[i] = Order[i+1];
Order[i+1] = Temp;
fChanges = 1;
}
} while ( fChanges );
}
else
{
do {
fChanges = 0;
for ( i = 0; i < nSize - 1; i++ )
{
if ( Costs[Order[i]] >= Costs[Order[i+1]] )
continue;
Temp = Order[i];
Order[i] = Order[i+1];
Order[i+1] = Temp;
fChanges = 1;
}
} while ( fChanges );
}
}
/**Function*************************************************************
Synopsis [Returns the smallest prime larger than the number.]
Description []
......@@ -2104,7 +2153,6 @@ unsigned int Cudd_PrimeCopy( unsigned int p)
} /* end of Cudd_Prime */
/*---------------------------------------------------------------------------*/
/* Definition of internal functions */
/*---------------------------------------------------------------------------*/
......
......@@ -163,7 +163,7 @@ static inline Vec_Int_t * Vec_IntDup( Vec_Int_t * pVec )
Vec_Int_t * p;
p = ALLOC( Vec_Int_t, 1 );
p->nSize = pVec->nSize;
p->nCap = pVec->nCap;
p->nCap = pVec->nSize;
p->pArray = p->nCap? ALLOC( int, p->nCap ) : NULL;
memcpy( p->pArray, pVec->pArray, sizeof(int) * pVec->nSize );
return p;
......
......@@ -120,6 +120,7 @@ struct Kit_DsdNtk_t_
unsigned char nNodes; // the number of nodes
unsigned char Root; // the root of the tree
unsigned * pMem; // memory for the truth tables (memory manager?)
unsigned * pSupps; // supports of the nodes
Kit_DsdObj_t * pNodes[0]; // the nodes
};
......@@ -142,8 +143,10 @@ static inline int Kit_DsdLitRegular( int Lit ) { return Li
static inline unsigned Kit_DsdObjOffset( int nFans ) { return (nFans >> 2) + ((nFans & 3) > 0); }
static inline unsigned * Kit_DsdObjTruth( Kit_DsdObj_t * pObj ) { return pObj->Type == KIT_DSD_PRIME ? (unsigned *)pObj->pFans + pObj->Offset: NULL; }
static inline Kit_DsdObj_t * Kit_DsdNtkObj( Kit_DsdNtk_t * pNtk, int Id ) { assert( Id >= 0 && Id < pNtk->nVars + pNtk->nNodes ); return Id < pNtk->nVars ? NULL : pNtk->pNodes[Id - pNtk->nVars]; }
static inline Kit_DsdObj_t * Kit_DsdNtkRoot( Kit_DsdNtk_t * pNtk ) { return Kit_DsdNtkObj( pNtk, Kit_DsdLit2Var(pNtk->Root) ); }
static inline Kit_DsdObj_t * Kit_DsdNtkObj( Kit_DsdNtk_t * pNtk, int Id ) { assert( Id >= 0 && Id < pNtk->nVars + pNtk->nNodes ); return Id < pNtk->nVars ? NULL : pNtk->pNodes[Id - pNtk->nVars]; }
static inline Kit_DsdObj_t * Kit_DsdNtkRoot( Kit_DsdNtk_t * pNtk ) { return Kit_DsdNtkObj( pNtk, Kit_DsdLit2Var(pNtk->Root) ); }
static inline int Kit_DsdLitIsLeaf( Kit_DsdNtk_t * pNtk, int Lit ) { int Id = Kit_DsdLit2Var(Lit); assert( Id >= 0 && Id < pNtk->nVars + pNtk->nNodes ); return Id < pNtk->nVars; }
static inline unsigned Kit_DsdLitSupport( Kit_DsdNtk_t * pNtk, int Lit ) { int Id = Kit_DsdLit2Var(Lit); assert( Id >= 0 && Id < pNtk->nVars + pNtk->nNodes ); return pNtk->pSupps? (Id < pNtk->nVars? (1 << Id) : pNtk->pSupps[Id - pNtk->nVars]) : 0; }
#define Kit_DsdNtkForEachObj( pNtk, pObj, i ) \
for ( i = 0; (i < (pNtk)->nNodes) && ((pObj) = (pNtk)->pNodes[i]); i++ )
......@@ -398,6 +401,12 @@ static inline void Kit_TruthAndPhase( unsigned * pOut, unsigned * pIn0, unsigned
pOut[w] = pIn0[w] & pIn1[w];
}
}
static inline void Kit_TruthMux( unsigned * pOut, unsigned * pIn0, unsigned * pIn1, unsigned * pCtrl, int nVars )
{
int w;
for ( w = Kit_TruthWordNum(nVars)-1; w >= 0; w-- )
pOut[w] = (pIn0[w] & ~pCtrl[w]) | (pIn1[w] & pCtrl[w]);
}
////////////////////////////////////////////////////////////////////////
/// ITERATORS ///
......@@ -428,6 +437,11 @@ extern void Kit_DsdPrint( FILE * pFile, Kit_DsdNtk_t * pNtk );
extern Kit_DsdNtk_t * Kit_DsdDecompose( unsigned * pTruth, int nVars );
extern void Kit_DsdNtkFree( Kit_DsdNtk_t * pNtk );
extern int Kit_DsdNonDsdSizeMax( Kit_DsdNtk_t * pNtk );
extern void Kit_DsdGetSupports( Kit_DsdNtk_t * p );
extern Kit_DsdNtk_t * Kit_DsdExpand( Kit_DsdNtk_t * p );
extern Kit_DsdNtk_t * Kit_DsdShrink( Kit_DsdNtk_t * p, int pPrios[] );
extern void Kit_DsdRotate( Kit_DsdNtk_t * p, int pFreqs[] );
extern int Kit_DsdCofactoring( unsigned * pTruth, int nVars, int * pCofVars, int nLimit, int fVerbose );
/*=== kitFactor.c ==========================================================*/
extern Kit_Graph_t * Kit_SopFactor( Vec_Int_t * vCover, int fCompl, int nVars, Vec_Int_t * vMemory );
/*=== kitGraph.c ==========================================================*/
......@@ -478,7 +492,7 @@ extern void Kit_TruthForall( unsigned * pTruth, int nVars, int iVar )
extern void Kit_TruthForallNew( unsigned * pRes, unsigned * pTruth, int nVars, int iVar );
extern void Kit_TruthForallSet( unsigned * pRes, unsigned * pTruth, int nVars, unsigned uMask );
extern void Kit_TruthUniqueNew( unsigned * pRes, unsigned * pTruth, int nVars, int iVar );
extern void Kit_TruthMux( unsigned * pOut, unsigned * pCof0, unsigned * pCof1, int nVars, int iVar );
extern void Kit_TruthMuxVar( unsigned * pOut, unsigned * pCof0, unsigned * pCof1, int nVars, int iVar );
extern void Kit_TruthChangePhase( unsigned * pTruth, int nVars, int iVar );
extern int Kit_TruthMinCofSuppOverlap( unsigned * pTruth, int nVars, int * pVarMin );
extern void Kit_TruthCountOnesInCofs( unsigned * pTruth, int nVars, short * pStore );
......
......@@ -854,7 +854,7 @@ void Kit_TruthForallSet( unsigned * pRes, unsigned * pTruth, int nVars, unsigned
SeeAlso []
***********************************************************************/
void Kit_TruthMux( unsigned * pOut, unsigned * pCof0, unsigned * pCof1, int nVars, int iVar )
void Kit_TruthMuxVar( unsigned * pOut, unsigned * pCof0, unsigned * pCof1, int nVars, int iVar )
{
int nWords = Kit_TruthWordNum( nVars );
int i, k, Step;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment