summaryrefslogtreecommitdiffstats
path: root/src/base/io
diff options
context:
space:
mode:
authorAlan Mishchenko <alanmi@berkeley.edu>2011-10-04 18:43:23 +0700
committerAlan Mishchenko <alanmi@berkeley.edu>2011-10-04 18:43:23 +0700
commitd66b586330ba6e285fb12a4bc21779d4b88a403f (patch)
tree478ba55c55aea1a5a6b4c90ff3877509b11095e5 /src/base/io
parent8c302870f44d718261962d24e034ee19a8b6add8 (diff)
downloadabc-d66b586330ba6e285fb12a4bc21779d4b88a403f.tar.gz
abc-d66b586330ba6e285fb12a4bc21779d4b88a403f.tar.bz2
abc-d66b586330ba6e285fb12a4bc21779d4b88a403f.zip
Modified write_blif to output LUT structures.
Diffstat (limited to 'src/base/io')
-rw-r--r--src/base/io/io.c24
-rw-r--r--src/base/io/ioAbc.h2
-rw-r--r--src/base/io/ioWriteBlif.c164
3 files changed, 177 insertions, 13 deletions
diff --git a/src/base/io/io.c b/src/base/io/io.c
index d8277b08..3b85a020 100644
--- a/src/base/io/io.c
+++ b/src/base/io/io.c
@@ -1581,13 +1581,28 @@ usage:
int IoCommandWriteBlif( Abc_Frame_t * pAbc, int argc, char **argv )
{
char * pFileName;
+ char * pLutStruct = NULL;
int c, fSpecial = 0;
Extra_UtilGetoptReset();
- while ( ( c = Extra_UtilGetopt( argc, argv, "jh" ) ) != EOF )
+ while ( ( c = Extra_UtilGetopt( argc, argv, "Sjh" ) ) != EOF )
{
switch ( c )
{
+ case 'S':
+ if ( globalUtilOptind >= argc )
+ {
+ Abc_Print( -1, "Command line switch \"-S\" should be followed by string.\n" );
+ goto usage;
+ }
+ pLutStruct = argv[globalUtilOptind];
+ globalUtilOptind++;
+ if ( !strlen(pLutStruct) == 2 && !strlen(pLutStruct) == 3 )
+ {
+ Abc_Print( -1, "Command line switch \"-S\" should be followed by a 2- or 3-char string (e.g. \"44\" or \"555\").\n" );
+ goto usage;
+ }
+ break;
case 'j':
fSpecial ^= 1;
break;
@@ -1607,15 +1622,16 @@ int IoCommandWriteBlif( Abc_Frame_t * pAbc, int argc, char **argv )
// get the output file name
pFileName = argv[globalUtilOptind];
// call the corresponding file writer
- if ( fSpecial )
- Io_WriteBlifSpecial( pAbc->pNtkCur, pFileName );
+ if ( fSpecial || pLutStruct )
+ Io_WriteBlifSpecial( pAbc->pNtkCur, pFileName, pLutStruct );
else
Io_Write( pAbc->pNtkCur, pFileName, IO_FILE_BLIF );
return 0;
usage:
- fprintf( pAbc->Err, "usage: write_blif [-jh] <file>\n" );
+ fprintf( pAbc->Err, "usage: write_blif [-S str] [-jh] <file>\n" );
fprintf( pAbc->Err, "\t writes the network into a BLIF file\n" );
+ fprintf( pAbc->Err, "\t-S str : string representing the LUT structure [default = %s]\n", pLutStruct ? pLutStruct : "not used" );
fprintf( pAbc->Err, "\t-j : enables special BLIF writing [default = %s]\n", fSpecial? "yes" : "no" );;
fprintf( pAbc->Err, "\t-h : print the help massage\n" );
fprintf( pAbc->Err, "\tfile : the name of the file to write (extension .blif)\n" );
diff --git a/src/base/io/ioAbc.h b/src/base/io/ioAbc.h
index fa3f6240..f3db4c15 100644
--- a/src/base/io/ioAbc.h
+++ b/src/base/io/ioAbc.h
@@ -106,7 +106,7 @@ extern void Io_WriteBblif( Abc_Ntk_t * pNtk, char * pFileName );
extern void Io_WriteBlifLogic( Abc_Ntk_t * pNtk, char * pFileName, int fWriteLatches );
extern void Io_WriteBlif( Abc_Ntk_t * pNtk, char * pFileName, int fWriteLatches, int fBb2Wb, int fSeq );
extern void Io_WriteTimingInfo( FILE * pFile, Abc_Ntk_t * pNtk );
-extern void Io_WriteBlifSpecial( Abc_Ntk_t * pNtk, char * FileName );
+extern void Io_WriteBlifSpecial( Abc_Ntk_t * pNtk, char * FileName, char * pLutStruct );
/*=== abcWriteBlifMv.c ==========================================================*/
extern void Io_WriteBlifMv( Abc_Ntk_t * pNtk, char * FileName );
/*=== abcWriteBench.c =========================================================*/
diff --git a/src/base/io/ioWriteBlif.c b/src/base/io/ioWriteBlif.c
index dd33cfdd..e731631e 100644
--- a/src/base/io/ioWriteBlif.c
+++ b/src/base/io/ioWriteBlif.c
@@ -661,10 +661,10 @@ void Abc_NtkConvertBb2Wb( char * pFileNameIn, char * pFileNameOut, int fSeq, int
SeeAlso []
***********************************************************************/
-char * Io_NtkDeriveSop( Mem_Flex_t * pMem, unsigned uTruth, int nVars, Vec_Int_t * vCover )
+char * Io_NtkDeriveSop( Mem_Flex_t * pMem, word uTruth, int nVars, Vec_Int_t * vCover )
{
char * pSop;
- int RetValue = Kit_TruthIsop( &uTruth, nVars, vCover, 1 );
+ int RetValue = Kit_TruthIsop( (unsigned *)&uTruth, nVars, vCover, 1 );
assert( RetValue == 0 || RetValue == 1 );
// check the case of constant cover
if ( Vec_IntSize(vCover) == 0 || (Vec_IntSize(vCover) == 1 && Vec_IntEntry(vCover,0) == 0) )
@@ -767,7 +767,7 @@ void Io_NtkWriteNodeInt( FILE * pFile, Abc_Obj_t * pNode, Vec_Int_t * vCover )
for ( c = 0; c < 2; c++ )
{
pSop = Io_NtkDeriveSop( (Mem_Flex_t *)Abc_ObjNtk(pNode)->pManFunc,
- (unsigned)(nVars == 7 ? Cofs7[c][0] : Cofs6[c]), nVarsMin[c], vCover );
+ (word)(nVars == 7 ? Cofs7[c][0] : Cofs6[c]), nVarsMin[c], vCover );
fprintf( pFile, ".names" );
for ( i = 0; i < nVarsMin[c]; i++ )
fprintf( pFile, " %s", Abc_ObjName(Abc_ObjFanin(pNode,pVars[c][i])) );
@@ -819,7 +819,7 @@ void Io_NtkWriteNodeInt( FILE * pFile, Abc_Obj_t * pNode, Vec_Int_t * vCover )
// write SOP
pSop = Io_NtkDeriveSop( (Mem_Flex_t *)Abc_ObjNtk(pNode)->pManFunc,
- (unsigned)Cofs6[c], nVarsMin[c], vCover );
+ (word)Cofs6[c], nVarsMin[c], vCover );
fprintf( pFile, "%s", pSop );
}
}
@@ -827,6 +827,149 @@ void Io_NtkWriteNodeInt( FILE * pFile, Abc_Obj_t * pNode, Vec_Int_t * vCover )
/**Function*************************************************************
+ Synopsis [Write the node into a file.]
+
+ Description []
+
+ SideEffects []
+
+ SeeAlso []
+
+***********************************************************************/
+void Io_NtkWriteNodeIntStruct( FILE * pFile, Abc_Obj_t * pNode, Vec_Int_t * vCover, char * pStr )
+{
+ Abc_Obj_t * pNet;
+ int nLeaves = Abc_ObjFaninNum(pNode);
+ int i, nLutLeaf, nLutRoot;
+
+ // quit if parameters are wrong
+ if ( strlen(pStr) != 2 )
+ {
+ printf( "Wrong LUT struct (%s)\n", pStr );
+ return;
+ }
+ nLutLeaf = pStr[0] - '0';
+ if ( nLutLeaf < 3 || nLutLeaf > 6 )
+ {
+ printf( "Leaf size (%d) should belong to {3,4,5,6}.\n", nLutLeaf );
+ return;
+ }
+ nLutRoot = pStr[1] - '0';
+ if ( nLutRoot < 3 || nLutRoot > 6 )
+ {
+ printf( "Root size (%d) should belong to {3,4,5,6}.\n", nLutRoot );
+ return;
+ }
+ if ( nLeaves > nLutLeaf + nLutRoot - 1 )
+ {
+ printf( "Node \"%s\" has %d inputs (too many for the LUT structure \"%d%d\"). Writing BLIF has failed.\n",
+ Abc_ObjName(Abc_ObjFanout0(pNode)), nLeaves, nLutLeaf, nLutRoot );
+ return;
+ }
+
+ // consider easy case
+ fprintf( pFile, "\n" );
+ if ( nLeaves <= Abc_MaxInt( nLutLeaf, nLutRoot ) )
+ {
+ // write the .names line
+ fprintf( pFile, ".names" );
+ Abc_ObjForEachFanin( pNode, pNet, i )
+ fprintf( pFile, " %s", Abc_ObjName(pNet) );
+ // get the output name
+ fprintf( pFile, " %s\n", Abc_ObjName(Abc_ObjFanout0(pNode)) );
+ // write the cubes
+ fprintf( pFile, "%s", (char*)Abc_ObjData(pNode) );
+ return;
+ }
+ else
+ {
+ extern int If_CluMinimumBase( word * t, int * pSupp, int nVarsAll, int * pnVars );
+ extern int If_CluCheckExt( void * p, word * pTruth, int nVars, int nLutLeaf, int nLutRoot, char * pLut0, char * pLut1, word * pFunc0, word * pFunc1 );
+
+ static word TruthStore[16][1<<10] = {{0}}, * pTruths[16];
+ word pCube[1<<10], pRes[1<<10], Func0, Func1;
+ char pLut0[32], pLut1[32], * pSop;
+// int nVarsMin[3], pVars[3][20];
+
+ if ( TruthStore[0][0] == 0 )
+ {
+ static word Truth6[6] = {
+ 0xAAAAAAAAAAAAAAAA,
+ 0xCCCCCCCCCCCCCCCC,
+ 0xF0F0F0F0F0F0F0F0,
+ 0xFF00FF00FF00FF00,
+ 0xFFFF0000FFFF0000,
+ 0xFFFFFFFF00000000
+ };
+ int nVarsMax = 16;
+ int nWordsMax = (1 << nVarsMax);
+ int i, k;
+ assert( nVarsMax <= 16 );
+ for ( i = 0; i < nVarsMax; i++ )
+ pTruths[i] = TruthStore[i];
+ for ( i = 0; i < 6; i++ )
+ for ( k = 0; k < nWordsMax; k++ )
+ pTruths[i][k] = Truth6[i];
+ for ( i = 6; i < nVarsMax; i++ )
+ for ( k = 0; k < nWordsMax; k++ )
+ pTruths[i][k] = ((k >> (i-6)) & 1) ? ~0 : 0;
+ }
+
+ // collect variables
+// Abc_ObjForEachFanin( pNode, pNet, i )
+// pVars[0][i] = pVars[1][i] = pVars[2][i] = i;
+
+ // derive truth table
+ Abc_SopToTruthBig( (char*)Abc_ObjData(pNode), nLeaves, pTruths, pCube, pRes );
+
+// Extra_PrintHex( stdout, (unsigned *)pRes, nLeaves ); printf( " " );
+// Kit_DsdPrintFromTruth( (unsigned*)pRes, nLeaves ); printf( "\n" );
+
+ // perform decomposition
+ if ( !If_CluCheckExt( NULL, pRes, nLeaves, nLutLeaf, nLutRoot, pLut0, pLut1, &Func0, &Func1 ) )
+ {
+ Extra_PrintHex( stdout, (unsigned *)pRes, nLeaves ); printf( " " );
+ Kit_DsdPrintFromTruth( (unsigned*)pRes, nLeaves ); printf( "\n" );
+ printf( "Node \"%s\" is not decomposable. Writing BLIF has failed.\n", Abc_ObjName(Abc_ObjFanout0(pNode)) );
+ return;
+ }
+
+ // write leaf node
+ fprintf( pFile, ".names" );
+ for ( i = 0; i < pLut1[0]; i++ )
+ fprintf( pFile, " %s", Abc_ObjName(Abc_ObjFanin(pNode,pLut1[2+i])) );
+ fprintf( pFile, " %s_lut1\n", Abc_ObjName(Abc_ObjFanout0(pNode)) );
+ // write SOP
+ pSop = Io_NtkDeriveSop( (Mem_Flex_t *)Abc_ObjNtk(pNode)->pManFunc, Func1, pLut1[0], vCover );
+ fprintf( pFile, "%s", pSop );
+/*
+ // write leaf node
+ fprintf( pFile, ".names" );
+ for ( i = 0; i < pLut2[0]; i++ )
+ fprintf( pFile, " %s", Abc_ObjName(Abc_ObjFanin(pNode,pLut2[2+i])) );
+ fprintf( pFile, " %s_lut1\n", Abc_ObjName(Abc_ObjFanout0(pNode)) );
+ // write SOP
+ pSop = Io_NtkDeriveSop( (Mem_Flex_t *)Abc_ObjNtk(pNode)->pManFunc, Func2, pLut2[0], vCover );
+ fprintf( pFile, "%s", pSop );
+*/
+ // write root node
+ fprintf( pFile, ".names" );
+ for ( i = 0; i < pLut0[0]; i++ )
+ if ( pLut0[2+i] == nLeaves )
+ fprintf( pFile, " %s_lut1", Abc_ObjName(Abc_ObjFanout0(pNode)) );
+ else if ( pLut0[2+i] == nLeaves+1 )
+ fprintf( pFile, " %s_lut2", Abc_ObjName(Abc_ObjFanout0(pNode)) );
+ else
+ fprintf( pFile, " %s", Abc_ObjName(Abc_ObjFanin(pNode,pLut0[2+i])) );
+ fprintf( pFile, " %s\n", Abc_ObjName(Abc_ObjFanout0(pNode)) );
+ // write SOP
+ pSop = Io_NtkDeriveSop( (Mem_Flex_t *)Abc_ObjNtk(pNode)->pManFunc, Func0, pLut0[0], vCover );
+ fprintf( pFile, "%s", pSop );
+ }
+}
+
+/**Function*************************************************************
+
Synopsis [Write the network into a BLIF file with the given name.]
Description []
@@ -836,7 +979,7 @@ void Io_NtkWriteNodeInt( FILE * pFile, Abc_Obj_t * pNode, Vec_Int_t * vCover )
SeeAlso []
***********************************************************************/
-void Io_WriteBlifInt( Abc_Ntk_t * pNtk, char * FileName )
+void Io_WriteBlifInt( Abc_Ntk_t * pNtk, char * FileName, char * pLutStruct )
{
FILE * pFile;
Vec_Int_t * vCover;
@@ -871,7 +1014,12 @@ void Io_WriteBlifInt( Abc_Ntk_t * pNtk, char * FileName )
// write each internal node
vCover = Vec_IntAlloc( (1<<16) );
Abc_NtkForEachNode( pNtk, pNode, i )
- Io_NtkWriteNodeInt( pFile, pNode, vCover );
+ {
+ if ( pLutStruct )
+ Io_NtkWriteNodeIntStruct( pFile, pNode, vCover, pLutStruct );
+ else
+ Io_NtkWriteNodeInt( pFile, pNode, vCover );
+ }
Vec_IntFree( vCover );
// write the end
fprintf( pFile, ".end\n\n" );
@@ -889,7 +1037,7 @@ void Io_WriteBlifInt( Abc_Ntk_t * pNtk, char * FileName )
SeeAlso []
***********************************************************************/
-void Io_WriteBlifSpecial( Abc_Ntk_t * pNtk, char * FileName )
+void Io_WriteBlifSpecial( Abc_Ntk_t * pNtk, char * FileName, char * pLutStruct )
{
Abc_Ntk_t * pNtkTemp;
assert( Abc_NtkIsLogic(pNtk) );
@@ -901,7 +1049,7 @@ void Io_WriteBlifSpecial( Abc_Ntk_t * pNtk, char * FileName )
fprintf( stdout, "Writing BLIF has failed.\n" );
return;
}
- Io_WriteBlifInt( pNtkTemp, FileName );
+ Io_WriteBlifInt( pNtkTemp, FileName, pLutStruct );
Abc_NtkDelete( pNtkTemp );
}