From 13bd7b334cfc84a19446a8ae93b59af5eb78ac22 Mon Sep 17 00:00:00 2001 From: Alan Mishchenko Date: Fri, 24 Aug 2012 21:31:46 -0700 Subject: New package to read/write a subset of Liberty for STA. --- src/map/scl/module.make | 4 + src/map/scl/scl.c | 178 ++++++++++++++++++ src/map/scl/scl.h | 60 ++++++ src/map/scl/sclFile.c | 485 ++++++++++++++++++++++++++++++++++++++++++++++++ src/map/scl/sclInt.h | 366 ++++++++++++++++++++++++++++++++++++ src/map/scl/sclSize.c | 50 +++++ src/map/scl/sclTime.c | 50 +++++ 7 files changed, 1193 insertions(+) create mode 100644 src/map/scl/module.make create mode 100644 src/map/scl/scl.c create mode 100644 src/map/scl/scl.h create mode 100644 src/map/scl/sclFile.c create mode 100644 src/map/scl/sclInt.h create mode 100644 src/map/scl/sclSize.c create mode 100644 src/map/scl/sclTime.c (limited to 'src/map') diff --git a/src/map/scl/module.make b/src/map/scl/module.make new file mode 100644 index 00000000..208f4aaa --- /dev/null +++ b/src/map/scl/module.make @@ -0,0 +1,4 @@ +SRC += src/map/scl/scl.c \ + src/map/scl/sclFile.c \ + src/map/scl/sclSize.c \ + src/map/scl/sclTime.c diff --git a/src/map/scl/scl.c b/src/map/scl/scl.c new file mode 100644 index 00000000..69c72f39 --- /dev/null +++ b/src/map/scl/scl.c @@ -0,0 +1,178 @@ +/**CFile**************************************************************** + + FileName [scl.c] + + SystemName [ABC: Logic synthesis and verification system.] + + Synopsis [Standard-cell library representation.] + + Author [Alan Mishchenko, Niklas Een] + + Affiliation [UC Berkeley] + + Date [Ver. 1.0. Started - August 24, 2012.] + + Revision [$Id: scl.c,v 1.0 2012/08/24 00:00:00 alanmi Exp $] + +***********************************************************************/ + +#include "sclInt.h" +#include "scl.h" +#include "base/main/mainInt.h" + +ABC_NAMESPACE_IMPL_START + + +//////////////////////////////////////////////////////////////////////// +/// DECLARATIONS /// +//////////////////////////////////////////////////////////////////////// + +static int Scl_CommandRead ( Abc_Frame_t * pAbc, int argc, char **argv ); +static int Scl_CommandWrite( Abc_Frame_t * pAbc, int argc, char **argv ); + +//////////////////////////////////////////////////////////////////////// +/// FUNCTION DEFINITIONS /// +//////////////////////////////////////////////////////////////////////// + +/**Function************************************************************* + + Synopsis [] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ +void Scl_Init( Abc_Frame_t * pAbc ) +{ + Cmd_CommandAdd( pAbc, "SC mapping", "read_scl", Scl_CommandRead, 0 ); + Cmd_CommandAdd( pAbc, "SC mapping", "write_scl", Scl_CommandWrite, 0 ); +} + +/**Function************************************************************* + + Synopsis [] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ +void Scl_End( Abc_Frame_t * pAbc ) +{ + Abc_SclLoad( NULL, &pAbc->pLibScl ); +} + + + +/**Function************************************************************* + + Synopsis [] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ +int Scl_CommandRead( Abc_Frame_t * pAbc, int argc, char ** argv ) +{ + char * pFileName; + FILE * pFile; + int c; + + Extra_UtilGetoptReset(); + while ( ( c = Extra_UtilGetopt( argc, argv, "h" ) ) != EOF ) + { + switch ( c ) + { + case 'h': + goto usage; + default: + goto usage; + } + } + if ( argc != globalUtilOptind + 1 ) + goto usage; + + // get the input file name + pFileName = argv[globalUtilOptind]; + if ( (pFile = fopen( pFileName, "r" )) == NULL ) + { + fprintf( pAbc->Err, "Cannot open input file \"%s\". \n", pFileName ); + return 1; + } + fclose( pFile ); + + // set the new network + Abc_SclLoad( pFileName, &pAbc->pLibScl ); + return 0; + +usage: + fprintf( pAbc->Err, "usage: read_scl [-h] \n" ); + fprintf( pAbc->Err, "\t reads Liberty library from file\n" ); + fprintf( pAbc->Err, "\t-h : prints the command summary\n" ); + fprintf( pAbc->Err, "\t : the name of a file to read\n" ); + return 1; +} + +/**Function************************************************************* + + Synopsis [] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ +int Scl_CommandWrite( Abc_Frame_t * pAbc, int argc, char **argv ) +{ + char * pFileName; + int c; + + Extra_UtilGetoptReset(); + while ( ( c = Extra_UtilGetopt( argc, argv, "h" ) ) != EOF ) + { + switch ( c ) + { + case 'h': + goto usage; + default: + goto usage; + } + } + if ( argc != globalUtilOptind + 1 ) + goto usage; + if ( pAbc->pLibScl == NULL ) + { + fprintf( pAbc->Err, "There is no Liberty Library available.\n" ); + return 1; + } + // get the input file name + pFileName = argv[globalUtilOptind]; + Abc_SclSave( pFileName, pAbc->pLibScl ); + return 0; + +usage: + fprintf( pAbc->Err, "usage: write_scl [-h] \n" ); + fprintf( pAbc->Err, "\t write Liberty library into file\n" ); + fprintf( pAbc->Err, "\t-h : print the help massage\n" ); + fprintf( pAbc->Err, "\t : the name of the file to write\n" ); + return 1; +} + + +//////////////////////////////////////////////////////////////////////// +/// END OF FILE /// +//////////////////////////////////////////////////////////////////////// + + +ABC_NAMESPACE_IMPL_END + diff --git a/src/map/scl/scl.h b/src/map/scl/scl.h new file mode 100644 index 00000000..5ce2f347 --- /dev/null +++ b/src/map/scl/scl.h @@ -0,0 +1,60 @@ +/**CFile**************************************************************** + + FileName [scl.h] + + SystemName [ABC: Logic synthesis and verification system.] + + Synopsis [Standard-cell library representation.] + + Author [Alan Mishchenko, Niklas Een] + + Affiliation [UC Berkeley] + + Date [Ver. 1.0. Started - August 24, 2012.] + + Revision [$Id: scl.h,v 1.0 2012/08/24 00:00:00 alanmi Exp $] + +***********************************************************************/ + +#ifndef ABC__map__scl__scl_h +#define ABC__map__scl__scl_h + + +//////////////////////////////////////////////////////////////////////// +/// INCLUDES /// +//////////////////////////////////////////////////////////////////////// + +//////////////////////////////////////////////////////////////////////// +/// PARAMETERS /// +//////////////////////////////////////////////////////////////////////// + +ABC_NAMESPACE_HEADER_START + +//////////////////////////////////////////////////////////////////////// +/// STRUCTURE DEFINITIONS /// +//////////////////////////////////////////////////////////////////////// + +//////////////////////////////////////////////////////////////////////// +/// GLOBAL VARIABLES /// +//////////////////////////////////////////////////////////////////////// + +//////////////////////////////////////////////////////////////////////// +/// MACRO DEFINITIONS /// +//////////////////////////////////////////////////////////////////////// + +//////////////////////////////////////////////////////////////////////// +/// FUNCTION DEFINITIONS /// +//////////////////////////////////////////////////////////////////////// + +/*=== scl.c =============================================================*/ +extern void Abc_SclLoad( char * pFileName, void ** ppScl ); +extern void Abc_SclSave( char * pFileName, void * pScl ); + +ABC_NAMESPACE_HEADER_END + + +#endif + +//////////////////////////////////////////////////////////////////////// +/// END OF FILE /// +//////////////////////////////////////////////////////////////////////// diff --git a/src/map/scl/sclFile.c b/src/map/scl/sclFile.c new file mode 100644 index 00000000..35f32664 --- /dev/null +++ b/src/map/scl/sclFile.c @@ -0,0 +1,485 @@ +/**CFile**************************************************************** + + FileName [sclIo.c] + + SystemName [ABC: Logic synthesis and verification system.] + + Synopsis [Standard-cell library representation.] + + Author [Alan Mishchenko, Niklas Een] + + Affiliation [UC Berkeley] + + Date [Ver. 1.0. Started - August 24, 2012.] + + Revision [$Id: sclIo.c,v 1.0 2012/08/24 00:00:00 alanmi Exp $] + +***********************************************************************/ + +#include "sclInt.h" + +ABC_NAMESPACE_IMPL_START + + +//////////////////////////////////////////////////////////////////////// +/// DECLARATIONS /// +//////////////////////////////////////////////////////////////////////// + +//////////////////////////////////////////////////////////////////////// +/// FUNCTION DEFINITIONS /// +//////////////////////////////////////////////////////////////////////// + +/**Function************************************************************* + + Synopsis [Binary IO for numbers (int, word, float) and string (char*).] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ +static inline void Abc_SclPutI( Vec_Str_t * vOut, word Val ) +{ + int i; + for ( i = 0; i < 4; i++ ) + Vec_StrPush( vOut, (char)(Val >> (8*i)) ); +} +static inline int Abc_SclGetI( Vec_Str_t * vOut, int * pPos ) +{ + int i; + int Val = 0; + for ( i = 0; i < 4; i++ ) + Val |= (int)(unsigned char)Vec_StrEntry(vOut, *pPos++) << (8*i); + return Val; +} + +static inline void Abc_SclPutW( Vec_Str_t * vOut, word Val ) +{ + int i; + for ( i = 0; i < 8; i++ ) + Vec_StrPush( vOut, (char)(Val >> (8*i)) ); +} +static inline word Abc_SclGetW( Vec_Str_t * vOut, int * pPos ) +{ + int i; + word Val = 0; + for ( i = 0; i < 8; i++ ) + Val |= (word)(unsigned char)Vec_StrEntry(vOut, *pPos++) << (8*i); + return Val; +} + +static inline void Abc_SclPutF( Vec_Str_t * vOut, float Val ) +{ + union { float num; unsigned char data[4]; } tmp; + tmp.num = Val; + Vec_StrPush( vOut, tmp.data[0] ); + Vec_StrPush( vOut, tmp.data[1] ); + Vec_StrPush( vOut, tmp.data[2] ); + Vec_StrPush( vOut, tmp.data[3] ); +} +static inline float Abc_SclGetF( Vec_Str_t * vOut, int * pPos ) +{ + union { float num; unsigned char data[4]; } tmp; + tmp.data[0] = Vec_StrEntry( vOut, *pPos++ ); + tmp.data[1] = Vec_StrEntry( vOut, *pPos++ ); + tmp.data[2] = Vec_StrEntry( vOut, *pPos++ ); + tmp.data[3] = Vec_StrEntry( vOut, *pPos++ ); + return tmp.num; +} + +static inline void Abc_SclPutS( Vec_Str_t * vOut, char * pStr ) +{ + while ( *pStr ) + Vec_StrPush( vOut, *pStr++ ); + Vec_StrPush( vOut, (char)0 ); +} +static inline char * Abc_SclGetS( Vec_Str_t * vOut, int * pPos ) +{ + char * pStr = Vec_StrEntryP( vOut, *pPos ); + while ( Vec_StrEntry(vOut, *pPos++) ); + return Abc_UtilStrsav(pStr); +} + + +/**Function************************************************************* + + Synopsis [Writing library into file.] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ +static void Abc_SclWriteSurface( Vec_Str_t * vOut, SC_Surface * p ) +{ + Vec_Flt_t * vVec; + int i, k, Entry; + float EntryF; + + Abc_SclPutI( vOut, Vec_FltSize(p->vIndex0) ); + Vec_FltForEachEntry( p->vIndex0, Entry, i ) + Abc_SclPutF( vOut, Entry ); + + Abc_SclPutI( vOut, Vec_FltSize(p->vIndex1) ); + Vec_FltForEachEntry( p->vIndex1, Entry, i ) + Abc_SclPutF( vOut, Entry ); + + Vec_PtrForEachEntry( Vec_Flt_t *, p->vData, vVec, k ) + Vec_FltForEachEntry( vVec, EntryF, i ) + Abc_SclPutF( vOut, EntryF ); + + for ( i = 0; i < 3; i++ ) + Abc_SclPutF( vOut, 0 ); + for ( i = 0; i < 4; i++ ) + Abc_SclPutF( vOut, 0 ); + for ( i = 0; i < 6; i++ ) + Abc_SclPutF( vOut, 0 ); +} +static void Abc_SclWriteLibrary( Vec_Str_t * vOut, SC_Lib * p ) +{ + SC_WireLoad * pWL; + SC_WireLoadSel * pWLS; + SC_Cell * pCell; + int n_valid_cells; + int i, j, k; + + Abc_SclPutI( vOut, ABC_SCL_CUR_VERSION ); + + // Write non-composite fields: + Abc_SclPutS( vOut, p->lib_name ); + Abc_SclPutS( vOut, p->default_wire_load ); + Abc_SclPutS( vOut, p->default_wire_load_sel ); + Abc_SclPutF( vOut, p->default_max_out_slew ); + + assert( p->unit_time >= 0 ); + assert( p->unit_cap_int >= 0 ); + Abc_SclPutI( vOut, p->unit_time ); + Abc_SclPutF( vOut, p->unit_cap_float ); + Abc_SclPutI( vOut, p->unit_cap_int ); + + // Write 'wire_load' vector: + Abc_SclPutI( vOut, Vec_PtrSize(p->vWireLoads) ); + Vec_PtrForEachEntry( SC_WireLoad *, p->vWireLoads, pWL, i ) + { + Abc_SclPutS( vOut, pWL->name ); + Abc_SclPutF( vOut, pWL->res ); + Abc_SclPutF( vOut, pWL->cap ); + + Abc_SclPutI( vOut, Vec_IntSize(pWL->vFanout) ); + for ( j = 0; j < Vec_IntSize(pWL->vFanout); j++ ) + { + Abc_SclPutI( vOut, Vec_IntEntry(pWL->vFanout, j) ); + Abc_SclPutF( vOut, Vec_FltEntry(pWL->vLen, j) ); + } + } + + // Write 'wire_load_sel' vector: + Abc_SclPutI( vOut, Vec_PtrSize(p->vWireLoadSels) ); + Vec_PtrForEachEntry( SC_WireLoadSel *, p->vWireLoadSels, pWLS, i ) + { + Abc_SclPutS( vOut, pWLS->name ); + Abc_SclPutI( vOut, Vec_FltSize(pWLS->vAreaFrom) ); + for ( j = 0; j < Vec_FltSize(pWLS->vAreaFrom); j++) + { + Abc_SclPutF( vOut, Vec_FltEntry(pWLS->vAreaFrom, j) ); + Abc_SclPutF( vOut, Vec_FltEntry(pWLS->vAreaTo, j) ); + Abc_SclPutS( vOut, Vec_PtrEntry(pWLS->vWireLoadModel, j) ); + } + } + + // Write 'cells' vector: + n_valid_cells = 0; + Vec_PtrForEachEntry( SC_Cell *, p->vCells, pCell, i ) + if ( !pCell->seq && !pCell->unsupp ) + n_valid_cells++; + + Abc_SclPutI( vOut, n_valid_cells ); + Vec_PtrForEachEntry( SC_Cell *, p->vCells, pCell, i ) + { + SC_Pin * pPin; + if ( pCell->seq || pCell->unsupp ) + continue; + + Abc_SclPutS( vOut, pCell->name ); + Abc_SclPutF( vOut, pCell->area ); + Abc_SclPutI( vOut, pCell->drive_strength ); + + // Write 'pins': (sorted at this point; first inputs, then outputs) + Abc_SclPutI( vOut, pCell->n_inputs); + Abc_SclPutI( vOut, pCell->n_outputs); + + Vec_PtrForEachEntryStop( SC_Pin *, pCell->vPins, pPin, j, pCell->n_inputs ) + { + assert(pPin->dir == sc_dir_Input); + Abc_SclPutS( vOut, pPin->name ); + Abc_SclPutF( vOut, pPin->rise_cap ); + Abc_SclPutF( vOut, pPin->fall_cap ); + } + + Vec_PtrForEachEntryStart( SC_Pin *, pCell->vPins, pPin, j, pCell->n_inputs ) + { + SC_Timings * pRTime; + word uWord; + assert(pPin->dir == sc_dir_Output); + + Abc_SclPutS( vOut, pPin->name ); + Abc_SclPutF( vOut, pPin->max_out_cap ); + Abc_SclPutF( vOut, pPin->max_out_slew ); + + Abc_SclPutI( vOut, Vec_WrdSize(pPin->vFunc) ); + Vec_WrdForEachEntry( pPin->vFunc, uWord, k ) // -- 'size = 1u << (n_vars - 6)' + Abc_SclPutW( vOut, uWord ); // -- 64-bit number, written uncompressed (low-byte first) + + // Write 'rtiming': (pin-to-pin timing tables for this particular output) + assert( Vec_PtrSize(pPin->vRTimings) == pCell->n_inputs ); + Vec_PtrForEachEntry( SC_Timings *, pPin->vRTimings, pRTime, k ) + { + Abc_SclPutS( vOut, pRTime->name ); + Abc_SclPutI( vOut, Vec_PtrSize(pRTime->vTimings) ); + // -- NOTE! After post-processing, the size of the 'rtiming[k]' vector is either + // 0 or 1 (in static timing, we have merged all tables to get the worst case). + // The case with size 0 should only occur for multi-output gates. + if ( Vec_PtrSize(pRTime->vTimings) == 1 ) + { + SC_Timing * pTime = (SC_Timing *)Vec_PtrEntry( pRTime->vTimings, 0 ); + // -- NOTE! We don't need to save 'related_pin' string because we have sorted + // the elements on input pins. + Abc_SclPutI( vOut, (int)pTime->tsense); + Abc_SclWriteSurface( vOut, pTime->pCellRise ); + Abc_SclWriteSurface( vOut, pTime->pCellFall ); + Abc_SclWriteSurface( vOut, pTime->pRiseTrans ); + Abc_SclWriteSurface( vOut, pTime->pFallTrans ); + } + else + assert( Vec_PtrSize(pRTime->vTimings) == 0 ); + } + } + } +} +void Abc_SclWrite( char * pFileName, SC_Lib * p ) +{ + Vec_Str_t * vOut; + vOut = Vec_StrAlloc( 10000 ); + Abc_SclWriteLibrary( vOut, p ); + if ( Vec_StrSize(vOut) > 0 ) + { + FILE * pFile = fopen( pFileName, "wb" ); + if ( pFile != NULL ) + { + fwrite( Vec_StrArray(vOut), Vec_StrSize(vOut), 1, pFile ); + fclose( pFile ); + } + } + Vec_StrFree( vOut ); +} +void Abc_SclSave( char * pFileName, void * pScl ) +{ + if ( pScl == NULL ) return; + Abc_SclWrite( pFileName, (SC_Lib *)pScl ); +} + + +/**Function************************************************************* + + Synopsis [Reading library from file.] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ +static void Abc_SclReadSurface( Vec_Str_t * vOut, int * pPos, SC_Surface * p ) +{ + Vec_Flt_t * vVec; + int i, j; + + for ( i = Abc_SclGetI(vOut, pPos); i != 0; i-- ) + Vec_FltPush( p->vIndex0, Abc_SclGetF(vOut, pPos) ); + + for ( i = Abc_SclGetI(vOut, pPos); i != 0; i-- ) + Vec_FltPush( p->vIndex1, Abc_SclGetF(vOut, pPos) ); + + for ( i = 0; i < Vec_FltSize(p->vIndex0); i++ ) + { + vVec = Vec_FltAlloc( Vec_FltSize(p->vIndex1) ); + Vec_PtrPush( p->vData, vVec ); + for ( j = 0; j < Vec_FltSize(p->vIndex0); j++ ) + Vec_FltPush( vVec, Abc_SclGetF(vOut, pPos) ); + } + + for ( i = 0; i < 3; i++ ) + Abc_SclGetF( vOut, pPos ); + for ( i = 0; i < 4; i++ ) + Abc_SclGetF( vOut, pPos ); + for ( i = 0; i < 6; i++ ) + Abc_SclGetF( vOut, pPos ); +} +static void Abc_SclReadLibrary( Vec_Str_t * vOut, int * pPos, SC_Lib * p ) +{ + int i, j, k, n; + int version = Abc_SclGetI( vOut, pPos ); + assert( version == ABC_SCL_CUR_VERSION ); + + // Read non-composite fields: + p->lib_name = Abc_SclGetS(vOut, pPos); + p->default_wire_load = Abc_SclGetS(vOut, pPos); + p->default_wire_load_sel = Abc_SclGetS(vOut, pPos); + p->default_max_out_slew = Abc_SclGetF(vOut, pPos); + + p->unit_time = Abc_SclGetI(vOut, pPos); + p->unit_cap_float = Abc_SclGetF(vOut, pPos); + p->unit_cap_int = Abc_SclGetI(vOut, pPos); + + // Read 'wire_load' vector: + for ( i = Abc_SclGetI(vOut, pPos); i != 0; i-- ) + { + SC_WireLoad * pWL = Abc_SclWireLoadAlloc(); + Vec_PtrPush( p->vWireLoads, pWL ); + + pWL->name = Abc_SclGetS(vOut, pPos); + pWL->res = Abc_SclGetF(vOut, pPos); + pWL->cap = Abc_SclGetF(vOut, pPos); + + for ( j = Abc_SclGetI(vOut, pPos); j != 0; j-- ) + { + Vec_IntPush( pWL->vFanout, Abc_SclGetI(vOut, pPos) ); + Vec_FltPush( pWL->vLen, Abc_SclGetF(vOut, pPos) ); + } + } + + // Read 'wire_load_sel' vector: + for ( i = Abc_SclGetI(vOut, pPos); i != 0; i-- ) + { + SC_WireLoadSel * pWLS = Abc_SclWireLoadSelAlloc(); + Vec_PtrPush( p->vWireLoadSels, pWLS ); + + pWLS->name = Abc_SclGetS(vOut, pPos); + for ( j = Abc_SclGetI(vOut, pPos); j != 0; j-- ) + { + Vec_FltPush( pWLS->vAreaFrom, Abc_SclGetF(vOut, pPos) ); + Vec_FltPush( pWLS->vAreaTo, Abc_SclGetF(vOut, pPos) ); + Vec_PtrPush( pWLS->vWireLoadModel, Abc_SclGetS(vOut, pPos) ); + } + } + + for ( i = Abc_SclGetI(vOut, pPos); i != 0; i-- ) + { + SC_Cell * pCell = Abc_SclCellAlloc(); + Vec_PtrPush( p->vCells, pCell ); + + pCell->name = Abc_SclGetS(vOut, pPos); + pCell->area = Abc_SclGetF(vOut, pPos); + pCell->drive_strength = Abc_SclGetI(vOut, pPos); + + pCell->n_inputs = Abc_SclGetI(vOut, pPos); + pCell->n_outputs = Abc_SclGetI(vOut, pPos); + + for ( j = 0; j < pCell->n_inputs; j++ ) + { + SC_Pin * pPin = Abc_SclPinAlloc(); + Vec_PtrPush( pCell->vPins, pPin ); + + pPin->dir = sc_dir_Input; + + pPin->name = Abc_SclGetS(vOut, pPos); + pPin->rise_cap = Abc_SclGetF(vOut, pPos); + pPin->fall_cap = Abc_SclGetF(vOut, pPos); + } + + for ( j = 0; j < pCell->n_outputs; j++ ) + { + SC_Pin * pPin = Abc_SclPinAlloc(); + Vec_PtrPush( pCell->vPins, pPin ); + + pPin->dir = sc_dir_Output; + + pPin->name = Abc_SclGetS(vOut, pPos); + pPin->max_out_cap = Abc_SclGetF(vOut, pPos); + pPin->max_out_slew = Abc_SclGetF(vOut, pPos); + + Vec_WrdGrow( pPin->vFunc, Abc_SclGetI(vOut, pPos) ); + for ( k = 0; k < Vec_WrdSize(pPin->vFunc); k++ ) + Vec_WrdPush( pPin->vFunc, Abc_SclGetW(vOut, pPos) ); + + // Read 'rtiming': (pin-to-pin timing tables for this particular output) + for ( k = 0; k < pCell->n_inputs; k++ ) + { + SC_Timings * pRTime = Abc_SclTimingsAlloc(); + Vec_PtrPush( pPin->vRTimings, pRTime ); + + pRTime->name = Abc_SclGetS(vOut, pPos); + + n = Abc_SclGetI(vOut, pPos); assert(n <= 1); + if ( n == 1 ) + { + SC_Timing * pTime = Abc_SclTimingAlloc(); + Vec_PtrPush( pRTime->vTimings, pTime ); + + pTime->tsense = (SC_TSense)Abc_SclGetI(vOut, pPos); + Abc_SclReadSurface( vOut, pPos, pTime->pCellRise ); + Abc_SclReadSurface( vOut, pPos, pTime->pCellFall ); + Abc_SclReadSurface( vOut, pPos, pTime->pRiseTrans ); + Abc_SclReadSurface( vOut, pPos, pTime->pFallTrans ); + } + else + assert( Vec_PtrSize(pPin->vRTimings) == 0 ); + } + } + } +} +SC_Lib * Abc_SclRead( char * pFileName ) +{ + SC_Lib * p; + FILE * pFile; + Vec_Str_t * vOut; + int nFileSize, Pos = 0; + + pFile = fopen( pFileName, "rb" ); + if ( pFile == NULL ) + { + printf( "Cannot open file \"%s\" for reading.\n", pFileName ); + return NULL; + } + // get the file size, in bytes + fseek( pFile, 0, SEEK_END ); + nFileSize = ftell( pFile ); + rewind( pFile ); + // load the contents + vOut = Vec_StrAlloc( nFileSize ); + vOut->nSize = vOut->nCap; + nFileSize = fread( Vec_StrArray(vOut), Vec_StrSize(vOut), 1, pFile ); + assert( nFileSize == Vec_StrSize(vOut) ); + fclose( pFile ); + // read the library + p = Abc_SclLibAlloc(); + Abc_SclReadLibrary( vOut, &Pos, p ); + assert( Pos == Vec_StrSize(vOut) ); + Vec_StrFree( vOut ); + return p; +} +void Abc_SclLoad( char * pFileName, void ** ppScl ) +{ + if ( *ppScl ) + { + Abc_SclLibFree( *(SC_Lib **)ppScl ); + ppScl = NULL; + } + assert( *ppScl == NULL ); + if ( pFileName ) + *(SC_Lib **)ppScl = Abc_SclRead( pFileName ); +} + + +//////////////////////////////////////////////////////////////////////// +/// END OF FILE /// +//////////////////////////////////////////////////////////////////////// + + +ABC_NAMESPACE_IMPL_END + diff --git a/src/map/scl/sclInt.h b/src/map/scl/sclInt.h new file mode 100644 index 00000000..42732dab --- /dev/null +++ b/src/map/scl/sclInt.h @@ -0,0 +1,366 @@ +/**CFile**************************************************************** + + FileName [sclInt.h] + + SystemName [ABC: Logic synthesis and verification system.] + + Synopsis [Standard-cell library representation.] + + Author [Alan Mishchenko, Niklas Een] + + Affiliation [UC Berkeley] + + Date [Ver. 1.0. Started - August 24, 2012.] + + Revision [$Id: sclInt.h,v 1.0 2012/08/24 00:00:00 alanmi Exp $] + +***********************************************************************/ + +#ifndef ABC__map__scl__sclInt_h +#define ABC__map__scl__sclInt_h + + +//////////////////////////////////////////////////////////////////////// +/// INCLUDES /// +//////////////////////////////////////////////////////////////////////// + +#include +#include +#include +#include + +#include "misc/vec/vec.h" + +ABC_NAMESPACE_HEADER_START + + +//////////////////////////////////////////////////////////////////////// +/// PARAMETERS /// +//////////////////////////////////////////////////////////////////////// + +#define ABC_SCL_CUR_VERSION 5 + +typedef enum +{ + sc_dir_NULL, + sc_dir_Input, + sc_dir_Output, + sc_dir_InOut, + sc_dir_Internal, +} SC_Dir; + +typedef enum // -- timing sense, positive-, negative- or non-unate +{ + sc_ts_NULL, + sc_ts_Pos, + sc_ts_Neg, + sc_ts_Non, +} SC_TSense; + +//////////////////////////////////////////////////////////////////////// +/// STRUCTURE DEFINITIONS /// +//////////////////////////////////////////////////////////////////////// + +typedef struct SC_WireLoad_ SC_WireLoad; +typedef struct SC_WireLoadSel_ SC_WireLoadSel; +typedef struct SC_TableTempl_ SC_TableTempl; +typedef struct SC_Surface_ SC_Surface; +typedef struct SC_Timing_ SC_Timing; +typedef struct SC_Timings_ SC_Timings; +typedef struct SC_Pin_ SC_Pin; +typedef struct SC_Cell_ SC_Cell; +typedef struct SC_Lib_ SC_Lib; + +struct SC_WireLoad_ +{ + char * name; + float res; // }- multiply estimation in 'fanout_len[].snd' with this value + float cap; // + Vec_Int_t * vFanout; // Vec > -- pairs '(#fanouts, est-wire-len)' + Vec_Flt_t * vLen; +}; + +struct SC_WireLoadSel_ +{ + char * name; + Vec_Flt_t * vAreaFrom; // Vec > -- triplets '(from-area, upto-area, wire-load-model)'; range is [from, upto[ + Vec_Flt_t * vAreaTo; + Vec_Ptr_t * vWireLoadModel; +}; + +struct SC_TableTempl_ +{ + char * name; + Vec_Ptr_t * vVars; // Vec -- name of variable (numbered from 0, not 1 as in the Liberty file) + Vec_Ptr_t * vIndex; // Vec > -- this is the point of measurement in table for the given variable +}; + +struct SC_Surface_ +{ + char * templ_name; + Vec_Flt_t * vIndex0; // Vec -- correspondes to "index_1" in the liberty file (for timing: slew) + Vec_Flt_t * vIndex1; // Vec -- correspondes to "index_2" in the liberty file (for timing: load) + Vec_Ptr_t * vData; // Vec > -- 'data[i0][i1]' gives value at '(index0[i0], index1[i1])' +}; + +struct SC_Timing_ +{ + char * related_pin; // -- related pin + SC_TSense tsense; // -- timing sense (positive_unate, negative_unate, non_unate) + char * when_text; // -- logic condition on inputs triggering this delay model for the output + SC_Surface * pCellRise; // -- Used to compute pin-to-pin delay + SC_Surface * pCellFall; + SC_Surface * pRiseTrans; // -- Used to compute output slew + SC_Surface * pFallTrans; +}; + +struct SC_Timings_ +{ + char * name; // -- the 'related_pin' field + Vec_Ptr_t * vTimings; // structures of type SC_Timing +}; + +struct SC_Pin_ +{ + char * name; + SC_Dir dir; + float cap; // -- this value is used if 'rise_cap' and 'fall_cap' is missing (copied by 'postProcess()'). + float rise_cap; // }- used for input pins ('cap' too). + float fall_cap; // } + float max_out_cap; // } + float max_out_slew; // }- used only for output pins (max values must not be exceeded or else mapping is illegal) + char * func_text; // } + Vec_Wrd_t * vFunc; // } + Vec_Ptr_t * vRTimings; // -- for output pins +}; + +struct SC_Cell_ +{ + char * name; + int seq; // -- set to TRUE by parser if a sequential element + int unsupp; // -- set to TRUE by parser if cell contains information we cannot handle + float area; + int drive_strength; // -- some library files provide this field (currently unused, but may be a good hint for sizing) + Vec_Ptr_t * vPins; // NamedSet + int n_inputs; // -- 'pins[0 .. n_inputs-1]' are input pins + int n_outputs; // -- 'pins[n_inputs .. n_inputs+n_outputs-1]' are output pins +}; + +struct SC_Lib_ +{ + char * lib_name; + char * default_wire_load; + char * default_wire_load_sel; + float default_max_out_slew; // -- 'default_max_transition'; this is copied to each output pin where 'max_transition' is not defined + int unit_time; // -- Valid 9..12. Unit is '10^(-val)' seconds (e.g. 9=1ns, 10=100ps, 11=10ps, 12=1ps) + float unit_cap_float; // -- First part is a multiplier, second either 12 or 15 for 'pf' or 'ff'. + int unit_cap_int; + Vec_Ptr_t * vWireLoads; // NamedSet + Vec_Ptr_t * vWireLoadSels; // NamedSet + Vec_Ptr_t * vTempls; // NamedSet + Vec_Ptr_t * vCells; // NamedSet +}; + +//////////////////////////////////////////////////////////////////////// +/// GLOBAL VARIABLES /// +//////////////////////////////////////////////////////////////////////// + +//////////////////////////////////////////////////////////////////////// +/// MACRO DEFINITIONS /// +//////////////////////////////////////////////////////////////////////// + +//////////////////////////////////////////////////////////////////////// +/// FUNCTION DEFINITIONS /// +//////////////////////////////////////////////////////////////////////// + +static inline SC_WireLoad * Abc_SclWireLoadAlloc() +{ + SC_WireLoad * p; + p = ABC_CALLOC( SC_WireLoad, 1 ); + p->vFanout = Vec_IntAlloc( 0 ); + p->vLen = Vec_FltAlloc( 0 ); + return p; +} +static inline SC_WireLoadSel * Abc_SclWireLoadSelAlloc() +{ + SC_WireLoadSel * p; + p = ABC_CALLOC( SC_WireLoadSel, 1 ); + p->vAreaFrom = Vec_FltAlloc( 0 ); + p->vAreaTo = Vec_FltAlloc( 0 ); + p->vWireLoadModel = Vec_PtrAlloc( 0 ); + return p; +} +static inline SC_TableTempl * Abc_SclTableTemplAlloc() +{ + SC_TableTempl * p; + p = ABC_CALLOC( SC_TableTempl, 1 ); + p->vVars = Vec_PtrAlloc( 0 ); + p->vIndex = Vec_PtrAlloc( 0 ); + return p; +} +static inline SC_Surface * Abc_SclSurfaceAlloc() +{ + SC_Surface * p; + p = ABC_CALLOC( SC_Surface, 1 ); + p->vIndex0 = Vec_FltAlloc( 0 ); + p->vIndex1 = Vec_FltAlloc( 0 ); + p->vData = Vec_PtrAlloc( 0 ); + return p; +} +static inline SC_Timing * Abc_SclTimingAlloc() +{ + SC_Timing * p; + p = ABC_CALLOC( SC_Timing, 1 ); + p->pCellRise = Abc_SclSurfaceAlloc(); + p->pCellFall = Abc_SclSurfaceAlloc(); + p->pRiseTrans = Abc_SclSurfaceAlloc(); + p->pFallTrans = Abc_SclSurfaceAlloc(); + return p; +} +static inline SC_Timings * Abc_SclTimingsAlloc() +{ + SC_Timings * p; + p = ABC_CALLOC( SC_Timings, 1 ); + p->vTimings = Vec_PtrAlloc( 0 ); + return p; +} +static inline SC_Pin * Abc_SclPinAlloc() +{ + SC_Pin * p; + p = ABC_CALLOC( SC_Pin, 1 ); + p->max_out_slew = -1; + p->vRTimings = Vec_PtrAlloc( 0 ); + p->vFunc = Vec_WrdAlloc( 0 ); + return p; +} +static inline SC_Cell * Abc_SclCellAlloc() +{ + SC_Cell * p; + p = ABC_CALLOC( SC_Cell, 1 ); + p->vPins = Vec_PtrAlloc( 0 ); + return p; +} +static inline SC_Lib * Abc_SclLibAlloc() +{ + SC_Lib * p; + p = ABC_CALLOC( SC_Lib, 1 ); + p->default_max_out_slew = -1; + p->unit_time = 9; + p->unit_cap_float = 1; + p->unit_cap_int = 12; + p->vWireLoads = Vec_PtrAlloc( 0 ); + p->vWireLoadSels = Vec_PtrAlloc( 0 ); + p->vTempls = Vec_PtrAlloc( 0 ); + p->vCells = Vec_PtrAlloc( 0 ); + return p; +} + + +static inline void Abc_SclWireLoadFree( SC_WireLoad * p ) +{ + Vec_IntFree( p->vFanout ); + Vec_FltFree( p->vLen ); + ABC_FREE( p->name ); + ABC_FREE( p ); +} +static inline void Abc_SclWireLoadSelFree( SC_WireLoadSel * p ) +{ + Vec_FltFree( p->vAreaFrom ); + Vec_FltFree( p->vAreaTo ); + Vec_PtrFreeFree( p->vWireLoadModel ); + ABC_FREE( p->name ); + ABC_FREE( p ); +} +static inline void Abc_SclTableTemplFree( SC_TableTempl * p ) +{ + Vec_PtrFreeFree( p->vVars ); + Vec_VecFree( (Vec_Vec_t *)p->vIndex ); + ABC_FREE( p->name ); + ABC_FREE( p ); +} +static inline void Abc_SclSurfaceFree( SC_Surface * p ) +{ + Vec_FltFree( p->vIndex0 ); + Vec_FltFree( p->vIndex1 ); + Vec_VecFree( (Vec_Vec_t *)p->vData ); + ABC_FREE( p->templ_name ); + ABC_FREE( p ); +} +static inline void Abc_SclTimingFree( SC_Timing * p ) +{ + Abc_SclSurfaceFree( p->pCellRise ); + Abc_SclSurfaceFree( p->pCellFall ); + Abc_SclSurfaceFree( p->pRiseTrans ); + Abc_SclSurfaceFree( p->pFallTrans ); + ABC_FREE( p->related_pin ); + ABC_FREE( p->when_text ); + ABC_FREE( p ); +} +static inline void Abc_SclTimingsFree( SC_Timings * p ) +{ + SC_Timing * pTemp; + int i; + Vec_PtrForEachEntry( SC_Timing *, p->vTimings, pTemp, i ) + Abc_SclTimingFree( pTemp ); + Vec_PtrFree( p->vTimings ); + ABC_FREE( p->name ); + ABC_FREE( p ); +} +static inline void Abc_SclPinFree( SC_Pin * p ) +{ + SC_Timings * pTemp; + int i; + Vec_PtrForEachEntry( SC_Timings *, p->vRTimings, pTemp, i ) + Abc_SclTimingsFree( pTemp ); + Vec_PtrFree( p->vRTimings ); + Vec_WrdFree( p->vFunc ); + ABC_FREE( p->func_text ); + ABC_FREE( p->name ); + ABC_FREE( p ); +} +static inline void Abc_SclCellFree( SC_Cell * p ) +{ + SC_Pin * pTemp; + int i; + Vec_PtrForEachEntry( SC_Pin *, p->vPins, pTemp, i ) + Abc_SclPinFree( pTemp ); + Vec_PtrFree( p->vPins ); + ABC_FREE( p->name ); + ABC_FREE( p ); +} +static inline void Abc_SclLibFree( SC_Lib * p ) +{ + SC_WireLoad * pTemp1; + SC_WireLoadSel * pTemp2; + SC_TableTempl * pTemp3; + SC_Cell * pTemp4; + int i; + Vec_PtrForEachEntry( SC_WireLoad *, p->vWireLoads, pTemp1, i ) + Abc_SclWireLoadFree( pTemp1 ); + Vec_PtrFree( p->vWireLoads ); + Vec_PtrForEachEntry( SC_WireLoadSel *, p->vWireLoadSels, pTemp2, i ) + Abc_SclWireLoadSelFree( pTemp2 ); + Vec_PtrFree( p->vWireLoadSels ); + Vec_PtrForEachEntry( SC_TableTempl *, p->vTempls, pTemp3, i ) + Abc_SclTableTemplFree( pTemp3 ); + Vec_PtrFree( p->vTempls ); + Vec_PtrForEachEntry( SC_Cell *, p->vCells, pTemp4, i ) + Abc_SclCellFree( pTemp4 ); + Vec_PtrFree( p->vCells ); + ABC_FREE( p->lib_name ); + ABC_FREE( p->default_wire_load ); + ABC_FREE( p->default_wire_load_sel ); + ABC_FREE( p ); +} + + +/*=== scl.c =============================================================*/ + + +ABC_NAMESPACE_HEADER_END + +#endif + +//////////////////////////////////////////////////////////////////////// +/// END OF FILE /// +//////////////////////////////////////////////////////////////////////// diff --git a/src/map/scl/sclSize.c b/src/map/scl/sclSize.c new file mode 100644 index 00000000..606ceba5 --- /dev/null +++ b/src/map/scl/sclSize.c @@ -0,0 +1,50 @@ +/**CFile**************************************************************** + + FileName [sclIo.c] + + SystemName [ABC: Logic synthesis and verification system.] + + Synopsis [Standard-cell library representation.] + + Author [Alan Mishchenko, Niklas Een] + + Affiliation [UC Berkeley] + + Date [Ver. 1.0. Started - August 24, 2012.] + + Revision [$Id: sclIo.c,v 1.0 2012/08/24 00:00:00 alanmi Exp $] + +***********************************************************************/ + +#include "sclInt.h" + +ABC_NAMESPACE_IMPL_START + + +//////////////////////////////////////////////////////////////////////// +/// DECLARATIONS /// +//////////////////////////////////////////////////////////////////////// + +//////////////////////////////////////////////////////////////////////// +/// FUNCTION DEFINITIONS /// +//////////////////////////////////////////////////////////////////////// + +/**Function************************************************************* + + Synopsis [] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ + +//////////////////////////////////////////////////////////////////////// +/// END OF FILE /// +//////////////////////////////////////////////////////////////////////// + + +ABC_NAMESPACE_IMPL_END + diff --git a/src/map/scl/sclTime.c b/src/map/scl/sclTime.c new file mode 100644 index 00000000..606ceba5 --- /dev/null +++ b/src/map/scl/sclTime.c @@ -0,0 +1,50 @@ +/**CFile**************************************************************** + + FileName [sclIo.c] + + SystemName [ABC: Logic synthesis and verification system.] + + Synopsis [Standard-cell library representation.] + + Author [Alan Mishchenko, Niklas Een] + + Affiliation [UC Berkeley] + + Date [Ver. 1.0. Started - August 24, 2012.] + + Revision [$Id: sclIo.c,v 1.0 2012/08/24 00:00:00 alanmi Exp $] + +***********************************************************************/ + +#include "sclInt.h" + +ABC_NAMESPACE_IMPL_START + + +//////////////////////////////////////////////////////////////////////// +/// DECLARATIONS /// +//////////////////////////////////////////////////////////////////////// + +//////////////////////////////////////////////////////////////////////// +/// FUNCTION DEFINITIONS /// +//////////////////////////////////////////////////////////////////////// + +/**Function************************************************************* + + Synopsis [] + + Description [] + + SideEffects [] + + SeeAlso [] + +***********************************************************************/ + +//////////////////////////////////////////////////////////////////////// +/// END OF FILE /// +//////////////////////////////////////////////////////////////////////// + + +ABC_NAMESPACE_IMPL_END + -- cgit v1.2.3