/**Function******************************************************************** Synopsis [Fixes the ZDD variable group tree after a shuffle.] Description [Fixes the ZDD variable group tree after a shuffle. Assumes that the order of the variables in a terminal node has not been changed.] SideEffects [Changes the ZDD variable group tree.] SeeAlso [] ******************************************************************************/ static void zddFixTree( DdManager * table, MtrNode * treenode) { if (treenode == NULL) return; treenode->low = ((int) treenode->index < table->sizeZ) ? table->permZ[treenode->index] : treenode->index; if (treenode->child != NULL) { zddFixTree(table, treenode->child); } if (treenode->younger != NULL) zddFixTree(table, treenode->younger); if (treenode->parent != NULL && treenode->low < treenode->parent->low) { treenode->parent->low = treenode->low; treenode->parent->index = treenode->index; } return; } /* end of zddFixTree */
/**Function******************************************************************** Synopsis [Reorders ZDD variables according to the order of the BDD variables.] Description [Reorders ZDD variables according to the order of the BDD variables. This function can be called at the end of BDD reordering to insure that the order of the ZDD variables is consistent with the order of the BDD variables. The number of ZDD variables must be a multiple of the number of BDD variables. Let <code>M</code> be the ratio of the two numbers. cuddZddAlignToBdd then considers the ZDD variables from <code>M*i</code> to <code>(M+1)*i-1</code> as corresponding to BDD variable <code>i</code>. This function should be normally called from Cudd_ReduceHeap, which clears the cache. Returns 1 in case of success; 0 otherwise.] SideEffects [Changes the ZDD variable order for all diagrams and performs garbage collection of the ZDD unique table.] SeeAlso [Cudd_zddShuffleHeap Cudd_ReduceHeap] ******************************************************************************/ int cuddZddAlignToBdd( DdManager * table /* DD manager */) { int *invpermZ; /* permutation array */ int M; /* ratio of ZDD variables to BDD variables */ int i,j; /* loop indices */ int result; /* return value */ /* We assume that a ratio of 0 is OK. */ if (table->sizeZ == 0) return(1); /* NuSMV: add begin */ #if 0 /* NuSMV: add end */ empty = table->zero; /* NuSMV: add begin */ #endif empty = DD_FALSE(table); /* NuSMV: add end */ M = table->sizeZ / table->size; /* Check whether the number of ZDD variables is a multiple of the ** number of BDD variables. */ if (M * table->size != table->sizeZ) return(0); /* Create and initialize the inverse permutation array. */ invpermZ = ALLOC(int,table->sizeZ); if (invpermZ == NULL) { table->errorCode = CUDD_MEMORY_OUT; return(0); } for (i = 0; i < table->size; i++) { int index = table->invperm[i]; int indexZ = index * M; int levelZ = table->permZ[indexZ]; levelZ = (levelZ / M) * M; for (j = 0; j < M; j++) { invpermZ[M * i + j] = table->invpermZ[levelZ + j]; } } /* Eliminate dead nodes. Do not scan the cache again, because we ** assume that Cudd_ReduceHeap has already cleared it. */ cuddGarbageCollect(table,0); result = zddShuffle(table, invpermZ); FREE(invpermZ); /* Fix the ZDD variable group tree. */ zddFixTree(table,table->treeZ); return(result); } /* end of cuddZddAlignToBdd */