00001
00019 #include "fraigInt.h"
00020
00024
00025 struct Fraig_MemFixed_t_
00026 {
00027
00028 int nEntrySize;
00029 int nEntriesAlloc;
00030 int nEntriesUsed;
00031 int nEntriesMax;
00032 char * pEntriesFree;
00033
00034
00035 int nChunkSize;
00036 int nChunksAlloc;
00037 int nChunks;
00038 char ** pChunks;
00039
00040
00041 int nMemoryUsed;
00042 int nMemoryAlloc;
00043 };
00044
00048
00060 Fraig_MemFixed_t * Fraig_MemFixedStart( int nEntrySize )
00061 {
00062 Fraig_MemFixed_t * p;
00063
00064 p = ALLOC( Fraig_MemFixed_t, 1 );
00065 memset( p, 0, sizeof(Fraig_MemFixed_t) );
00066
00067 p->nEntrySize = nEntrySize;
00068 p->nEntriesAlloc = 0;
00069 p->nEntriesUsed = 0;
00070 p->pEntriesFree = NULL;
00071
00072 if ( nEntrySize * (1 << 10) < (1<<16) )
00073 p->nChunkSize = (1 << 10);
00074 else
00075 p->nChunkSize = (1<<16) / nEntrySize;
00076 if ( p->nChunkSize < 8 )
00077 p->nChunkSize = 8;
00078
00079 p->nChunksAlloc = 64;
00080 p->nChunks = 0;
00081 p->pChunks = ALLOC( char *, p->nChunksAlloc );
00082
00083 p->nMemoryUsed = 0;
00084 p->nMemoryAlloc = 0;
00085 return p;
00086 }
00087
00099 void Fraig_MemFixedStop( Fraig_MemFixed_t * p, int fVerbose )
00100 {
00101 int i;
00102 if ( p == NULL )
00103 return;
00104 if ( fVerbose )
00105 {
00106 printf( "Fixed memory manager: Entry = %5d. Chunk = %5d. Chunks used = %5d.\n",
00107 p->nEntrySize, p->nChunkSize, p->nChunks );
00108 printf( " Entries used = %8d. Entries peak = %8d. Memory used = %8d. Memory alloc = %8d.\n",
00109 p->nEntriesUsed, p->nEntriesMax, p->nEntrySize * p->nEntriesUsed, p->nMemoryAlloc );
00110 }
00111 for ( i = 0; i < p->nChunks; i++ )
00112 free( p->pChunks[i] );
00113 free( p->pChunks );
00114 free( p );
00115 }
00116
00128 char * Fraig_MemFixedEntryFetch( Fraig_MemFixed_t * p )
00129 {
00130 char * pTemp;
00131 int i;
00132
00133
00134 if ( p->nEntriesUsed == p->nEntriesAlloc )
00135 {
00136 assert( p->pEntriesFree == NULL );
00137 if ( p->nChunks == p->nChunksAlloc )
00138 {
00139 p->nChunksAlloc *= 2;
00140 p->pChunks = REALLOC( char *, p->pChunks, p->nChunksAlloc );
00141 }
00142 p->pEntriesFree = ALLOC( char, p->nEntrySize * p->nChunkSize );
00143 p->nMemoryAlloc += p->nEntrySize * p->nChunkSize;
00144
00145 pTemp = p->pEntriesFree;
00146 for ( i = 1; i < p->nChunkSize; i++ )
00147 {
00148 *((char **)pTemp) = pTemp + p->nEntrySize;
00149 pTemp += p->nEntrySize;
00150 }
00151
00152 *((char **)pTemp) = NULL;
00153
00154 p->pChunks[ p->nChunks++ ] = p->pEntriesFree;
00155
00156 p->nEntriesAlloc += p->nChunkSize;
00157 }
00158
00159 p->nEntriesUsed++;
00160 if ( p->nEntriesMax < p->nEntriesUsed )
00161 p->nEntriesMax = p->nEntriesUsed;
00162
00163 pTemp = p->pEntriesFree;
00164 p->pEntriesFree = *((char **)pTemp);
00165 return pTemp;
00166 }
00167
00179 void Fraig_MemFixedEntryRecycle( Fraig_MemFixed_t * p, char * pEntry )
00180 {
00181
00182 p->nEntriesUsed--;
00183
00184 *((char **)pEntry) = p->pEntriesFree;
00185 p->pEntriesFree = pEntry;
00186 }
00187
00199 void Fraig_MemFixedRestart( Fraig_MemFixed_t * p )
00200 {
00201 int i;
00202 char * pTemp;
00203
00204
00205 for ( i = 1; i < p->nChunks; i++ )
00206 free( p->pChunks[i] );
00207 p->nChunks = 1;
00208
00209 pTemp = p->pChunks[0];
00210 for ( i = 1; i < p->nChunkSize; i++ )
00211 {
00212 *((char **)pTemp) = pTemp + p->nEntrySize;
00213 pTemp += p->nEntrySize;
00214 }
00215
00216 *((char **)pTemp) = NULL;
00217
00218 p->pEntriesFree = p->pChunks[0];
00219
00220 p->nMemoryAlloc = p->nEntrySize * p->nChunkSize;
00221 p->nMemoryUsed = 0;
00222 p->nEntriesAlloc = p->nChunkSize;
00223 p->nEntriesUsed = 0;
00224 }
00225
00237 int Fraig_MemFixedReadMemUsage( Fraig_MemFixed_t * p )
00238 {
00239 return p->nMemoryAlloc;
00240 }
00241
00245
00246