From ffd77ffedda47d5ec5541c6a51bb9e80540fd3f7 Mon Sep 17 00:00:00 2001 From: Alan Mishchenko Date: Wed, 17 Sep 2014 15:14:17 -0700 Subject: Improvements to word-level Verilog parser. --- src/base/wlc/wlcWriteVer.c | 90 +++++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 86 insertions(+), 4 deletions(-) (limited to 'src/base/wlc/wlcWriteVer.c') diff --git a/src/base/wlc/wlcWriteVer.c b/src/base/wlc/wlcWriteVer.c index 3086011a..6899d462 100644 --- a/src/base/wlc/wlcWriteVer.c +++ b/src/base/wlc/wlcWriteVer.c @@ -31,6 +31,60 @@ ABC_NAMESPACE_IMPL_START /// FUNCTION DEFINITIONS /// //////////////////////////////////////////////////////////////////////// +/**Function************************************************************* + + Synopsis [] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ +void Wlc_WriteTableOne( FILE * pFile, int nFans, int nOuts, word * pTable, int Id ) +{ + int m, nMints = (1< 0 && nOuts <= 64 && (64 % nOuts) == 0 ); + fprintf( pFile, "module table%d(ind, val);\n", Id ); + fprintf( pFile, " input [%d:0] ind;\n", nFans-1 ); + fprintf( pFile, " output [%d:0] val;\n", nOuts-1 ); + fprintf( pFile, " reg [%d:0] val;\n", nOuts-1 ); + fprintf( pFile, " always @(ind)\n" ); + fprintf( pFile, " begin\n" ); + fprintf( pFile, " case (ind)\n" ); + for ( m = 0; m < nMints; m++ ) + fprintf( pFile, " %d\'h%x: val = %d\'h%x;\n", nFans, m, nOuts, (pTable[(nOuts * m) >> 6] >> ((nOuts * m) & 63)) & Abc_Tt6Mask(nOuts) ); + fprintf( pFile, " endcase\n" ); + fprintf( pFile, " end\n" ); + fprintf( pFile, "endmodule\n" ); + fprintf( pFile, "\n" ); +} +void Wlc_WriteTables( FILE * pFile, Wlc_Ntk_t * p ) +{ + Vec_Int_t * vNodes; + Wlc_Obj_t * pObj, * pFanin; + word * pTable; + int i; + if ( p->vTables == NULL || Vec_PtrSize(p->vTables) == 0 ) + return; + // map tables into their nodes + vNodes = Vec_IntStart( Vec_PtrSize(p->vTables) ); + Wlc_NtkForEachObj( p, pObj, i ) + if ( pObj->Type == WLC_OBJ_TABLE ) + Vec_IntWriteEntry( vNodes, Wlc_ObjTableId(pObj), i ); + // write tables + Vec_PtrForEachEntry( word *, p->vTables, pTable, i ) + { + pObj = Wlc_NtkObj( p, Vec_IntEntry(vNodes, i) ); + assert( pObj->Type == WLC_OBJ_TABLE ); + pFanin = Wlc_ObjFanin0( p, pObj ); + Wlc_WriteTableOne( pFile, Wlc_ObjRange(pFanin), Wlc_ObjRange(pObj), pTable, i ); + } + Vec_IntFree( vNodes ); +} + /**Function************************************************************* Synopsis [] @@ -80,23 +134,50 @@ void Wlc_WriteVerInt( FILE * pFile, Wlc_Ntk_t * p ) if ( Wlc_NtkPoNum(p) > 0 ) Wlc_WriteVerIntVec( pFile, p, &p->vPos, 3 ); fprintf( pFile, " );\n" ); + // mark fanins of rotation shifts + Wlc_NtkForEachObj( p, pObj, i ) + if ( pObj->Type == WLC_OBJ_ROTATE_R || pObj->Type == WLC_OBJ_ROTATE_L ) + Wlc_ObjFanin1(p, pObj)->Mark = 1; Wlc_NtkForEachObj( p, pObj, i ) { char * pName = Wlc_ObjName(p, i); char * pName0 = Wlc_ObjFaninNum(pObj) ? Wlc_ObjName(p, Wlc_ObjFaninId0(pObj)) : NULL; int nDigits = Abc_Base10Log(pObj->End+1) + Abc_Base10Log(pObj->Beg+1); + if ( pObj->Mark ) + { + pObj->Mark = 0; + continue; + } sprintf( Range, "%s[%d:%d]%*s", pObj->Signed ? "signed ":" ", pObj->End, pObj->Beg, 8-nDigits, "" ); fprintf( pFile, " " ); - assert( pObj->Type != WLC_OBJ_TABLE ); if ( pObj->Type == WLC_OBJ_PI ) - fprintf( pFile, "input wire %s %-16s", Range, pName ); + fprintf( pFile, "input wire %s %s", Range, pName ); else if ( pObj->Type == WLC_OBJ_PO ) fprintf( pFile, "output wire %s %-16s = %s", Range, pName, pName0 ); + else if ( pObj->Type == WLC_OBJ_TABLE ) + { + // wire [3:0] s4972; table0 s4972_Index(s4971, s4972); + fprintf( pFile, " wire %s %s ; table%d s%d_Index(%s, %s)", Range, pName, Wlc_ObjTableId(pObj), i, pName0, pName ); + } else if ( pObj->Type == WLC_OBJ_CONST ) { fprintf( pFile, " wire %s %-16s = %d\'%sh", Range, pName, Wlc_ObjRange(pObj), pObj->Signed ? "s":"" ); Abc_TtPrintHexArrayRev( pFile, (word *)Wlc_ObjConstValue(pObj), (Wlc_ObjRange(pObj) + 3) / 4 ); } + else if ( pObj->Type == WLC_OBJ_ROTATE_R || pObj->Type == WLC_OBJ_ROTATE_L ) + { + // wire [27:0] s4960 = (s57 >> 17) | (s57 << 11); + Wlc_Obj_t * pShift = Wlc_ObjFanin1(p, pObj); + int Num0 = *Wlc_ObjConstValue(pShift); + int Num1 = Wlc_ObjRange(pObj) - Num0; + assert( pShift->Type == WLC_OBJ_CONST ); + assert( Num0 > 0 && Num0 < Wlc_ObjRange(pObj) ); + fprintf( pFile, " wire %s %-16s = ", Range, Wlc_ObjName(p, i) ); + if ( pObj->Type == WLC_OBJ_ROTATE_R ) + fprintf( pFile, "(%s >> %d) | (%s << %d)", pName0, Num0, pName0, Num1 ); + else + fprintf( pFile, "(%s << %d) | (%s >> %d)", pName0, Num0, pName0, Num1 ); + } else { fprintf( pFile, " wire %s %-16s = ", Range, Wlc_ObjName(p, i) ); @@ -127,7 +208,7 @@ void Wlc_WriteVerInt( FILE * pFile, Wlc_Ntk_t * p ) fprintf( pFile, " %s%s", Wlc_ObjName(p, Wlc_ObjFaninId(pObj, k)), k == Wlc_ObjFaninNum(pObj)-1 ? "":"," ); fprintf( pFile, " }" ); } - else + else { fprintf( pFile, "%s ", Wlc_ObjName(p, Wlc_ObjFaninId(pObj, 0)) ); if ( pObj->Type == WLC_OBJ_SHIFT_R ) @@ -150,7 +231,7 @@ void Wlc_WriteVerInt( FILE * pFile, Wlc_Ntk_t * p ) fprintf( pFile, "||" ); else if ( pObj->Type == WLC_OBJ_COMP_EQU ) fprintf( pFile, "==" ); - else if ( pObj->Type == WLC_OBJ_COMP_NOT ) + else if ( pObj->Type == WLC_OBJ_COMP_NOTEQU ) fprintf( pFile, "!=" ); else if ( pObj->Type == WLC_OBJ_COMP_LESS ) fprintf( pFile, "<" ); @@ -191,6 +272,7 @@ void Wlc_WriteVer( Wlc_Ntk_t * p, char * pFileName ) } fprintf( pFile, "// Benchmark \"%s\" written by ABC on %s\n", p->pName, Extra_TimeStamp() ); fprintf( pFile, "\n" ); + Wlc_WriteTables( pFile, p ); Wlc_WriteVerInt( pFile, p ); fprintf( pFile, "\n" ); fclose( pFile ); -- cgit v1.2.3