#include "calInt.h"
Go to the source code of this file.
Functions | |
static int | CeilLog2 (int number) |
void | Cal_BddSetGCMode (Cal_BddManager bddManager, int gcMode) |
int | Cal_BddManagerGC (Cal_BddManager bddManager) |
void | Cal_BddManagerSetGCLimit (Cal_BddManager manager) |
void | CalBddManagerGCCheck (Cal_BddManager_t *bddManager) |
int | CalHashTableGC (Cal_BddManager_t *bddManager, CalHashTable_t *hashTable) |
void | CalRepackNodesAfterGC (Cal_BddManager_t *bddManager) |
int Cal_BddManagerGC | ( | Cal_BddManager | bddManager | ) |
Function********************************************************************
Synopsis [Invokes the garbage collection at the manager level.]
Description [For each variable in the increasing id free nodes with reference count equal to zero freeing a node results in decrementing reference count of then and else nodes by one.]
SideEffects [None.]
Definition at line 110 of file calGC.c.
00111 { 00112 Cal_BddIndex_t index; 00113 Cal_BddId_t id; 00114 int numNodesFreed; 00115 /* unsigned long origNodes = bddManager->numNodes; */ 00116 00117 if (bddManager->numPeakNodes < (bddManager->numNodes + 00118 bddManager->numForwardedNodes)){ 00119 bddManager->numPeakNodes = bddManager->numNodes + 00120 bddManager->numForwardedNodes ; 00121 } 00122 00123 CalHashTableGC(bddManager, bddManager->uniqueTable[0]); 00124 for(index = 0; index < bddManager->numVars; index++){ 00125 id = bddManager->indexToId[index]; 00126 numNodesFreed = CalHashTableGC(bddManager, bddManager->uniqueTable[id]); 00127 bddManager->numNodes -= numNodesFreed; 00128 bddManager->numNodesFreed += numNodesFreed; 00129 } 00130 /* Free the cache entries related to unused BDD nodes */ 00131 /* The assumption is that during CalHashTableGC, the freed BDD nodes 00132 are marked. However, since they are not touched after being put 00133 on the free list, the mark should be unaffected and can be used 00134 for cleaning up the cache table. 00135 */ 00136 CalCacheTableTwoGCFlush(bddManager->cacheTable); 00137 bddManager->numGC++; 00138 return 0; 00139 }
void Cal_BddManagerSetGCLimit | ( | Cal_BddManager | manager | ) |
Function********************************************************************
Synopsis [Sets the limit of the garbage collection.]
Description [It tries to set the limit at twice the number of nodes in the manager at the current point. However, the limit is not allowed to fall below the MIN_GC_LIMIT or to exceed the value of node limit (if one exists).]
SideEffects [None.]
Definition at line 154 of file calGC.c.
00155 { 00156 manager->uniqueTableGCLimit = ((manager->numNodes) << 1); 00157 if(manager->uniqueTableGCLimit < CAL_MIN_GC_LIMIT){ 00158 manager->uniqueTableGCLimit = CAL_MIN_GC_LIMIT; 00159 } 00160 if (manager->nodeLimit && (manager->uniqueTableGCLimit > 00161 manager->nodeLimit)){ 00162 manager->uniqueTableGCLimit = manager->nodeLimit; 00163 } 00164 }
void Cal_BddSetGCMode | ( | Cal_BddManager | bddManager, | |
int | gcMode | |||
) |
AutomaticEnd Function********************************************************************
Synopsis [Sets the garbage collection mode, 0 means the garbage collection should be turned off, 1 means garbage collection should be on.]
Description [Sets the garbage collection mode, 0 means the garbage collection should be turned off, 1 means garbage collection should be on.]
SideEffects [None.]
Definition at line 90 of file calGC.c.
00093 { 00094 bddManager->gcMode = gcMode; 00095 }
void CalBddManagerGCCheck | ( | Cal_BddManager_t * | bddManager | ) |
Function********************************************************************
Synopsis [required]
Description [optional]
SideEffects [required]
SeeAlso [optional]
Definition at line 181 of file calGC.c.
00182 { 00183 if (bddManager->gcMode == 0) return; 00184 if (bddManager->gcCheck > 0) return; 00185 bddManager->gcCheck = CAL_GC_CHECK; 00186 if(bddManager->numNodes > bddManager->uniqueTableGCLimit){ 00187 Cal_BddManagerGC(bddManager); 00188 Cal_BddManagerSetGCLimit(bddManager); 00189 } 00190 }
int CalHashTableGC | ( | Cal_BddManager_t * | bddManager, | |
CalHashTable_t * | hashTable | |||
) |
Function********************************************************************
Synopsis [This function performs the garbage collection operation for a particular index.]
Description [The input is the hash table containing the nodes belonging to that level. Each bin of the hash table is traversed and the Bdd nodes with 0 reference count are put at the appropriate level in the processing que of the manager.]
SideEffects [The number of nodes in the hash table can possibly decrease.]
SeeAlso [optional]
Definition at line 208 of file calGC.c.
00209 { 00210 CalBddNode_t *last, *next, *ptr, *thenBddNode, *elseBddNode; 00211 int i; 00212 int oldNumEntries; 00213 00214 oldNumEntries = hashTable->numEntries; 00215 for(i = 0; i < hashTable->numBins; i++){ 00216 last = NULL; 00217 ptr = hashTable->bins[i]; 00218 while(ptr != Cal_Nil(CalBddNode_t)){ 00219 next = CalBddNodeGetNextBddNode(ptr); 00220 if(CalBddNodeIsRefCountZero(ptr)){ 00221 if (last == NULL){ 00222 hashTable->bins[i] = next; 00223 } 00224 else{ 00225 CalBddNodePutNextBddNode(last,next); 00226 } 00227 thenBddNode = CAL_BDD_POINTER(CalBddNodeGetThenBddNode(ptr)); 00228 elseBddNode = CAL_BDD_POINTER(CalBddNodeGetElseBddNode(ptr)); 00229 CalBddNodeDcrRefCount(thenBddNode); 00230 CalBddNodeDcrRefCount(elseBddNode); 00231 CalNodeManagerFreeNode(hashTable->nodeManager, ptr); 00232 /* Mark the freed node for cache table clean up */ 00233 /* We have to make sure that the clean up routine is called */ 00234 /* right after this function (so that the marking remains */ 00235 /* valid) */ 00236 CalBddNodeMark(ptr); 00237 hashTable->numEntries--; 00238 } 00239 else { 00240 last = ptr; 00241 } 00242 ptr = next; 00243 } 00244 } 00245 return oldNumEntries - hashTable->numEntries; 00246 }
void CalRepackNodesAfterGC | ( | Cal_BddManager_t * | bddManager | ) |
Function********************************************************************
Synopsis [required]
Description [optional]
SideEffects [required]
SeeAlso [optional]
Definition at line 261 of file calGC.c.
00262 { 00263 int index, id, numPagesRequired, packingFlag, pageNum, nodeNum; 00264 int rehashFlag = 0; 00265 int newSizeIndex, hashValue; 00266 CalNodeManager_t *nodeManager; 00267 CalHashTable_t *uniqueTableForId; 00268 CalBddNode_t *bddNode, *thenBddNode, *elseBddNode, *freeNodeList; 00269 CalBddNode_t *newNode; 00270 Cal_Bdd_t thenBdd, elseBdd; 00271 00272 packingFlag = 0; 00273 00274 for (index = bddManager->numVars-1; index >= 0; index--){ 00275 id = bddManager->indexToId[index]; 00276 uniqueTableForId = bddManager->uniqueTable[id]; 00277 nodeManager = uniqueTableForId->nodeManager; 00278 if (CalBddIdNeedsRepacking(bddManager, id) == 0){ 00279 if (packingFlag == 0) continue; /* nothing needs to be done */ 00280 /* We just need to update the cofactors and continue; */ 00281 for (pageNum=0; pageNum < nodeManager->numPages; pageNum++){ 00282 for(nodeNum = 0, 00283 bddNode = (CalBddNode_t *)nodeManager->pageList[pageNum]; 00284 nodeNum < NUM_NODES_PER_PAGE; nodeNum++, bddNode += 1){ 00285 if (CalBddNodeIsRefCountZero(bddNode) || 00286 CalBddNodeIsForwarded(bddNode)) continue; 00287 thenBddNode = CalBddNodeGetThenBddNode(bddNode); 00288 elseBddNode = CalBddNodeGetElseBddNode(bddNode); 00289 CalBddNodeGetThenBdd(bddNode, thenBdd); 00290 CalBddNodeGetElseBdd(bddNode, elseBdd); 00291 if (CalBddIsForwarded(thenBdd)){ 00292 CalBddForward(thenBdd); 00293 CalBddNodePutThenBdd(bddNode, thenBdd); 00294 rehashFlag = 1; 00295 } 00296 if (CalBddIsForwarded(elseBdd)){ 00297 CalBddForward(elseBdd); 00298 CalBddNodePutElseBdd(bddNode, elseBdd); 00299 rehashFlag = 1; 00300 } 00301 Cal_Assert(!CalBddIsRefCountZero(thenBdd)); 00302 Cal_Assert(!CalBddIsRefCountZero(elseBdd)); 00303 Cal_Assert(bddManager->idToIndex[id] < 00304 bddManager->idToIndex[bddNode->thenBddId]); 00305 Cal_Assert(bddManager->idToIndex[id] < 00306 bddManager->idToIndex[bddNode->elseBddId]); 00307 if (rehashFlag){ 00308 CalUniqueTableForIdRehashNode(uniqueTableForId, bddNode, 00309 thenBddNode, elseBddNode); 00310 } 00311 } 00312 } 00313 continue; /* move to next higher index */ 00314 } 00315 packingFlag = 1; 00316 if ((uniqueTableForId->numBins > uniqueTableForId->numEntries) && 00317 (uniqueTableForId->sizeIndex > HASH_TABLE_DEFAULT_SIZE_INDEX)){ 00318 /* Free the old bins */ 00319 Cal_MemFree(uniqueTableForId->bins); 00320 /* Create the new set of bins */ 00321 newSizeIndex = 00322 CeilLog2(uniqueTableForId->numEntries/HASH_TABLE_DEFAULT_MAX_DENSITY); 00323 if (newSizeIndex < HASH_TABLE_DEFAULT_SIZE_INDEX){ 00324 newSizeIndex = HASH_TABLE_DEFAULT_SIZE_INDEX; 00325 } 00326 uniqueTableForId->sizeIndex = newSizeIndex; 00327 uniqueTableForId->numBins = TABLE_SIZE(uniqueTableForId->sizeIndex); 00328 uniqueTableForId->maxCapacity = 00329 uniqueTableForId->numBins * HASH_TABLE_DEFAULT_MAX_DENSITY; 00330 uniqueTableForId->bins = Cal_MemAlloc(CalBddNode_t *, 00331 uniqueTableForId->numBins); 00332 if(uniqueTableForId->bins == Cal_Nil(CalBddNode_t *)){ 00333 CalBddFatalMessage("out of memory"); 00334 } 00335 } 00336 /* Clear the unique table bins */ 00337 memset((char *)uniqueTableForId->bins, 0, 00338 uniqueTableForId->numBins*sizeof(CalBddNode_t *)); 00339 numPagesRequired = 00340 uniqueTableForId->numEntries/NUM_NODES_PER_PAGE+1; 00341 /* Traverse the first numPagesRequired pages of this nodeManager */ 00342 /* Create the new free list */ 00343 nodeManager->freeNodeList = freeNodeList = Cal_Nil(CalBddNode_t); 00344 for (pageNum = 0; pageNum < nodeManager->numPages; pageNum++){ 00345 for(nodeNum = 0, 00346 bddNode = (CalBddNode_t *)nodeManager->pageList[pageNum]; 00347 nodeNum < NUM_NODES_PER_PAGE; nodeNum++, bddNode += 1){ 00348 if(CalBddNodeIsRefCountZero(bddNode) || 00349 CalBddNodeIsForwarded(bddNode)){ 00350 if (pageNum < numPagesRequired){ 00351 bddNode->nextBddNode = freeNodeList; 00352 freeNodeList = bddNode; 00353 } 00354 continue; 00355 } 00356 CalBddNodeGetThenBdd(bddNode, thenBdd); 00357 CalBddNodeGetElseBdd(bddNode, elseBdd); 00358 if (CalBddIsForwarded(thenBdd)){ 00359 CalBddForward(thenBdd); 00360 CalBddNodePutThenBdd(bddNode, thenBdd); 00361 } 00362 if (CalBddIsForwarded(elseBdd)){ 00363 CalBddForward(elseBdd); 00364 CalBddNodePutElseBdd(bddNode, elseBdd); 00365 } 00366 if (pageNum < numPagesRequired){ 00367 /* Simply insert the node in the unique table */ 00368 hashValue = CalDoHash2(thenBdd.bddNode, elseBdd.bddNode, 00369 uniqueTableForId); 00370 CalBddNodePutNextBddNode(bddNode, uniqueTableForId->bins[hashValue]); 00371 uniqueTableForId->bins[hashValue] = bddNode; 00372 } 00373 else { 00374 /* Create a new node */ 00375 newNode = freeNodeList; 00376 freeNodeList = newNode->nextBddNode; 00377 newNode->thenBddNode = bddNode->thenBddNode; 00378 newNode->elseBddNode = bddNode->elseBddNode; 00379 newNode->thenBddId = bddNode->thenBddId; 00380 newNode->elseBddId = bddNode->elseBddId; 00381 newNode->nextBddNode = bddNode->nextBddNode; 00382 bddNode->elseBddNode = FORWARD_FLAG; 00383 bddNode->thenBddId = id; 00384 bddNode->thenBddNode = newNode; 00385 hashValue = CalDoHash2(thenBdd.bddNode, elseBdd.bddNode, 00386 uniqueTableForId); 00387 CalBddNodePutNextBddNode(newNode, uniqueTableForId->bins[hashValue]); 00388 uniqueTableForId->bins[hashValue] = newNode; 00389 } 00390 } 00391 if (pageNum >= numPagesRequired){ 00392 /* Free this page. I am assuming that there would not be any 00393 call to PageManagerAllocPage, until this function finishes */ 00394 /* Also, CalPageManagerFreePage overwrites only the first field of 00395 the bdd node (the nextBddNode field), hence no relevant 00396 information is lost */ 00397 CalPageManagerFreePage(nodeManager->pageManager, 00398 nodeManager->pageList[pageNum]); 00399 nodeManager->pageList[pageNum] = 0; 00400 } 00401 } 00402 #ifdef _CAL_VERBOSE 00403 printf("Recycled %4d pages for %3d id\n", 00404 nodeManager->numPages-numPagesRequired, id); 00405 #endif 00406 nodeManager->numPages = numPagesRequired; 00407 nodeManager->freeNodeList = freeNodeList; 00408 } 00409 /* Need to update the handles to the nodes being moved */ 00410 if (bddManager->pipelineState == CREATE){ 00411 /* There are some results computed in pipeline */ 00412 CalBddReorderFixProvisionalNodes(bddManager); 00413 } 00414 00415 CalCacheTableTwoRepackUpdate(bddManager->cacheTable); 00416 00417 /* Fix the user BDDs */ 00418 CalBddReorderFixUserBddPtrs(bddManager); 00419 00420 /* Fix the association */ 00421 CalReorderAssociationFix(bddManager); 00422 00423 Cal_Assert(CalCheckAssoc(bddManager)); 00424 }
static int CeilLog2 | ( | int | number | ) | [static] |
CFile***********************************************************************
FileName [calGC.c]
PackageName [cal]
Synopsis [Garbage collection routines]
Description [optional]
SeeAlso [optional]
Author [Jagesh Sanghavi (sanghavi@eecs.berkeley.edu) Rajeev Ranjan (rajeev@eecs.berkeley.edu)]
Copyright [Copyright (c) 1994-1996 The Regents of the Univ. of California. All rights reserved.
Permission is hereby granted, without written agreement and without license or royalty fees, to use, copy, modify, and distribute this software and its documentation for any purpose, provided that the above copyright notice and the following two paragraphs appear in all copies of this software.
IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.]
Revision [
]AutomaticStart
Function********************************************************************
Synopsis [Returns the smallest integer greater than or equal to log2 of a number]
Description [Returns the smallest integer greater than or equal to log2 of a number (The assumption is that the number is >= 1)]
SideEffects [None]