/**Function******************************************************************** Synopsis [Performs the recursive step of Cudd_zddPrintCover.] Description [] SideEffects [None] SeeAlso [] ******************************************************************************/ static void zddPrintCoverAux( DdManager * zdd /* manager */, DdNode * node /* current node */, int level /* depth in the recursion */, int * list /* current recursion path */) { DdNode *Nv, *Nnv; int i, v; DdNode *base = DD_ONE(zdd); if (Cudd_IsConstant(node)) { if (node == base) { /* Check for missing variable. */ if (level != zdd->sizeZ) { list[zdd->invpermZ[level]] = 0; zddPrintCoverAux(zdd, node, level + 1, list); return; } /* Terminal case: Print one cube based on the current recursion ** path. */ for (i = 0; i < zdd->sizeZ; i += 2) { v = list[i] * 4 + list[i+1]; if (v == 0) (void) fprintf(zdd->out,"-"); else if (v == 4) (void) fprintf(zdd->out,"1"); else if (v == 1) (void) fprintf(zdd->out,"0"); else (void) fprintf(zdd->out,"@"); /* should never happen */ } (void) fprintf(zdd->out," 1\n"); } } else { /* Check for missing variable. */ if (level != cuddIZ(zdd,node->index)) { list[zdd->invpermZ[level]] = 0; zddPrintCoverAux(zdd, node, level + 1, list); return; } Nnv = cuddE(node); Nv = cuddT(node); if (Nv == Nnv) { list[node->index] = 2; zddPrintCoverAux(zdd, Nnv, level + 1, list); return; } list[node->index] = 1; zddPrintCoverAux(zdd, Nv, level + 1, list); list[node->index] = 0; zddPrintCoverAux(zdd, Nnv, level + 1, list); } return; } /* end of zddPrintCoverAux */
/**Function******************************************************************** Synopsis [Performs the recursive step of Cudd_zddPortToBdd.] Description [] SideEffects [None] SeeAlso [] ******************************************************************************/ static DdNode * zddPortToBddStep( DdManager * dd /* manager */, DdNode * f /* ZDD to be converted */, int depth /* recursion depth */) { DdNode *one, *zero, *T, *E, *res, *var; unsigned int index; unsigned int level; statLine(dd); one = DD_ONE(dd); zero = DD_ZERO(dd); if (f == zero) return(Cudd_Not(one)); if (depth == dd->sizeZ) return(one); index = dd->invpermZ[depth]; level = cuddIZ(dd,f->index); var = cuddUniqueInter(dd,index,one,Cudd_Not(one)); if (var == NULL) return(NULL); cuddRef(var); if (level > (unsigned) depth) { E = zddPortToBddStep(dd,f,depth+1); if (E == NULL) { Cudd_RecursiveDeref(dd,var); return(NULL); } cuddRef(E); res = cuddBddIteRecur(dd,var,Cudd_Not(one),E); if (res == NULL) { Cudd_RecursiveDeref(dd,var); Cudd_RecursiveDeref(dd,E); return(NULL); } cuddRef(res); Cudd_RecursiveDeref(dd,var); Cudd_RecursiveDeref(dd,E); cuddDeref(res); return(res); } res = cuddCacheLookup1(dd,Cudd_zddPortToBdd,f); if (res != NULL) { Cudd_RecursiveDeref(dd,var); return(res); } T = zddPortToBddStep(dd,cuddT(f),depth+1); if (T == NULL) { Cudd_RecursiveDeref(dd,var); return(NULL); } cuddRef(T); E = zddPortToBddStep(dd,cuddE(f),depth+1); if (E == NULL) { Cudd_RecursiveDeref(dd,var); Cudd_RecursiveDeref(dd,T); return(NULL); } cuddRef(E); res = cuddBddIteRecur(dd,var,T,E); if (res == NULL) { Cudd_RecursiveDeref(dd,var); Cudd_RecursiveDeref(dd,T); Cudd_RecursiveDeref(dd,E); return(NULL); } cuddRef(res); Cudd_RecursiveDeref(dd,var); Cudd_RecursiveDeref(dd,T); Cudd_RecursiveDeref(dd,E); cuddDeref(res); cuddCacheInsert1(dd,Cudd_zddPortToBdd,f,res); return(res); } /* end of zddPortToBddStep */
/**Function******************************************************************** Synopsis [Performs the recursive step of Cudd_zddIte.] Description [] SideEffects [None] SeeAlso [] ******************************************************************************/ DdNode * cuddZddIte( DdManager * dd, DdNode * f, DdNode * g, DdNode * h) { DdNode *tautology, *empty; DdNode *r,*Gv,*Gvn,*Hv,*Hvn,*t,*e; unsigned int topf,topg,toph,v,top; int index; statLine(dd); /* Trivial cases. */ /* One variable cases. */ if (f == (empty = DD_ZERO(dd))) { /* ITE(0,G,H) = H */ return(h); } topf = cuddIZ(dd,f->index); topg = cuddIZ(dd,g->index); toph = cuddIZ(dd,h->index); v = ddMin(topg,toph); top = ddMin(topf,v); tautology = (top == CUDD_MAXINDEX) ? DD_ONE(dd) : dd->univ[top]; if (f == tautology) { /* ITE(1,G,H) = G */ return(g); } /* From now on, f is known to not be a constant. */ zddVarToConst(f,&g,&h,tautology,empty); /* Check remaining one variable cases. */ if (g == h) { /* ITE(F,G,G) = G */ return(g); } if (g == tautology) { /* ITE(F,1,0) = F */ if (h == empty) return(f); } /* Check cache. */ r = cuddCacheLookupZdd(dd,DD_ZDD_ITE_TAG,f,g,h); if (r != NULL) { return(r); } /* Recompute these because they may have changed in zddVarToConst. */ topg = cuddIZ(dd,g->index); toph = cuddIZ(dd,h->index); v = ddMin(topg,toph); if (topf < v) { r = cuddZddIte(dd,cuddE(f),g,h); if (r == NULL) return(NULL); } else if (topf > v) { if (topg > v) { Gvn = g; index = h->index; } else { Gvn = cuddE(g); index = g->index; } if (toph > v) { Hv = empty; Hvn = h; } else { Hv = cuddT(h); Hvn = cuddE(h); } e = cuddZddIte(dd,f,Gvn,Hvn); if (e == NULL) return(NULL); cuddRef(e); r = cuddZddGetNode(dd,index,Hv,e); if (r == NULL) { Cudd_RecursiveDerefZdd(dd,e); return(NULL); } cuddDeref(e); } else { index = f->index; if (topg > v) { Gv = empty; Gvn = g; } else { Gv = cuddT(g); Gvn = cuddE(g); } if (toph > v) { Hv = empty; Hvn = h; } else { Hv = cuddT(h); Hvn = cuddE(h); } e = cuddZddIte(dd,cuddE(f),Gvn,Hvn); if (e == NULL) return(NULL); cuddRef(e); t = cuddZddIte(dd,cuddT(f),Gv,Hv); if (t == NULL) { Cudd_RecursiveDerefZdd(dd,e); return(NULL); } cuddRef(t); r = cuddZddGetNode(dd,index,t,e); if (r == NULL) { Cudd_RecursiveDerefZdd(dd,e); Cudd_RecursiveDerefZdd(dd,t); return(NULL); } cuddDeref(t); cuddDeref(e); } cuddCacheInsert(dd,DD_ZDD_ITE_TAG,f,g,h,r); return(r); } /* end of cuddZddIte */