mirror of https://github.com/YosysHQ/abc.git
Restructuring gate-sizing code trying to separate timing analysis.
This commit is contained in:
parent
1bdb3773f9
commit
fd28deefc7
12
abclib.dsp
12
abclib.dsp
|
|
@ -2459,11 +2459,11 @@ SOURCE=.\src\map\scl\sclDnsize.c
|
|||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\src\map\scl\sclFile.c
|
||||
SOURCE=.\src\map\scl\sclLib.c
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\src\map\scl\sclInt.h
|
||||
SOURCE=.\src\map\scl\sclLib.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
|
|
@ -2471,11 +2471,15 @@ SOURCE=.\src\map\scl\sclLoad.c
|
|||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\src\map\scl\sclMan.h
|
||||
SOURCE=.\src\map\scl\sclSize.c
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\src\map\scl\sclTime.c
|
||||
SOURCE=.\src\map\scl\sclSize.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\src\map\scl\sclTime.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
|
|
|
|||
|
|
@ -21,7 +21,8 @@
|
|||
#include "mpmInt.h"
|
||||
#include "misc/st/st.h"
|
||||
#include "map/mio/mio.h"
|
||||
#include "map/scl/sclInt.h"
|
||||
#include "map/scl/sclSize.h"
|
||||
#include "map/scl/sclTime.h"
|
||||
|
||||
ABC_NAMESPACE_IMPL_START
|
||||
|
||||
|
|
|
|||
|
|
@ -1,8 +1,8 @@
|
|||
SRC += src/map/scl/scl.c \
|
||||
src/map/scl/sclBuff.c \
|
||||
src/map/scl/sclDnsize.c \
|
||||
src/map/scl/sclFile.c \
|
||||
src/map/scl/sclLib.c \
|
||||
src/map/scl/sclLoad.c \
|
||||
src/map/scl/sclTime.c \
|
||||
src/map/scl/sclSize.c \
|
||||
src/map/scl/sclUpsize.c \
|
||||
src/map/scl/sclUtil.c
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@
|
|||
|
||||
***********************************************************************/
|
||||
|
||||
#include "sclInt.h"
|
||||
#include "sclSize.h"
|
||||
#include "base/main/mainInt.h"
|
||||
|
||||
ABC_NAMESPACE_IMPL_START
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@
|
|||
|
||||
***********************************************************************/
|
||||
|
||||
#include "sclInt.h"
|
||||
#include "sclSize.h"
|
||||
#include "map/mio/mio.h"
|
||||
|
||||
ABC_NAMESPACE_IMPL_START
|
||||
|
|
|
|||
|
|
@ -18,8 +18,7 @@
|
|||
|
||||
***********************************************************************/
|
||||
|
||||
#include "sclInt.h"
|
||||
#include "sclMan.h"
|
||||
#include "sclSize.h"
|
||||
|
||||
ABC_NAMESPACE_IMPL_START
|
||||
|
||||
|
|
|
|||
|
|
@ -1,12 +1,12 @@
|
|||
/**CFile****************************************************************
|
||||
|
||||
FileName [sclFile.c]
|
||||
FileName [sclLib.c]
|
||||
|
||||
SystemName [ABC: Logic synthesis and verification system.]
|
||||
|
||||
PackageName [Standard-cell library representation.]
|
||||
|
||||
Synopsis [Input/output procedures for simplified library representation.]
|
||||
Synopsis [Standard cell library.]
|
||||
|
||||
Author [Alan Mishchenko, Niklas Een]
|
||||
|
||||
|
|
@ -14,12 +14,14 @@
|
|||
|
||||
Date [Ver. 1.0. Started - August 24, 2012.]
|
||||
|
||||
Revision [$Id: sclFile.c,v 1.0 2012/08/24 00:00:00 alanmi Exp $]
|
||||
Revision [$Id: sclLib.c,v 1.0 2012/08/24 00:00:00 alanmi Exp $]
|
||||
|
||||
***********************************************************************/
|
||||
|
||||
#include "sclInt.h"
|
||||
#include "sclLib.h"
|
||||
#include "misc/st/st.h"
|
||||
#include "map/mio/mio.h"
|
||||
#include "bool/kit/kit.h"
|
||||
|
||||
ABC_NAMESPACE_IMPL_START
|
||||
|
||||
|
|
@ -28,8 +30,6 @@ ABC_NAMESPACE_IMPL_START
|
|||
/// DECLARATIONS ///
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
extern void Extra_PrintHex( FILE * pFile, unsigned Sign[], int nBits );
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
/// FUNCTION DEFINITIONS ///
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
|
@ -667,6 +667,234 @@ void Abc_SclWriteText( char * pFileName, SC_Lib * p )
|
|||
}
|
||||
|
||||
|
||||
/**Function*************************************************************
|
||||
|
||||
Synopsis [Reading library from file.]
|
||||
|
||||
Description []
|
||||
|
||||
SideEffects []
|
||||
|
||||
SeeAlso []
|
||||
|
||||
***********************************************************************/
|
||||
static unsigned Abc_SclHashString( char * pName, int TableSize )
|
||||
{
|
||||
static int s_Primes[10] = { 1291, 1699, 2357, 4177, 5147, 5647, 6343, 7103, 7873, 8147 };
|
||||
unsigned i, Key = 0;
|
||||
for ( i = 0; pName[i] != '\0'; i++ )
|
||||
Key += s_Primes[i%10]*pName[i]*pName[i];
|
||||
return Key % TableSize;
|
||||
}
|
||||
int * Abc_SclHashLookup( SC_Lib * p, char * pName )
|
||||
{
|
||||
int i;
|
||||
for ( i = Abc_SclHashString(pName, p->nBins); i < p->nBins; i = (i + 1) % p->nBins )
|
||||
if ( p->pBins[i] == -1 || !strcmp(pName, SC_LibCell(p, p->pBins[i])->pName) )
|
||||
return p->pBins + i;
|
||||
assert( 0 );
|
||||
return NULL;
|
||||
}
|
||||
void Abc_SclHashCells( SC_Lib * p )
|
||||
{
|
||||
SC_Cell * pCell;
|
||||
int i, * pPlace;
|
||||
assert( p->nBins == 0 );
|
||||
p->nBins = Abc_PrimeCudd( 5 * Vec_PtrSize(p->vCells) );
|
||||
p->pBins = ABC_FALLOC( int, p->nBins );
|
||||
SC_LibForEachCell( p, pCell, i )
|
||||
{
|
||||
pPlace = Abc_SclHashLookup( p, pCell->pName );
|
||||
assert( *pPlace == -1 );
|
||||
*pPlace = i;
|
||||
}
|
||||
}
|
||||
int Abc_SclCellFind( SC_Lib * p, char * pName )
|
||||
{
|
||||
return *Abc_SclHashLookup( p, pName );
|
||||
}
|
||||
|
||||
/**Function*************************************************************
|
||||
|
||||
Synopsis [Links equal gates into rings while sorting them by area.]
|
||||
|
||||
Description []
|
||||
|
||||
SideEffects []
|
||||
|
||||
SeeAlso []
|
||||
|
||||
***********************************************************************/
|
||||
static int Abc_SclCompareCells( SC_Cell ** pp1, SC_Cell ** pp2 )
|
||||
{
|
||||
if ( (*pp1)->n_inputs < (*pp2)->n_inputs )
|
||||
return -1;
|
||||
if ( (*pp1)->n_inputs > (*pp2)->n_inputs )
|
||||
return 1;
|
||||
if ( (*pp1)->area < (*pp2)->area )
|
||||
return -1;
|
||||
if ( (*pp1)->area > (*pp2)->area )
|
||||
return 1;
|
||||
return strcmp( (*pp1)->pName, (*pp2)->pName );
|
||||
}
|
||||
void Abc_SclLinkCells( SC_Lib * p )
|
||||
{
|
||||
SC_Cell * pCell, * pRepr = NULL;
|
||||
int i, k;
|
||||
assert( Vec_PtrSize(p->vCellClasses) == 0 );
|
||||
SC_LibForEachCell( p, pCell, i )
|
||||
{
|
||||
// find gate with the same function
|
||||
SC_LibForEachCellClass( p, pRepr, k )
|
||||
if ( pCell->n_inputs == pRepr->n_inputs &&
|
||||
pCell->n_outputs == pRepr->n_outputs &&
|
||||
Vec_WrdEqual(SC_CellFunc(pCell), SC_CellFunc(pRepr)) )
|
||||
break;
|
||||
if ( k == Vec_PtrSize(p->vCellClasses) )
|
||||
{
|
||||
Vec_PtrPush( p->vCellClasses, pCell );
|
||||
pCell->pNext = pCell->pPrev = pCell;
|
||||
continue;
|
||||
}
|
||||
// add it to the list before the cell
|
||||
pRepr->pPrev->pNext = pCell; pCell->pNext = pRepr;
|
||||
pCell->pPrev = pRepr->pPrev; pRepr->pPrev = pCell;
|
||||
}
|
||||
// sort cells by size the then by name
|
||||
qsort( (void *)Vec_PtrArray(p->vCellClasses), Vec_PtrSize(p->vCellClasses), sizeof(void *), (int(*)(const void *,const void *))Abc_SclCompareCells );
|
||||
// sort cell lists
|
||||
SC_LibForEachCellClass( p, pRepr, k )
|
||||
{
|
||||
Vec_Ptr_t * vList = Vec_PtrAlloc( 100 );
|
||||
SC_RingForEachCell( pRepr, pCell, i )
|
||||
Vec_PtrPush( vList, pCell );
|
||||
qsort( (void *)Vec_PtrArray(vList), Vec_PtrSize(vList), sizeof(void *), (int(*)(const void *,const void *))Abc_SclCompareCells );
|
||||
// create new representative
|
||||
pRepr = (SC_Cell *)Vec_PtrEntry( vList, 0 );
|
||||
pRepr->pNext = pRepr->pPrev = pRepr;
|
||||
pRepr->Order = 0;
|
||||
// relink cells
|
||||
Vec_PtrForEachEntryStart( SC_Cell *, vList, pCell, i, 1 )
|
||||
{
|
||||
pRepr->pPrev->pNext = pCell; pCell->pNext = pRepr;
|
||||
pCell->pPrev = pRepr->pPrev; pRepr->pPrev = pCell;
|
||||
pCell->Order = i;
|
||||
}
|
||||
// update list
|
||||
Vec_PtrWriteEntry( p->vCellClasses, k, pRepr );
|
||||
Vec_PtrFree( vList );
|
||||
}
|
||||
}
|
||||
void Abc_SclPrintCells( SC_Lib * p )
|
||||
{
|
||||
SC_Cell * pCell, * pRepr;
|
||||
int i, k, j, nLength = 0;
|
||||
assert( Vec_PtrSize(p->vCellClasses) > 0 );
|
||||
printf( "Library \"%s\" ", p->pName );
|
||||
printf( "containing %d cells in %d classes.\n",
|
||||
Vec_PtrSize(p->vCells), Vec_PtrSize(p->vCellClasses) );
|
||||
// find the longest name
|
||||
SC_LibForEachCellClass( p, pRepr, k )
|
||||
SC_RingForEachCell( pRepr, pCell, i )
|
||||
nLength = Abc_MaxInt( nLength, strlen(pRepr->pName) );
|
||||
// print cells
|
||||
SC_LibForEachCellClass( p, pRepr, k )
|
||||
{
|
||||
printf( "Class%3d : ", k );
|
||||
printf( "Ins = %d ", pRepr->n_inputs );
|
||||
printf( "Outs = %d", pRepr->n_outputs );
|
||||
for ( i = 0; i < pRepr->n_outputs; i++ )
|
||||
{
|
||||
printf( " " );
|
||||
Kit_DsdPrintFromTruth( (unsigned *)Vec_WrdArray(SC_CellPin(pRepr, pRepr->n_inputs+i)->vFunc), pRepr->n_inputs );
|
||||
}
|
||||
printf( "\n" );
|
||||
SC_RingForEachCell( pRepr, pCell, i )
|
||||
{
|
||||
printf( " %3d : ", i+1 );
|
||||
printf( "%-*s ", nLength, pCell->pName );
|
||||
printf( "%2d ", pCell->drive_strength );
|
||||
printf( "A =%8.2f D =", pCell->area );
|
||||
// print linear approximation
|
||||
for ( j = 0; j < 3; j++ )
|
||||
{
|
||||
SC_Pin * pPin = SC_CellPin( pCell, pCell->n_inputs );
|
||||
if ( Vec_PtrSize(pPin->vRTimings) > 0 )
|
||||
{
|
||||
SC_Timings * pRTime = (SC_Timings *)Vec_PtrEntry( pPin->vRTimings, 0 );
|
||||
SC_Timing * pTime = (SC_Timing *)Vec_PtrEntry( pRTime->vTimings, 0 );
|
||||
printf( " %6.2f", j ? pTime->pCellRise->approx[0][j] : SC_LibTimePs(p, pTime->pCellRise->approx[0][j]) );
|
||||
}
|
||||
}
|
||||
// print input capacitance
|
||||
printf( " Cap =" );
|
||||
for ( j = 0; j < pCell->n_inputs; j++ )
|
||||
{
|
||||
SC_Pin * pPin = SC_CellPin( pCell, j );
|
||||
printf( " %6.2f", SC_LibCapFf(p, pPin->rise_cap) );
|
||||
}
|
||||
printf( "\n" );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**Function*************************************************************
|
||||
|
||||
Synopsis [Returns the wireload model for the given area.]
|
||||
|
||||
Description []
|
||||
|
||||
SideEffects []
|
||||
|
||||
SeeAlso []
|
||||
|
||||
***********************************************************************/
|
||||
SC_WireLoad * Abc_SclFindWireLoadModel( SC_Lib * p, float Area )
|
||||
{
|
||||
SC_WireLoad * pWL = NULL;
|
||||
char * pWLoadUsed = NULL;
|
||||
int i;
|
||||
if ( p->default_wire_load_sel && strlen(p->default_wire_load_sel) )
|
||||
{
|
||||
SC_WireLoadSel * pWLS = NULL;
|
||||
SC_LibForEachWireLoadSel( p, pWLS, i )
|
||||
if ( !strcmp(pWLS->pName, p->default_wire_load_sel) )
|
||||
break;
|
||||
if ( i == Vec_PtrSize(p->vWireLoadSels) )
|
||||
{
|
||||
Abc_Print( -1, "Cannot find wire load selection model \"%s\".\n", p->default_wire_load_sel );
|
||||
exit(1);
|
||||
}
|
||||
for ( i = 0; i < Vec_FltSize(pWLS->vAreaFrom); i++)
|
||||
if ( Area >= Vec_FltEntry(pWLS->vAreaFrom, i) && Area < Vec_FltEntry(pWLS->vAreaTo, i) )
|
||||
{
|
||||
pWLoadUsed = (char *)Vec_PtrEntry(pWLS->vWireLoadModel, i);
|
||||
break;
|
||||
}
|
||||
if ( i == Vec_FltSize(pWLS->vAreaFrom) )
|
||||
pWLoadUsed = (char *)Vec_PtrEntryLast(pWLS->vWireLoadModel);
|
||||
}
|
||||
else if ( p->default_wire_load && strlen(p->default_wire_load) )
|
||||
pWLoadUsed = p->default_wire_load;
|
||||
else
|
||||
{
|
||||
Abc_Print( 0, "No wire model given.\n" );
|
||||
return NULL;
|
||||
}
|
||||
// Get the actual table and reformat it for 'wire_cap' output:
|
||||
assert( pWLoadUsed != NULL );
|
||||
SC_LibForEachWireLoad( p, pWL, i )
|
||||
if ( !strcmp(pWL->pName, pWLoadUsed) )
|
||||
break;
|
||||
if ( i == Vec_PtrSize(p->vWireLoads) )
|
||||
{
|
||||
Abc_Print( -1, "Cannot find wire load model \"%s\".\n", pWLoadUsed );
|
||||
exit(1);
|
||||
}
|
||||
// printf( "Using wireload model \"%s\".\n", pWL->pName );
|
||||
return pWL;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
/// END OF FILE ///
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
|
@ -1,6 +1,6 @@
|
|||
/**CFile****************************************************************
|
||||
|
||||
FileName [sclInt.h]
|
||||
FileName [sclLib.h]
|
||||
|
||||
SystemName [ABC: Logic synthesis and verification system.]
|
||||
|
||||
|
|
@ -14,12 +14,12 @@
|
|||
|
||||
Date [Ver. 1.0. Started - August 24, 2012.]
|
||||
|
||||
Revision [$Id: sclInt.h,v 1.0 2012/08/24 00:00:00 alanmi Exp $]
|
||||
Revision [$Id: sclLib.h,v 1.0 2012/08/24 00:00:00 alanmi Exp $]
|
||||
|
||||
***********************************************************************/
|
||||
|
||||
#ifndef ABC__map__scl__sclInt_h
|
||||
#define ABC__map__scl__sclInt_h
|
||||
#ifndef ABC__map__scl__sclLib_h
|
||||
#define ABC__map__scl__sclLib_h
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
|
@ -31,8 +31,7 @@
|
|||
#include <string.h>
|
||||
#include <assert.h>
|
||||
#include <math.h>
|
||||
|
||||
#include "base/abc/abc.h"
|
||||
#include "misc/vec/vec.h"
|
||||
|
||||
ABC_NAMESPACE_HEADER_START
|
||||
|
||||
|
|
@ -78,6 +77,13 @@ struct SC_SizePars_
|
|||
int fVeryVerbose;
|
||||
};
|
||||
|
||||
typedef struct SC_Pair_ SC_Pair;
|
||||
struct SC_Pair_
|
||||
{
|
||||
float rise;
|
||||
float fall;
|
||||
};
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
/// STRUCTURE DEFINITIONS ///
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
|
@ -430,33 +436,17 @@ static inline void Abc_SclLibFree( SC_Lib * p )
|
|||
}
|
||||
|
||||
|
||||
/*=== sclBuff.c ===============================================================*/
|
||||
extern int Abc_SclCheckNtk( Abc_Ntk_t * p, int fVerbose );
|
||||
extern Abc_Ntk_t * Abc_SclPerformBuffering( Abc_Ntk_t * p, int Degree, int fVerbose );
|
||||
/*=== sclDnsize.c ===============================================================*/
|
||||
extern void Abc_SclDnsizePerform( SC_Lib * pLib, Abc_Ntk_t * pNtk, SC_SizePars * pPars );
|
||||
/*=== sclFile.c ===============================================================*/
|
||||
/*=== sclLib.c ===============================================================*/
|
||||
extern SC_Lib * Abc_SclRead( char * pFileName );
|
||||
extern void Abc_SclWrite( char * pFileName, SC_Lib * p );
|
||||
extern void Abc_SclWriteText( char * pFileName, SC_Lib * p );
|
||||
extern void Abc_SclLoad( char * pFileName, SC_Lib ** ppScl );
|
||||
extern void Abc_SclSave( char * pFileName, SC_Lib * pScl );
|
||||
/*=== sclLoad.c ===============================================================*/
|
||||
extern SC_WireLoad * Abc_SclFindWireLoadModel( SC_Lib * p, float Area );
|
||||
/*=== sclTime.c ===============================================================*/
|
||||
extern void Abc_SclTimePerform( SC_Lib * pLib, Abc_Ntk_t * pNtk, int fUseWireLoads, int fShowAll, int fShort, int fDumpStats );
|
||||
extern void Abc_SclPrintBuffers( SC_Lib * pLib, Abc_Ntk_t * pNtk, int fVerbose );
|
||||
/*=== sclUpsize.c ===============================================================*/
|
||||
extern void Abc_SclUpsizePerform( SC_Lib * pLib, Abc_Ntk_t * pNtk, SC_SizePars * pPars );
|
||||
/*=== sclUtil.c ===============================================================*/
|
||||
extern void Abc_SclHashCells( SC_Lib * p );
|
||||
extern int Abc_SclCellFind( SC_Lib * p, char * pName );
|
||||
extern void Abc_SclLinkCells( SC_Lib * p );
|
||||
extern void Abc_SclPrintCells( SC_Lib * p );
|
||||
extern Vec_Int_t * Abc_SclManFindGates( SC_Lib * pLib, Abc_Ntk_t * p );
|
||||
extern void Abc_SclManSetGates( SC_Lib * pLib, Abc_Ntk_t * p, Vec_Int_t * vGates );
|
||||
extern void Abc_SclPrintGateSizes( SC_Lib * pLib, Abc_Ntk_t * p );
|
||||
extern void Abc_SclMinsizePerform( SC_Lib * pLib, Abc_Ntk_t * p, int fUseMax, int fVerbose );
|
||||
extern SC_WireLoad * Abc_SclFindWireLoadModel( SC_Lib * p, float Area );
|
||||
|
||||
|
||||
ABC_NAMESPACE_HEADER_END
|
||||
|
|
@ -18,8 +18,7 @@
|
|||
|
||||
***********************************************************************/
|
||||
|
||||
#include "sclInt.h"
|
||||
#include "sclMan.h"
|
||||
#include "sclSize.h"
|
||||
|
||||
ABC_NAMESPACE_IMPL_START
|
||||
|
||||
|
|
@ -32,63 +31,6 @@ ABC_NAMESPACE_IMPL_START
|
|||
/// FUNCTION DEFINITIONS ///
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/**Function*************************************************************
|
||||
|
||||
Synopsis [Returns the wireload model for the given area.]
|
||||
|
||||
Description []
|
||||
|
||||
SideEffects []
|
||||
|
||||
SeeAlso []
|
||||
|
||||
***********************************************************************/
|
||||
SC_WireLoad * Abc_SclFindWireLoadModel( SC_Lib * p, float Area )
|
||||
{
|
||||
SC_WireLoad * pWL = NULL;
|
||||
char * pWLoadUsed = NULL;
|
||||
int i;
|
||||
if ( p->default_wire_load_sel && strlen(p->default_wire_load_sel) )
|
||||
{
|
||||
SC_WireLoadSel * pWLS = NULL;
|
||||
SC_LibForEachWireLoadSel( p, pWLS, i )
|
||||
if ( !strcmp(pWLS->pName, p->default_wire_load_sel) )
|
||||
break;
|
||||
if ( i == Vec_PtrSize(p->vWireLoadSels) )
|
||||
{
|
||||
Abc_Print( -1, "Cannot find wire load selection model \"%s\".\n", p->default_wire_load_sel );
|
||||
exit(1);
|
||||
}
|
||||
for ( i = 0; i < Vec_FltSize(pWLS->vAreaFrom); i++)
|
||||
if ( Area >= Vec_FltEntry(pWLS->vAreaFrom, i) && Area < Vec_FltEntry(pWLS->vAreaTo, i) )
|
||||
{
|
||||
pWLoadUsed = (char *)Vec_PtrEntry(pWLS->vWireLoadModel, i);
|
||||
break;
|
||||
}
|
||||
if ( i == Vec_FltSize(pWLS->vAreaFrom) )
|
||||
pWLoadUsed = (char *)Vec_PtrEntryLast(pWLS->vWireLoadModel);
|
||||
}
|
||||
else if ( p->default_wire_load && strlen(p->default_wire_load) )
|
||||
pWLoadUsed = p->default_wire_load;
|
||||
else
|
||||
{
|
||||
Abc_Print( 0, "No wire model given.\n" );
|
||||
return NULL;
|
||||
}
|
||||
// Get the actual table and reformat it for 'wire_cap' output:
|
||||
assert( pWLoadUsed != NULL );
|
||||
SC_LibForEachWireLoad( p, pWL, i )
|
||||
if ( !strcmp(pWL->pName, pWLoadUsed) )
|
||||
break;
|
||||
if ( i == Vec_PtrSize(p->vWireLoads) )
|
||||
{
|
||||
Abc_Print( -1, "Cannot find wire load model \"%s\".\n", pWLoadUsed );
|
||||
exit(1);
|
||||
}
|
||||
// printf( "Using wireload model \"%s\".\n", pWL->pName );
|
||||
return pWL;
|
||||
}
|
||||
|
||||
/**Function*************************************************************
|
||||
|
||||
Synopsis [Returns estimated wire capacitances for each fanout count.]
|
||||
|
|
|
|||
|
|
@ -1,12 +1,12 @@
|
|||
/**CFile****************************************************************
|
||||
|
||||
FileName [sclTime.c]
|
||||
FileName [sclSize.c]
|
||||
|
||||
SystemName [ABC: Logic synthesis and verification system.]
|
||||
|
||||
PackageName [Standard-cell library representation.]
|
||||
|
||||
Synopsis [Static timing analysis using Liberty delay model.]
|
||||
Synopsis [Core timing analysis used in gate-sizing.]
|
||||
|
||||
Author [Alan Mishchenko, Niklas Een]
|
||||
|
||||
|
|
@ -14,12 +14,11 @@
|
|||
|
||||
Date [Ver. 1.0. Started - August 24, 2012.]
|
||||
|
||||
Revision [$Id: sclTime.c,v 1.0 2012/08/24 00:00:00 alanmi Exp $]
|
||||
Revision [$Id: sclSize.c,v 1.0 2012/08/24 00:00:00 alanmi Exp $]
|
||||
|
||||
***********************************************************************/
|
||||
|
||||
#include "sclInt.h"
|
||||
#include "sclMan.h"
|
||||
#include "sclSize.h"
|
||||
#include "map/mio/mio.h"
|
||||
|
||||
ABC_NAMESPACE_IMPL_START
|
||||
|
|
@ -1,6 +1,6 @@
|
|||
/**CFile****************************************************************
|
||||
|
||||
FileName [sclMan.h]
|
||||
FileName [sclSize.h]
|
||||
|
||||
SystemName [ABC: Logic synthesis and verification system.]
|
||||
|
||||
|
|
@ -14,19 +14,21 @@
|
|||
|
||||
Date [Ver. 1.0. Started - August 24, 2012.]
|
||||
|
||||
Revision [$Id: sclMan.h,v 1.0 2012/08/24 00:00:00 alanmi Exp $]
|
||||
Revision [$Id: sclSize.h,v 1.0 2012/08/24 00:00:00 alanmi Exp $]
|
||||
|
||||
***********************************************************************/
|
||||
|
||||
#ifndef ABC__map__scl__sclMan_h
|
||||
#define ABC__map__scl__sclMan_h
|
||||
#ifndef ABC__map__scl__sclSize_h
|
||||
#define ABC__map__scl__sclSize_h
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
/// INCLUDES ///
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#include "base/abc/abc.h"
|
||||
#include "misc/vec/vecQue.h"
|
||||
#include "sclLib.h"
|
||||
|
||||
ABC_NAMESPACE_HEADER_START
|
||||
|
||||
|
|
@ -38,15 +40,7 @@ ABC_NAMESPACE_HEADER_START
|
|||
/// STRUCTURE DEFINITIONS ///
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
typedef struct SC_Pair_ SC_Pair;
|
||||
typedef struct SC_Man_ SC_Man;
|
||||
|
||||
struct SC_Pair_
|
||||
{
|
||||
float rise;
|
||||
float fall;
|
||||
};
|
||||
|
||||
struct SC_Man_
|
||||
{
|
||||
SC_Lib * pLib; // library
|
||||
|
|
@ -376,16 +370,30 @@ static inline void Abc_SclDumpStats( SC_Man * p, char * pFileName, abctime Time
|
|||
}
|
||||
|
||||
|
||||
/*=== sclTime.c =============================================================*/
|
||||
extern Abc_Obj_t * Abc_SclFindCriticalCo( SC_Man * p, int * pfRise );
|
||||
extern Abc_Obj_t * Abc_SclFindMostCriticalFanin( SC_Man * p, int * pfRise, Abc_Obj_t * pNode );
|
||||
extern void Abc_SclTimeNtkPrint( SC_Man * p, int fShowAll, int fShort );
|
||||
extern SC_Man * Abc_SclManStart( SC_Lib * pLib, Abc_Ntk_t * pNtk, int fUseWireLoads, int fDept, float DUser );
|
||||
extern void Abc_SclTimeCone( SC_Man * p, Vec_Int_t * vCone );
|
||||
extern void Abc_SclTimeNtkRecompute( SC_Man * p, float * pArea, float * pDelay, int fReverse, float DUser );
|
||||
/*=== sclTime.c =============================================================*/
|
||||
extern void Abc_SclComputeLoad( SC_Man * p );
|
||||
extern void Abc_SclUpdateLoad( SC_Man * p, Abc_Obj_t * pObj, SC_Cell * pOld, SC_Cell * pNew );
|
||||
/*=== sclBuff.c ===============================================================*/
|
||||
extern int Abc_SclCheckNtk( Abc_Ntk_t * p, int fVerbose );
|
||||
extern Abc_Ntk_t * Abc_SclPerformBuffering( Abc_Ntk_t * p, int Degree, int fVerbose );
|
||||
/*=== sclDnsize.c ===============================================================*/
|
||||
extern void Abc_SclDnsizePerform( SC_Lib * pLib, Abc_Ntk_t * pNtk, SC_SizePars * pPars );
|
||||
/*=== sclLoad.c ===============================================================*/
|
||||
extern void Abc_SclComputeLoad( SC_Man * p );
|
||||
extern void Abc_SclUpdateLoad( SC_Man * p, Abc_Obj_t * pObj, SC_Cell * pOld, SC_Cell * pNew );
|
||||
/*=== sclSize.c ===============================================================*/
|
||||
extern Abc_Obj_t * Abc_SclFindCriticalCo( SC_Man * p, int * pfRise );
|
||||
extern Abc_Obj_t * Abc_SclFindMostCriticalFanin( SC_Man * p, int * pfRise, Abc_Obj_t * pNode );
|
||||
extern void Abc_SclTimeNtkPrint( SC_Man * p, int fShowAll, int fShort );
|
||||
extern SC_Man * Abc_SclManStart( SC_Lib * pLib, Abc_Ntk_t * pNtk, int fUseWireLoads, int fDept, float DUser );
|
||||
extern void Abc_SclTimeCone( SC_Man * p, Vec_Int_t * vCone );
|
||||
extern void Abc_SclTimeNtkRecompute( SC_Man * p, float * pArea, float * pDelay, int fReverse, float DUser );
|
||||
extern void Abc_SclTimePerform( SC_Lib * pLib, Abc_Ntk_t * pNtk, int fUseWireLoads, int fShowAll, int fShort, int fDumpStats );
|
||||
extern void Abc_SclPrintBuffers( SC_Lib * pLib, Abc_Ntk_t * pNtk, int fVerbose );
|
||||
/*=== sclUpsize.c ===============================================================*/
|
||||
extern void Abc_SclUpsizePerform( SC_Lib * pLib, Abc_Ntk_t * pNtk, SC_SizePars * pPars );
|
||||
/*=== sclUtil.c ===============================================================*/
|
||||
extern Vec_Int_t * Abc_SclManFindGates( SC_Lib * pLib, Abc_Ntk_t * p );
|
||||
extern void Abc_SclManSetGates( SC_Lib * pLib, Abc_Ntk_t * p, Vec_Int_t * vGates );
|
||||
extern void Abc_SclPrintGateSizes( SC_Lib * pLib, Abc_Ntk_t * p );
|
||||
extern void Abc_SclMinsizePerform( SC_Lib * pLib, Abc_Ntk_t * p, int fUseMax, int fVerbose );
|
||||
|
||||
|
||||
ABC_NAMESPACE_HEADER_END
|
||||
|
|
@ -0,0 +1,288 @@
|
|||
/**CFile****************************************************************
|
||||
|
||||
FileName [sclTime.h]
|
||||
|
||||
SystemName [ABC: Logic synthesis and verification system.]
|
||||
|
||||
PackageName [Standard-cell library representation.]
|
||||
|
||||
Synopsis [Timing/gate-sizing manager.]
|
||||
|
||||
Author [Alan Mishchenko, Niklas Een]
|
||||
|
||||
Affiliation [UC Berkeley]
|
||||
|
||||
Date [Ver. 1.0. Started - August 24, 2012.]
|
||||
|
||||
Revision [$Id: sclTime.h,v 1.0 2012/08/24 00:00:00 alanmi Exp $]
|
||||
|
||||
***********************************************************************/
|
||||
|
||||
#ifndef ABC__map__scl__sclTime_h
|
||||
#define ABC__map__scl__sclTime_h
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
/// INCLUDES ///
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#include "misc/vec/vec.h"
|
||||
#include "sclLib.h"
|
||||
|
||||
ABC_NAMESPACE_HEADER_START
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
/// PARAMETERS ///
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
/// STRUCTURE DEFINITIONS ///
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
typedef struct SC_Time_ SC_Time;
|
||||
struct SC_Time_
|
||||
{
|
||||
SC_Lib * pLib; // library
|
||||
Vec_Int_t * vCis; // comb inputs
|
||||
Vec_Int_t * vCos; // comb outputs
|
||||
int nObjs; // allocated size
|
||||
// get assignment
|
||||
Vec_Int_t * vGates; // mapping of objId into gateId
|
||||
// timing information
|
||||
SC_Pair * pLoads; // loads for each gate
|
||||
SC_Pair * pLoads2; // loads for each gate
|
||||
SC_Pair * pDepts; // departures for each gate
|
||||
SC_Pair * pTimes; // arrivals for each gate
|
||||
SC_Pair * pSlews; // slews for each gate
|
||||
SC_Pair * pTimes2; // arrivals for each gate
|
||||
SC_Pair * pSlews2; // slews for each gate
|
||||
float * pSlack; // slacks for each gate
|
||||
SC_WireLoad * pWLoadUsed; // name of the used WireLoad model
|
||||
// optimization parameters
|
||||
float SumArea; // total area
|
||||
float MaxDelay; // max delay
|
||||
float SumArea0; // total area at the begining
|
||||
float MaxDelay0; // max delay at the begining
|
||||
float BestDelay; // best delay in the middle
|
||||
};
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
/// GLOBAL VARIABLES ///
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
/// MACRO DEFINITIONS ///
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static inline SC_Cell * Scl_ObjCell( SC_Time * p, int i ) { return SC_LibCell( p->pLib, Vec_IntEntry(p->vGates, i) ); }
|
||||
static inline void Scl_ObjSetCell( SC_Time * p, int i, SC_Cell * pCell ) { Vec_IntWriteEntry( p->vGates, i, pCell->Id ); }
|
||||
|
||||
static inline SC_Pair * Scl_ObjLoad( SC_Time * p, int i ) { return p->pLoads + i; }
|
||||
static inline SC_Pair * Scl_ObjLoad2( SC_Time * p, int i ) { return p->pLoads2 + i; }
|
||||
static inline SC_Pair * Scl_ObjDept( SC_Time * p, int i ) { return p->pDepts + i; }
|
||||
static inline SC_Pair * Scl_ObjTime( SC_Time * p, int i ) { return p->pTimes + i; }
|
||||
static inline SC_Pair * Scl_ObjSlew( SC_Time * p, int i ) { return p->pSlews + i; }
|
||||
static inline SC_Pair * Scl_ObjTime2( SC_Time * p, int i ) { return p->pTimes2 + i; }
|
||||
static inline SC_Pair * Scl_ObjSlew2( SC_Time * p, int i ) { return p->pSlews2 + i; }
|
||||
|
||||
static inline float Scl_ObjTimeMax( SC_Time * p, int i ) { return Abc_MaxFloat(Scl_ObjTime(p, i)->rise, Scl_ObjTime(p, i)->fall); }
|
||||
static inline float Scl_ObjDepthMax( SC_Time * p, int i ) { return Abc_MaxFloat(Scl_ObjDept(p, i)->rise, Scl_ObjDept(p, i)->fall); }
|
||||
static inline float Scl_ObjGetSlack( SC_Time * p, int i, float D ) { return D - Abc_MaxFloat(Scl_ObjTime(p, i)->rise + Scl_ObjDept(p, i)->rise, Scl_ObjTime(p, i)->fall + Scl_ObjDept(p, i)->fall); }
|
||||
static inline float Scl_ObjGetSlackR( SC_Time * p, int i, float D ) { return D - (Scl_ObjTime(p, i)->rise + Scl_ObjDept(p, i)->rise); }
|
||||
static inline float Scl_ObjGetSlackF( SC_Time * p, int i, float D ) { return D - (Scl_ObjTime(p, i)->fall + Scl_ObjDept(p, i)->fall); }
|
||||
static inline float Scl_ObjSlack( SC_Time * p, int i ) { return p->pSlack[i]; }
|
||||
|
||||
static inline void Scl_ObjDupFanin( SC_Time * p, int i, int iFanin ) { *Scl_ObjTime(p, i) = *Scl_ObjTime(p, iFanin); }
|
||||
static inline float Scl_ObjGain( SC_Time * p, int i ) { return 0.5*((Scl_ObjTime2(p, i)->rise - Scl_ObjTime(p, i)->rise) + (Scl_ObjTime2(p, i)->fall - Scl_ObjTime(p, i)->fall)); }
|
||||
static inline int Scl_ObjLegal( SC_Time * p, int i, float D ) { return Scl_ObjTime(p, i)->rise <= Scl_ObjTime2(p, i)->rise + Scl_ObjGetSlackR(p, i, D) && Scl_ObjTime(p, i)->fall <= Scl_ObjTime2(p, i)->fall + Scl_ObjGetSlackF(p, i, D); }
|
||||
|
||||
static inline double Scl_ObjLoadFf( SC_Time * p, int i, int fRise ) { return SC_LibCapFf( p->pLib, fRise ? Scl_ObjLoad(p, i)->rise : Scl_ObjLoad(p, i)->fall); }
|
||||
static inline double Scl_ObjTimePs( SC_Time * p, int i, int fRise ) { return SC_LibTimePs(p->pLib, fRise ? Scl_ObjTime(p, i)->rise : Scl_ObjTime(p, i)->fall); }
|
||||
static inline double Scl_ObjSlewPs( SC_Time * p, int i, int fRise ) { return SC_LibTimePs(p->pLib, fRise ? Scl_ObjSlew(p, i)->rise : Scl_ObjSlew(p, i)->fall); }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
/// FUNCTION DEFINITIONS ///
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/**Function*************************************************************
|
||||
|
||||
Synopsis [Constructor/destructor of STA manager.]
|
||||
|
||||
Description []
|
||||
|
||||
SideEffects []
|
||||
|
||||
SeeAlso []
|
||||
|
||||
***********************************************************************/
|
||||
static inline SC_Time * Scl_ManAlloc( SC_Lib * pLib, Vec_Int_t * vCis, Vec_Int_t * vCos, int nObjs )
|
||||
{
|
||||
SC_Time * p;
|
||||
p = ABC_CALLOC( SC_Time, 1 );
|
||||
p->pLib = pLib;
|
||||
p->vCis = vCis;
|
||||
p->vCos = vCos;
|
||||
p->nObjs = nObjs;
|
||||
p->pLoads = ABC_CALLOC( SC_Pair, p->nObjs );
|
||||
p->pLoads2 = ABC_CALLOC( SC_Pair, p->nObjs );
|
||||
p->pDepts = ABC_CALLOC( SC_Pair, p->nObjs );
|
||||
p->pTimes = ABC_CALLOC( SC_Pair, p->nObjs );
|
||||
p->pSlews = ABC_CALLOC( SC_Pair, p->nObjs );
|
||||
p->pTimes2 = ABC_CALLOC( SC_Pair, p->nObjs );
|
||||
p->pSlews2 = ABC_CALLOC( SC_Pair, p->nObjs );
|
||||
p->pSlack = ABC_FALLOC( float, p->nObjs );
|
||||
return p;
|
||||
}
|
||||
static inline void Scl_ManFree( SC_Time * p )
|
||||
{
|
||||
Vec_IntFreeP( &p->vGates );
|
||||
ABC_FREE( p->pLoads );
|
||||
ABC_FREE( p->pLoads2 );
|
||||
ABC_FREE( p->pDepts );
|
||||
ABC_FREE( p->pTimes );
|
||||
ABC_FREE( p->pSlews );
|
||||
ABC_FREE( p->pTimes2 );
|
||||
ABC_FREE( p->pSlews2 );
|
||||
ABC_FREE( p->pSlack );
|
||||
ABC_FREE( p );
|
||||
}
|
||||
static inline void Scl_ManCleanTime( SC_Time * p )
|
||||
{
|
||||
memset( p->pDepts, 0, sizeof(SC_Pair) * p->nObjs );
|
||||
memset( p->pTimes, 0, sizeof(SC_Pair) * p->nObjs );
|
||||
memset( p->pSlews, 0, sizeof(SC_Pair) * p->nObjs );
|
||||
}
|
||||
|
||||
|
||||
/**Function*************************************************************
|
||||
|
||||
Synopsis [Stores/retrieves timing information for the logic cone.]
|
||||
|
||||
Description []
|
||||
|
||||
SideEffects []
|
||||
|
||||
SeeAlso []
|
||||
|
||||
***********************************************************************/
|
||||
static inline void Scl_ConeStore( SC_Time * p, Vec_Int_t * vCone )
|
||||
{
|
||||
int i, iObj;
|
||||
Vec_IntForEachEntry( vCone, iObj, i )
|
||||
{
|
||||
*Scl_ObjTime2(p, iObj) = *Scl_ObjTime(p, iObj);
|
||||
*Scl_ObjSlew2(p, iObj) = *Scl_ObjSlew(p, iObj);
|
||||
}
|
||||
}
|
||||
static inline void Scl_ConeRestore( SC_Time * p, Vec_Int_t * vCone )
|
||||
{
|
||||
int i, iObj;
|
||||
Vec_IntForEachEntry( vCone, iObj, i )
|
||||
{
|
||||
*Scl_ObjTime(p, iObj) = *Scl_ObjTime2(p, iObj);
|
||||
*Scl_ObjSlew(p, iObj) = *Scl_ObjSlew2(p, iObj);
|
||||
}
|
||||
}
|
||||
static inline void Scl_ConeClear( SC_Time * p, Vec_Int_t * vCone )
|
||||
{
|
||||
SC_Pair Zero = { 0.0, 0.0 };
|
||||
int i, iObj;
|
||||
Vec_IntForEachEntry( vCone, iObj, i )
|
||||
{
|
||||
*Scl_ObjTime(p, iObj) = Zero;
|
||||
*Scl_ObjSlew(p, iObj) = Zero;
|
||||
}
|
||||
}
|
||||
|
||||
/**Function*************************************************************
|
||||
|
||||
Synopsis [Timing computation for pin/gate/cone/network.]
|
||||
|
||||
Description []
|
||||
|
||||
SideEffects []
|
||||
|
||||
SeeAlso []
|
||||
|
||||
***********************************************************************/
|
||||
static inline float Scl_Lookup( SC_Surface * p, float slew, float load )
|
||||
{
|
||||
float * pIndex0, * pIndex1, * pDataS, * pDataS1;
|
||||
float sfrac, lfrac, p0, p1;
|
||||
int s, l;
|
||||
|
||||
// Find closest sample points in surface:
|
||||
pIndex0 = Vec_FltArray(p->vIndex0);
|
||||
for ( s = 1; s < Vec_FltSize(p->vIndex0)-1; s++ )
|
||||
if ( pIndex0[s] > slew )
|
||||
break;
|
||||
s--;
|
||||
|
||||
pIndex1 = Vec_FltArray(p->vIndex1);
|
||||
for ( l = 1; l < Vec_FltSize(p->vIndex1)-1; l++ )
|
||||
if ( pIndex1[l] > load )
|
||||
break;
|
||||
l--;
|
||||
|
||||
// Interpolate (or extrapolate) function value from sample points:
|
||||
sfrac = (slew - pIndex0[s]) / (pIndex0[s+1] - pIndex0[s]);
|
||||
lfrac = (load - pIndex1[l]) / (pIndex1[l+1] - pIndex1[l]);
|
||||
|
||||
pDataS = Vec_FltArray( (Vec_Flt_t *)Vec_PtrEntry(p->vData, s) );
|
||||
pDataS1 = Vec_FltArray( (Vec_Flt_t *)Vec_PtrEntry(p->vData, s+1) );
|
||||
|
||||
p0 = pDataS [l] + lfrac * (pDataS [l+1] - pDataS [l]);
|
||||
p1 = pDataS1[l] + lfrac * (pDataS1[l+1] - pDataS1[l]);
|
||||
|
||||
return p0 + sfrac * (p1 - p0); // <<== multiply result with K factor here
|
||||
}
|
||||
static inline void Scl_TimeFanin( SC_Time * p, SC_Timing * pTime, int iObj, int iFanin )
|
||||
{
|
||||
SC_Pair * pArrIn = Scl_ObjTime( p, iFanin );
|
||||
SC_Pair * pSlewIn = Scl_ObjSlew( p, iFanin );
|
||||
SC_Pair * pLoad = Scl_ObjLoad( p, iObj );
|
||||
SC_Pair * pArrOut = Scl_ObjTime( p, iObj ); // modified
|
||||
SC_Pair * pSlewOut = Scl_ObjSlew( p, iObj ); // modified
|
||||
|
||||
if (pTime->tsense == sc_ts_Pos || pTime->tsense == sc_ts_Non)
|
||||
{
|
||||
pArrOut->rise = Abc_MaxFloat( pArrOut->rise, pArrIn->rise + Scl_Lookup(pTime->pCellRise, pSlewIn->rise, pLoad->rise) );
|
||||
pArrOut->fall = Abc_MaxFloat( pArrOut->fall, pArrIn->fall + Scl_Lookup(pTime->pCellFall, pSlewIn->fall, pLoad->fall) );
|
||||
pSlewOut->rise = Abc_MaxFloat( pSlewOut->rise, Scl_Lookup(pTime->pRiseTrans, pSlewIn->rise, pLoad->rise) );
|
||||
pSlewOut->fall = Abc_MaxFloat( pSlewOut->fall, Scl_Lookup(pTime->pFallTrans, pSlewIn->fall, pLoad->fall) );
|
||||
}
|
||||
if (pTime->tsense == sc_ts_Neg || pTime->tsense == sc_ts_Non)
|
||||
{
|
||||
pArrOut->rise = Abc_MaxFloat( pArrOut->rise, pArrIn->fall + Scl_Lookup(pTime->pCellRise, pSlewIn->fall, pLoad->rise) );
|
||||
pArrOut->fall = Abc_MaxFloat( pArrOut->fall, pArrIn->rise + Scl_Lookup(pTime->pCellFall, pSlewIn->rise, pLoad->fall) );
|
||||
pSlewOut->rise = Abc_MaxFloat( pSlewOut->rise, Scl_Lookup(pTime->pRiseTrans, pSlewIn->fall, pLoad->rise) );
|
||||
pSlewOut->fall = Abc_MaxFloat( pSlewOut->fall, Scl_Lookup(pTime->pFallTrans, pSlewIn->rise, pLoad->fall) );
|
||||
}
|
||||
}
|
||||
static inline void Scl_DeptFanin( SC_Time * p, SC_Timing * pTime, int iObj, int iFanin )
|
||||
{
|
||||
SC_Pair * pDepIn = Scl_ObjDept( p, iFanin ); // modified
|
||||
SC_Pair * pSlewIn = Scl_ObjSlew( p, iFanin );
|
||||
SC_Pair * pLoad = Scl_ObjLoad( p, iObj );
|
||||
SC_Pair * pDepOut = Scl_ObjDept( p, iObj );
|
||||
|
||||
if (pTime->tsense == sc_ts_Pos || pTime->tsense == sc_ts_Non)
|
||||
{
|
||||
pDepIn->rise = Abc_MaxFloat( pDepIn->rise, pDepOut->rise + Scl_Lookup(pTime->pCellRise, pSlewIn->rise, pLoad->rise) );
|
||||
pDepIn->fall = Abc_MaxFloat( pDepIn->fall, pDepOut->fall + Scl_Lookup(pTime->pCellFall, pSlewIn->fall, pLoad->fall) );
|
||||
}
|
||||
if (pTime->tsense == sc_ts_Neg || pTime->tsense == sc_ts_Non)
|
||||
{
|
||||
pDepIn->fall = Abc_MaxFloat( pDepIn->fall, pDepOut->rise + Scl_Lookup(pTime->pCellRise, pSlewIn->fall, pLoad->rise) );
|
||||
pDepIn->rise = Abc_MaxFloat( pDepIn->rise, pDepOut->fall + Scl_Lookup(pTime->pCellFall, pSlewIn->rise, pLoad->fall) );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
ABC_NAMESPACE_HEADER_END
|
||||
|
||||
#endif
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
/// END OF FILE ///
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
|
@ -18,8 +18,7 @@
|
|||
|
||||
***********************************************************************/
|
||||
|
||||
#include "sclInt.h"
|
||||
#include "sclMan.h"
|
||||
#include "sclSize.h"
|
||||
|
||||
ABC_NAMESPACE_IMPL_START
|
||||
|
||||
|
|
|
|||
|
|
@ -18,9 +18,8 @@
|
|||
|
||||
***********************************************************************/
|
||||
|
||||
#include "sclInt.h"
|
||||
#include "sclSize.h"
|
||||
#include "map/mio/mio.h"
|
||||
#include "bool/kit/kit.h"
|
||||
|
||||
ABC_NAMESPACE_IMPL_START
|
||||
|
||||
|
|
@ -33,177 +32,6 @@ ABC_NAMESPACE_IMPL_START
|
|||
/// FUNCTION DEFINITIONS ///
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
/**Function*************************************************************
|
||||
|
||||
Synopsis [Reading library from file.]
|
||||
|
||||
Description []
|
||||
|
||||
SideEffects []
|
||||
|
||||
SeeAlso []
|
||||
|
||||
***********************************************************************/
|
||||
static unsigned Abc_SclHashString( char * pName, int TableSize )
|
||||
{
|
||||
static int s_Primes[10] = { 1291, 1699, 2357, 4177, 5147, 5647, 6343, 7103, 7873, 8147 };
|
||||
unsigned i, Key = 0;
|
||||
for ( i = 0; pName[i] != '\0'; i++ )
|
||||
Key += s_Primes[i%10]*pName[i]*pName[i];
|
||||
return Key % TableSize;
|
||||
}
|
||||
int * Abc_SclHashLookup( SC_Lib * p, char * pName )
|
||||
{
|
||||
int i;
|
||||
for ( i = Abc_SclHashString(pName, p->nBins); i < p->nBins; i = (i + 1) % p->nBins )
|
||||
if ( p->pBins[i] == -1 || !strcmp(pName, SC_LibCell(p, p->pBins[i])->pName) )
|
||||
return p->pBins + i;
|
||||
assert( 0 );
|
||||
return NULL;
|
||||
}
|
||||
void Abc_SclHashCells( SC_Lib * p )
|
||||
{
|
||||
SC_Cell * pCell;
|
||||
int i, * pPlace;
|
||||
assert( p->nBins == 0 );
|
||||
p->nBins = Abc_PrimeCudd( 5 * Vec_PtrSize(p->vCells) );
|
||||
p->pBins = ABC_FALLOC( int, p->nBins );
|
||||
SC_LibForEachCell( p, pCell, i )
|
||||
{
|
||||
pPlace = Abc_SclHashLookup( p, pCell->pName );
|
||||
assert( *pPlace == -1 );
|
||||
*pPlace = i;
|
||||
}
|
||||
}
|
||||
int Abc_SclCellFind( SC_Lib * p, char * pName )
|
||||
{
|
||||
return *Abc_SclHashLookup( p, pName );
|
||||
}
|
||||
|
||||
/**Function*************************************************************
|
||||
|
||||
Synopsis [Links equal gates into rings while sorting them by area.]
|
||||
|
||||
Description []
|
||||
|
||||
SideEffects []
|
||||
|
||||
SeeAlso []
|
||||
|
||||
***********************************************************************/
|
||||
static int Abc_SclCompareCells( SC_Cell ** pp1, SC_Cell ** pp2 )
|
||||
{
|
||||
if ( (*pp1)->n_inputs < (*pp2)->n_inputs )
|
||||
return -1;
|
||||
if ( (*pp1)->n_inputs > (*pp2)->n_inputs )
|
||||
return 1;
|
||||
if ( (*pp1)->area < (*pp2)->area )
|
||||
return -1;
|
||||
if ( (*pp1)->area > (*pp2)->area )
|
||||
return 1;
|
||||
return strcmp( (*pp1)->pName, (*pp2)->pName );
|
||||
}
|
||||
void Abc_SclLinkCells( SC_Lib * p )
|
||||
{
|
||||
SC_Cell * pCell, * pRepr = NULL;
|
||||
int i, k;
|
||||
assert( Vec_PtrSize(p->vCellClasses) == 0 );
|
||||
SC_LibForEachCell( p, pCell, i )
|
||||
{
|
||||
// find gate with the same function
|
||||
SC_LibForEachCellClass( p, pRepr, k )
|
||||
if ( pCell->n_inputs == pRepr->n_inputs &&
|
||||
pCell->n_outputs == pRepr->n_outputs &&
|
||||
Vec_WrdEqual(SC_CellFunc(pCell), SC_CellFunc(pRepr)) )
|
||||
break;
|
||||
if ( k == Vec_PtrSize(p->vCellClasses) )
|
||||
{
|
||||
Vec_PtrPush( p->vCellClasses, pCell );
|
||||
pCell->pNext = pCell->pPrev = pCell;
|
||||
continue;
|
||||
}
|
||||
// add it to the list before the cell
|
||||
pRepr->pPrev->pNext = pCell; pCell->pNext = pRepr;
|
||||
pCell->pPrev = pRepr->pPrev; pRepr->pPrev = pCell;
|
||||
}
|
||||
// sort cells by size the then by name
|
||||
qsort( (void *)Vec_PtrArray(p->vCellClasses), Vec_PtrSize(p->vCellClasses), sizeof(void *), (int(*)(const void *,const void *))Abc_SclCompareCells );
|
||||
// sort cell lists
|
||||
SC_LibForEachCellClass( p, pRepr, k )
|
||||
{
|
||||
Vec_Ptr_t * vList = Vec_PtrAlloc( 100 );
|
||||
SC_RingForEachCell( pRepr, pCell, i )
|
||||
Vec_PtrPush( vList, pCell );
|
||||
qsort( (void *)Vec_PtrArray(vList), Vec_PtrSize(vList), sizeof(void *), (int(*)(const void *,const void *))Abc_SclCompareCells );
|
||||
// create new representative
|
||||
pRepr = (SC_Cell *)Vec_PtrEntry( vList, 0 );
|
||||
pRepr->pNext = pRepr->pPrev = pRepr;
|
||||
pRepr->Order = 0;
|
||||
// relink cells
|
||||
Vec_PtrForEachEntryStart( SC_Cell *, vList, pCell, i, 1 )
|
||||
{
|
||||
pRepr->pPrev->pNext = pCell; pCell->pNext = pRepr;
|
||||
pCell->pPrev = pRepr->pPrev; pRepr->pPrev = pCell;
|
||||
pCell->Order = i;
|
||||
}
|
||||
// update list
|
||||
Vec_PtrWriteEntry( p->vCellClasses, k, pRepr );
|
||||
Vec_PtrFree( vList );
|
||||
}
|
||||
}
|
||||
void Abc_SclPrintCells( SC_Lib * p )
|
||||
{
|
||||
SC_Cell * pCell, * pRepr;
|
||||
int i, k, j, nLength = 0;
|
||||
assert( Vec_PtrSize(p->vCellClasses) > 0 );
|
||||
printf( "Library \"%s\" ", p->pName );
|
||||
printf( "containing %d cells in %d classes.\n",
|
||||
Vec_PtrSize(p->vCells), Vec_PtrSize(p->vCellClasses) );
|
||||
// find the longest name
|
||||
SC_LibForEachCellClass( p, pRepr, k )
|
||||
SC_RingForEachCell( pRepr, pCell, i )
|
||||
nLength = Abc_MaxInt( nLength, strlen(pRepr->pName) );
|
||||
// print cells
|
||||
SC_LibForEachCellClass( p, pRepr, k )
|
||||
{
|
||||
printf( "Class%3d : ", k );
|
||||
printf( "Ins = %d ", pRepr->n_inputs );
|
||||
printf( "Outs = %d", pRepr->n_outputs );
|
||||
for ( i = 0; i < pRepr->n_outputs; i++ )
|
||||
{
|
||||
printf( " " );
|
||||
Kit_DsdPrintFromTruth( (unsigned *)Vec_WrdArray(SC_CellPin(pRepr, pRepr->n_inputs+i)->vFunc), pRepr->n_inputs );
|
||||
}
|
||||
printf( "\n" );
|
||||
SC_RingForEachCell( pRepr, pCell, i )
|
||||
{
|
||||
printf( " %3d : ", i+1 );
|
||||
printf( "%-*s ", nLength, pCell->pName );
|
||||
printf( "%2d ", pCell->drive_strength );
|
||||
printf( "A =%8.2f D =", pCell->area );
|
||||
// print linear approximation
|
||||
for ( j = 0; j < 3; j++ )
|
||||
{
|
||||
SC_Pin * pPin = SC_CellPin( pCell, pCell->n_inputs );
|
||||
if ( Vec_PtrSize(pPin->vRTimings) > 0 )
|
||||
{
|
||||
SC_Timings * pRTime = (SC_Timings *)Vec_PtrEntry( pPin->vRTimings, 0 );
|
||||
SC_Timing * pTime = (SC_Timing *)Vec_PtrEntry( pRTime->vTimings, 0 );
|
||||
printf( " %6.2f", j ? pTime->pCellRise->approx[0][j] : SC_LibTimePs(p, pTime->pCellRise->approx[0][j]) );
|
||||
}
|
||||
}
|
||||
// print input capacitance
|
||||
printf( " Cap =" );
|
||||
for ( j = 0; j < pCell->n_inputs; j++ )
|
||||
{
|
||||
SC_Pin * pPin = SC_CellPin( pCell, j );
|
||||
printf( " %6.2f", SC_LibCapFf(p, pPin->rise_cap) );
|
||||
}
|
||||
printf( "\n" );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**Function*************************************************************
|
||||
|
||||
Synopsis [Converts pNode->pData gates into array of SC_Lit gate IDs and back.]
|
||||
|
|
|
|||
Loading…
Reference in New Issue