blob: ef52765e26e426ad5bbff55d2c030f513869ae2d [file] [log] [blame]
/**CFile****************************************************************
FileName [fraigMem.c]
PackageName [FRAIG: Functionally reduced AND-INV graphs.]
Synopsis [Fixed-size-entry memory manager for the FRAIG package.]
Author [Alan Mishchenko <alanmi@eecs.berkeley.edu>]
Affiliation [UC Berkeley]
Date [Ver. 2.0. Started - October 1, 2004]
Revision [$Id: fraigMem.c,v 1.4 2005/07/08 01:01:31 alanmi Exp $]
***********************************************************************/
#include "fraigInt.h"
ABC_NAMESPACE_IMPL_START
////////////////////////////////////////////////////////////////////////
/// DECLARATIONS ///
////////////////////////////////////////////////////////////////////////
struct Fraig_MemFixed_t_
{
// information about individual entries
int nEntrySize; // the size of one entry
int nEntriesAlloc; // the total number of entries allocated
int nEntriesUsed; // the number of entries in use
int nEntriesMax; // the max number of entries in use
char * pEntriesFree; // the linked list of free entries
// this is where the memory is stored
int nChunkSize; // the size of one chunk
int nChunksAlloc; // the maximum number of memory chunks
int nChunks; // the current number of memory chunks
char ** pChunks; // the allocated memory
// statistics
int nMemoryUsed; // memory used in the allocated entries
int nMemoryAlloc; // memory allocated
};
////////////////////////////////////////////////////////////////////////
/// FUNCTION DEFINITIONS ///
////////////////////////////////////////////////////////////////////////
/**Function*************************************************************
Synopsis [Starts the internal memory manager.]
Description [Can only work with entry size at least 4 byte long.]
SideEffects []
SeeAlso []
***********************************************************************/
Fraig_MemFixed_t * Fraig_MemFixedStart( int nEntrySize )
{
Fraig_MemFixed_t * p;
p = ABC_ALLOC( Fraig_MemFixed_t, 1 );
memset( p, 0, sizeof(Fraig_MemFixed_t) );
p->nEntrySize = nEntrySize;
p->nEntriesAlloc = 0;
p->nEntriesUsed = 0;
p->pEntriesFree = NULL;
if ( nEntrySize * (1 << 10) < (1<<16) )
p->nChunkSize = (1 << 10);
else
p->nChunkSize = (1<<16) / nEntrySize;
if ( p->nChunkSize < 8 )
p->nChunkSize = 8;
p->nChunksAlloc = 64;
p->nChunks = 0;
p->pChunks = ABC_ALLOC( char *, p->nChunksAlloc );
p->nMemoryUsed = 0;
p->nMemoryAlloc = 0;
return p;
}
/**Function*************************************************************
Synopsis [Stops the internal memory manager.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Fraig_MemFixedStop( Fraig_MemFixed_t * p, int fVerbose )
{
int i;
if ( p == NULL )
return;
if ( fVerbose )
{
printf( "Fixed memory manager: Entry = %5d. Chunk = %5d. Chunks used = %5d.\n",
p->nEntrySize, p->nChunkSize, p->nChunks );
printf( " Entries used = %8d. Entries peak = %8d. Memory used = %8d. Memory alloc = %8d.\n",
p->nEntriesUsed, p->nEntriesMax, p->nEntrySize * p->nEntriesUsed, p->nMemoryAlloc );
}
for ( i = 0; i < p->nChunks; i++ )
ABC_FREE( p->pChunks[i] );
ABC_FREE( p->pChunks );
ABC_FREE( p );
}
/**Function*************************************************************
Synopsis [Extracts one entry from the memory manager.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
char * Fraig_MemFixedEntryFetch( Fraig_MemFixed_t * p )
{
char * pTemp;
int i;
// check if there are still free entries
if ( p->nEntriesUsed == p->nEntriesAlloc )
{ // need to allocate more entries
assert( p->pEntriesFree == NULL );
if ( p->nChunks == p->nChunksAlloc )
{
p->nChunksAlloc *= 2;
p->pChunks = ABC_REALLOC( char *, p->pChunks, p->nChunksAlloc );
}
p->pEntriesFree = ABC_ALLOC( char, p->nEntrySize * p->nChunkSize );
p->nMemoryAlloc += p->nEntrySize * p->nChunkSize;
// transform these entries into a linked list
pTemp = p->pEntriesFree;
for ( i = 1; i < p->nChunkSize; i++ )
{
*((char **)pTemp) = pTemp + p->nEntrySize;
pTemp += p->nEntrySize;
}
// set the last link
*((char **)pTemp) = NULL;
// add the chunk to the chunk storage
p->pChunks[ p->nChunks++ ] = p->pEntriesFree;
// add to the number of entries allocated
p->nEntriesAlloc += p->nChunkSize;
}
// incrememt the counter of used entries
p->nEntriesUsed++;
if ( p->nEntriesMax < p->nEntriesUsed )
p->nEntriesMax = p->nEntriesUsed;
// return the first entry in the free entry list
pTemp = p->pEntriesFree;
p->pEntriesFree = *((char **)pTemp);
return pTemp;
}
/**Function*************************************************************
Synopsis [Returns one entry into the memory manager.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
void Fraig_MemFixedEntryRecycle( Fraig_MemFixed_t * p, char * pEntry )
{
// decrement the counter of used entries
p->nEntriesUsed--;
// add the entry to the linked list of free entries
*((char **)pEntry) = p->pEntriesFree;
p->pEntriesFree = pEntry;
}
/**Function*************************************************************
Synopsis [Frees all associated memory and resets the manager.]
Description [Relocates all the memory except the first chunk.]
SideEffects []
SeeAlso []
***********************************************************************/
void Fraig_MemFixedRestart( Fraig_MemFixed_t * p )
{
int i;
char * pTemp;
// deallocate all chunks except the first one
for ( i = 1; i < p->nChunks; i++ )
ABC_FREE( p->pChunks[i] );
p->nChunks = 1;
// transform these entries into a linked list
pTemp = p->pChunks[0];
for ( i = 1; i < p->nChunkSize; i++ )
{
*((char **)pTemp) = pTemp + p->nEntrySize;
pTemp += p->nEntrySize;
}
// set the last link
*((char **)pTemp) = NULL;
// set the free entry list
p->pEntriesFree = p->pChunks[0];
// set the correct statistics
p->nMemoryAlloc = p->nEntrySize * p->nChunkSize;
p->nMemoryUsed = 0;
p->nEntriesAlloc = p->nChunkSize;
p->nEntriesUsed = 0;
}
/**Function*************************************************************
Synopsis [Reports the memory usage.]
Description []
SideEffects []
SeeAlso []
***********************************************************************/
int Fraig_MemFixedReadMemUsage( Fraig_MemFixed_t * p )
{
return p->nMemoryAlloc;
}
////////////////////////////////////////////////////////////////////////
/// END OF FILE ///
////////////////////////////////////////////////////////////////////////
ABC_NAMESPACE_IMPL_END