Ejemplo n.º 1
0
/**Function********************************************************************

  Synopsis    [Finds the maximum discriminant of f.]

  Description [Returns a pointer to a constant ADD.]

  SideEffects [None]

******************************************************************************/
DdNode *
Cudd_addFindMax(
  DdManager * dd,
  DdNode * f)
{
    DdNode *t, *e, *res;

    statLine(dd);
    if (cuddIsConstant(f)) {
	return(f);
    }

    res = cuddCacheLookup1(dd,Cudd_addFindMax,f);
    if (res != NULL) {
	return(res);
    }

    t  = Cudd_addFindMax(dd,cuddT(f));
    if (t == DD_PLUS_INFINITY(dd)) return(t);

    e  = Cudd_addFindMax(dd,cuddE(f));

    res = (cuddV(t) >= cuddV(e)) ? t : e;

    cuddCacheInsert1(dd,Cudd_addFindMax,f,res);

    return(res);

} /* end of Cudd_addFindMax */
Ejemplo n.º 2
0
/**Function********************************************************************

  Synopsis    [Performs the recursive step of Cuddaux_Support.]

  Description [Performs the recursive step of Cuddaux_Support.]

  SideEffects [None]

  SeeAlso     []

******************************************************************************/
DdNode*
cuddauxSupportRecur(DdManager* dd,
		    DdNode * f)
{
  DdNode *one, *fv, *fvn, *T,*E, *res, *res1;

  one = DD_ONE(dd);
  if (cuddIsConstant(f)) {
    return one;
  }
  fv = cuddT(f);
  fvn = Cudd_Regular(cuddE(f));
  if (cuddIsConstant(fv) && cuddIsConstant(fvn)){
    return dd->vars[f->index];
  }
  /* Look in the cache */
  res = cuddCacheLookup1(dd,Cuddaux_Support,f);
  if (res != NULL)
    return(res);

  T = cuddIsConstant(fv) ? one : cuddauxSupportRecur(dd,fv);
  if (T == NULL)
    return(NULL);
  cuddRef(T);
  E = cuddIsConstant(fvn) ? one : cuddauxSupportRecur(dd,fvn);
  if (E == NULL){
    Cudd_IterDerefBdd(dd,T);
    return(NULL);
  }
  if (T==E){
    res = cuddUniqueInter(dd,f->index,T,Cudd_Not(one));
    if (res == NULL){
      Cudd_IterDerefBdd(dd,T);
      return NULL;
    }
    cuddDeref(T);
  }
  else {
    cuddRef(E);
    res1 = cuddBddAndRecur(dd,T,E);
    if (res1 == NULL){
      Cudd_IterDerefBdd(dd,T);
      Cudd_IterDerefBdd(dd,E);
      return(NULL);
    }
    cuddRef(res1);
    Cudd_IterDerefBdd(dd,T);
    Cudd_IterDerefBdd(dd,E);
    res = cuddUniqueInter(dd,f->index,res1,Cudd_Not(one));
    if (res == NULL){
      Cudd_IterDerefBdd(dd,T);
      Cudd_IterDerefBdd(dd,E);
      Cudd_IterDerefBdd(dd,res1);
      return(NULL);
    }
    cuddDeref(res1);
  }
  cuddCacheInsert1(dd,Cuddaux_Support,f,res);
  return(res);
} /* end of cuddauxSupportRecur */
Ejemplo n.º 3
0
/**Function*************************************************************

  Synopsis    [Performs the recursive step of Extra_bddSpaceCanonVars().]

  Description []

  SideEffects []

  SeeAlso     []

***********************************************************************/
DdNode * extraBddSpaceCanonVars( DdManager * dd, DdNode * bF )
{
	DdNode * bRes, * bFR;
	statLine( dd );

	bFR = Cudd_Regular(bF);
	if ( cuddIsConstant(bFR) )
		return bF;

    if ( (bRes = cuddCacheLookup1(dd, extraBddSpaceCanonVars, bF)) )
    	return bRes;
	else
	{
		DdNode * bF0,  * bF1;
		DdNode * bRes, * bRes0; 

		if ( bFR != bF ) // bF is complemented 
		{
			bF0 = Cudd_Not( cuddE(bFR) );
			bF1 = Cudd_Not( cuddT(bFR) );
		}
		else
		{
			bF0 = cuddE(bFR);
			bF1 = cuddT(bFR);
		}

		if ( bF0 == b0 )
		{
			bRes = extraBddSpaceCanonVars( dd, bF1 );
			if ( bRes == NULL )
				return NULL;
		}
		else if ( bF1 == b0 )
		{
			bRes = extraBddSpaceCanonVars( dd, bF0 );
			if ( bRes == NULL )
				return NULL;
		}
		else
		{
			bRes0 = extraBddSpaceCanonVars( dd, bF0 );
			if ( bRes0 == NULL )
				return NULL;
			cuddRef( bRes0 );

			bRes = cuddUniqueInter( dd, bFR->index, bRes0, b0 );
			if ( bRes == NULL ) 
			{
				Cudd_RecursiveDeref( dd,bRes0 );
				return NULL;
			}
			cuddDeref( bRes0 );
		}

		cuddCacheInsert1( dd, extraBddSpaceCanonVars, bF, bRes );
		return bRes;
	}
}
Ejemplo n.º 4
0
/**Function********************************************************************

  Synopsis    [Implements the recursive step of Cudd_bddVarMap.]

  Description [Implements the recursive step of Cudd_bddVarMap.
  Returns a pointer to the result if successful; NULL otherwise.]

  SideEffects [None]

  SeeAlso     [Cudd_bddVarMap]

******************************************************************************/
static DdNode *
cuddBddVarMapRecur(
  DdManager *manager /* DD manager */,
  DdNode *f /* BDD to be remapped */)
{
    DdNode	*F, *T, *E;
    DdNode	*res;
    int		index;

    statLine(manager);
    F = Cudd_Regular(f);

    /* Check for terminal case of constant node. */
    if (cuddIsConstant(F)) {
	return(f);
    }

    /* If problem already solved, look up answer and return. */
    if (F->ref != 1 &&
	(res = cuddCacheLookup1(manager,Cudd_bddVarMap,F)) != NULL) {
	return(Cudd_NotCond(res,F != f));
    }

    /* Split and recur on children of this node. */
    T = cuddBddVarMapRecur(manager,cuddT(F));
    if (T == NULL) return(NULL);
    cuddRef(T);
    E = cuddBddVarMapRecur(manager,cuddE(F));
    if (E == NULL) {
	Cudd_IterDerefBdd(manager, T);
	return(NULL);
    }
    cuddRef(E);

    /* Move variable that should be in this position to this position
    ** by retrieving the single var BDD for that variable, and calling
    ** cuddBddIteRecur with the T and E we just created.
    */
    index = manager->map[F->index];
    res = cuddBddIteRecur(manager,manager->vars[index],T,E);
    if (res == NULL) {
	Cudd_IterDerefBdd(manager, T);
	Cudd_IterDerefBdd(manager, E);
	return(NULL);
    }
    cuddRef(res);
    Cudd_IterDerefBdd(manager, T);
    Cudd_IterDerefBdd(manager, E);

    /* Do not keep the result if the reference count is only 1, since
    ** it will not be visited again.
    */
    if (F->ref != 1) {
	cuddCacheInsert1(manager,Cudd_bddVarMap,F,res);
    }
    cuddDeref(res);
    return(Cudd_NotCond(res,F != f));

} /* end of cuddBddVarMapRecur */
Ejemplo n.º 5
0
/**Function********************************************************************

  Synopsis    [Performs the recursive step of Cudd_addMonadicApply.]

  Description [Performs the recursive step of Cudd_addMonadicApply. Returns a
  pointer to the result if successful; NULL otherwise.]

  SideEffects [None]

  SeeAlso     [cuddAddApplyRecur]

******************************************************************************/
DdNode *
cuddAddMonadicApplyRecur(
  DdManager * dd,
  DdNode * (*op)(DdManager *, DdNode *),
  DdNode * f)
{
    DdNode *res, *ft, *fe, *T, *E;
    unsigned int ford;
    unsigned int index;

    /* Check terminal cases. */
    statLine(dd);
    res = (*op)(dd,f);
    if (res != NULL) return(res);

    /* Check cache. */
    res = cuddCacheLookup1(dd,op,f);
    if (res != NULL) return(res);

    /* Recursive step. */
    ford = cuddI(dd,f->index);
    index = f->index;
    ft = cuddT(f);
    fe = cuddE(f);

    T = cuddAddMonadicApplyRecur(dd,op,ft);
    if (T == NULL) return(NULL);
    cuddRef(T);

    E = cuddAddMonadicApplyRecur(dd,op,fe);
    if (E == NULL) {
	Cudd_RecursiveDeref(dd,T);
	return(NULL);
    }
    cuddRef(E);

    res = (T == E) ? T : cuddUniqueInter(dd,(int)index,T,E);
    if (res == NULL) {
	Cudd_RecursiveDeref(dd, T);
	Cudd_RecursiveDeref(dd, E);
	return(NULL);
    }
    cuddDeref(T);
    cuddDeref(E);

    /* Store result. */
    cuddCacheInsert1(dd,op,f,res);

    return(res);

} /* end of cuddAddMonadicApplyRecur */
Ejemplo n.º 6
0
/**
  @brief Implements the recursive step of Cudd_addRoundOff.

  @return a pointer to the result.

  @sideeffect None

*/
DdNode *
cuddAddRoundOffRecur(
  DdManager * dd,
  DdNode * f,
  double  trunc)
{

    DdNode *res, *fv, *fvn, *T, *E;
    double n;
    DD_CTFP1 cacheOp;

    statLine(dd);
    if (cuddIsConstant(f)) {
	n = ceil(cuddV(f)*trunc)/trunc;
	res = cuddUniqueConst(dd,n);
	return(res);
    }
    cacheOp = (DD_CTFP1) Cudd_addRoundOff;
    res = cuddCacheLookup1(dd,cacheOp,f);
    if (res != NULL) {
	return(res);
    }
    checkWhetherToGiveUp(dd);
    /* Recursive Step */
    fv = cuddT(f);
    fvn = cuddE(f);
    T = cuddAddRoundOffRecur(dd,fv,trunc);
    if (T == NULL) {
       return(NULL);
    }
    cuddRef(T);
    E = cuddAddRoundOffRecur(dd,fvn,trunc);
    if (E == NULL) {
	Cudd_RecursiveDeref(dd,T);
	return(NULL);
    }
    cuddRef(E);
    res = (T == E) ? T : cuddUniqueInter(dd,(int)f->index,T,E);
    if (res == NULL) {
	Cudd_RecursiveDeref(dd,T);
	Cudd_RecursiveDeref(dd,E);
	return(NULL);
    }
    cuddDeref(T);
    cuddDeref(E);

    /* Store result. */
    cuddCacheInsert1(dd,cacheOp,f,res);
    return(res);

} /* end of cuddAddRoundOffRecur */
Ejemplo n.º 7
0
DdNode *
cuddAddMonadicApplyWithDataRecur(
  DdManager * dd,
  DD_MAOPD op,
  DdNode * f,
	void * data)
{
    DdNode *res, *ft, *fe, *T, *E;
    unsigned int index;

    /* Check terminal cases. */
    statLine(dd);
    res = (*op)(dd,f, data);
    if (res != NULL) return(res);


    /* Check cache. */
    res = cuddCacheLookup1(dd,(DD_MAOP)global_bloody_counter_unary,f);
    if (res != NULL) return(res);

    /* Recursive step. */
    index = f->index;
    ft = cuddT(f);
    fe = cuddE(f);

    T = cuddAddMonadicApplyWithDataRecur(dd,op,ft, data);
    if (T == NULL) return(NULL);
    cuddRef(T);

    E = cuddAddMonadicApplyWithDataRecur(dd,op,fe, data);
    if (E == NULL) {
	Cudd_RecursiveDeref(dd,T);
	return(NULL);
    }
    cuddRef(E);

    res = (T == E) ? T : cuddUniqueInter(dd,(int)index,T,E);
    if (res == NULL) {
	Cudd_RecursiveDeref(dd, T);
	Cudd_RecursiveDeref(dd, E);
	return(NULL);
    }
    cuddDeref(T);
    cuddDeref(E);

    /* Store result. */
    cuddCacheInsert1(dd,(DD_MAOP)global_bloody_counter_unary,f,res);

    return(res);

} /* end of cuddAddMonadicApplyWithDataRecur */
Ejemplo n.º 8
0
/**
  @brief Implements the recursive step of Cudd_addNegate.

  @return a pointer to the result.

  @sideeffect None

*/
DdNode *
cuddAddNegateRecur(
  DdManager * dd,
  DdNode * f)
{
    DdNode *res,
	    *fv, *fvn,
	    *T, *E;

    statLine(dd);
    /* Check terminal cases. */
    if (cuddIsConstant(f)) {
	res = cuddUniqueConst(dd,-cuddV(f));
	return(res);
    }

    /* Check cache */
    res = cuddCacheLookup1(dd,Cudd_addNegate,f);
    if (res != NULL) return(res);

    checkWhetherToGiveUp(dd);

    /* Recursive Step */
    fv = cuddT(f);
    fvn = cuddE(f);
    T = cuddAddNegateRecur(dd,fv);
    if (T == NULL) return(NULL);
    cuddRef(T);

    E = cuddAddNegateRecur(dd,fvn);
    if (E == NULL) {
	Cudd_RecursiveDeref(dd,T);
	return(NULL);
    }
    cuddRef(E);
    res = (T == E) ? T : cuddUniqueInter(dd,(int)f->index,T,E);
    if (res == NULL) {
	Cudd_RecursiveDeref(dd, T);
	Cudd_RecursiveDeref(dd, E);
	return(NULL);
    }
    cuddDeref(T);
    cuddDeref(E);

    /* Store result. */
    cuddCacheInsert1(dd,Cudd_addNegate,f,res);

    return(res);

} /* end of cuddAddNegateRecur */
Ejemplo n.º 9
0
/**Function********************************************************************

  Synopsis    [Performs the recursive step of Cudd_addCmpl.]

  Description [Performs the recursive step of Cudd_addCmpl. Returns a
  pointer to the resulting ADD if successful; NULL otherwise.]

  SideEffects [None]

  SeeAlso     [Cudd_addCmpl]

******************************************************************************/
DdNode *
cuddAddCmplRecur(
  DdManager * dd,
  DdNode * f)
{
    DdNode *one,*zero;
    DdNode *r,*Fv,*Fnv,*t,*e;

    statLine(dd);
    one = DD_ONE(dd);
    zero = DD_ZERO(dd); 

    if (cuddIsConstant(f)) {
        if (f == zero) {
	    return(one);
	} else {
	    return(zero);
	}
    }
    r = cuddCacheLookup1(dd,Cudd_addCmpl,f);
    if (r != NULL) {
	return(r);
    }
    Fv = cuddT(f);
    Fnv = cuddE(f);
    t = cuddAddCmplRecur(dd,Fv);
    if (t == NULL) return(NULL);
    cuddRef(t);
    e = cuddAddCmplRecur(dd,Fnv);
    if (e == NULL) {
	Cudd_RecursiveDeref(dd,t);
	return(NULL);
    }
    cuddRef(e);
    r = (t == e) ? t : cuddUniqueInter(dd,(int)f->index,t,e);
    if (r == NULL) {
	Cudd_RecursiveDeref(dd, t);
	Cudd_RecursiveDeref(dd, e);
	return(NULL);
    }
    cuddDeref(t);
    cuddDeref(e);
    cuddCacheInsert1(dd,Cudd_addCmpl,f,r);
    return(r);

} /* end of cuddAddCmplRecur */
Ejemplo n.º 10
0
/**Function********************************************************************

  Synopsis [Converts a ZDD cover to a BDD graph.]

  Description [Converts a ZDD cover to a BDD graph. If successful, it
  returns a BDD node, otherwise it returns NULL. It is a recursive
  algorithm as the following. First computes 3 cofactors of a ZDD cover;
  f1, f0 and fd. Second, compute BDDs(b1, b0 and bd) of f1, f0 and fd.
  Third, compute T=b1+bd and E=b0+bd. Fourth, compute ITE(v,T,E) where v
  is the variable which has the index of the top node of the ZDD cover.
  In this case, since the index of v can be larger than either one of T or
  one of E, cuddUniqueInterIVO is called, here IVO stands for
  independent variable ordering.]

  SideEffects []

  SeeAlso     [Cudd_MakeBddFromZddCover]

******************************************************************************/
DdNode	*
cuddMakeBddFromZddCover(
  DdManager * dd,
  DdNode * node)
{
    DdNode	*neW;
    int		v;
    DdNode	*f1, *f0, *fd;
    DdNode	*b1, *b0, *bd;
    DdNode	*T, *E;

    statLine(dd);
    if (node == dd->one)
	return(dd->one);
    if (node == dd->zero)
	return(Cudd_Not(dd->one));

    /* Check cache */
    neW = cuddCacheLookup1(dd, cuddMakeBddFromZddCover, node);
    if (neW)
	return(neW);

    v = Cudd_Regular(node)->index;	/* either yi or zi */
    cuddZddGetCofactors3(dd, node, v, &f1, &f0, &fd);
    Cudd_Ref(f1);
    Cudd_Ref(f0);
    Cudd_Ref(fd);

    b1 = cuddMakeBddFromZddCover(dd, f1);
    if (!b1) {
	Cudd_RecursiveDerefZdd(dd, f1);
	Cudd_RecursiveDerefZdd(dd, f0);
	Cudd_RecursiveDerefZdd(dd, fd);
	return(NULL);
    }
    Cudd_Ref(b1);
    b0 = cuddMakeBddFromZddCover(dd, f0);
    if (!b1) {
	Cudd_RecursiveDerefZdd(dd, f1);
	Cudd_RecursiveDerefZdd(dd, f0);
	Cudd_RecursiveDerefZdd(dd, fd);
	Cudd_RecursiveDeref(dd, b1);
	return(NULL);
    }
    Cudd_Ref(b0);
    Cudd_RecursiveDerefZdd(dd, f1);
    Cudd_RecursiveDerefZdd(dd, f0);
    if (fd != dd->zero) {
	bd = cuddMakeBddFromZddCover(dd, fd);
	if (!bd) {
	    Cudd_RecursiveDerefZdd(dd, fd);
	    Cudd_RecursiveDeref(dd, b1);
	    Cudd_RecursiveDeref(dd, b0);
	    return(NULL);
	}
	Cudd_Ref(bd);
	Cudd_RecursiveDerefZdd(dd, fd);

	T = cuddBddAndRecur(dd, Cudd_Not(b1), Cudd_Not(bd));
	if (!T) {
	    Cudd_RecursiveDeref(dd, b1);
	    Cudd_RecursiveDeref(dd, b0);
	    Cudd_RecursiveDeref(dd, bd);
	    return(NULL);
	}
	T = Cudd_NotCond(T, T != NULL);
	Cudd_Ref(T);
	Cudd_RecursiveDeref(dd, b1);
	E = cuddBddAndRecur(dd, Cudd_Not(b0), Cudd_Not(bd));
	if (!E) {
	    Cudd_RecursiveDeref(dd, b0);
	    Cudd_RecursiveDeref(dd, bd);
	    Cudd_RecursiveDeref(dd, T);
	    return(NULL);
	}
	E = Cudd_NotCond(E, E != NULL);
	Cudd_Ref(E);
	Cudd_RecursiveDeref(dd, b0);
	Cudd_RecursiveDeref(dd, bd);
    }
    else {
	Cudd_RecursiveDerefZdd(dd, fd);
	T = b1;
	E = b0;
    }

    if (Cudd_IsComplement(T)) {
	neW = cuddUniqueInterIVO(dd, v / 2, Cudd_Not(T), Cudd_Not(E));
	if (!neW) {
	    Cudd_RecursiveDeref(dd, T);
	    Cudd_RecursiveDeref(dd, E);
	    return(NULL);
	}
	neW = Cudd_Not(neW);
    }
    else {
	neW = cuddUniqueInterIVO(dd, v / 2, T, E);
	if (!neW) {
	    Cudd_RecursiveDeref(dd, T);
	    Cudd_RecursiveDeref(dd, E);
	    return(NULL);
	}
    }
    Cudd_Ref(neW);
    Cudd_RecursiveDeref(dd, T);
    Cudd_RecursiveDeref(dd, E);

    cuddCacheInsert1(dd, cuddMakeBddFromZddCover, node, neW);
    Cudd_Deref(neW);
    return(neW);

} /* end of cuddMakeBddFromZddCover */
Ejemplo n.º 11
0
/**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 */
Ejemplo n.º 12
0
/**Function*************************************************************

  Synopsis    [Performs the recursive step of Extra_bddSpaceFromFunctionPos().]

  Description []

  SideEffects []

  SeeAlso     []

***********************************************************************/
DdNode * extraBddSpaceFromFunctionNeg( DdManager * dd, DdNode * bF )
{
	DdNode * bRes, * bFR;
	statLine( dd );

	bFR = Cudd_Regular(bF);
	if ( cuddIsConstant(bFR) )
		return b0;

    if ( (bRes = cuddCacheLookup1(dd, extraBddSpaceFromFunctionNeg, bF)) )
    	return bRes;
	else
	{
		DdNode * bF0,   * bF1;
		DdNode * bPos0, * bPos1;
		DdNode * bNeg0, * bNeg1;
		DdNode * bRes0, * bRes1; 

		if ( bFR != bF ) // bF is complemented 
		{
			bF0 = Cudd_Not( cuddE(bFR) );
			bF1 = Cudd_Not( cuddT(bFR) );
		}
		else
		{
			bF0 = cuddE(bFR);
			bF1 = cuddT(bFR);
		}


		bPos0  = extraBddSpaceFromFunctionNeg( dd, bF0 );
		if ( bPos0 == NULL )
			return NULL;
		cuddRef( bPos0 );

		bPos1  = extraBddSpaceFromFunctionNeg( dd, bF1 );
		if ( bPos1 == NULL )
		{
			Cudd_RecursiveDeref( dd, bPos0 );
			return NULL;
		}
		cuddRef( bPos1 );

		bRes0  = cuddBddAndRecur( dd, bPos0, bPos1 );
		if ( bRes0 == NULL )
		{
			Cudd_RecursiveDeref( dd, bPos0 );
			Cudd_RecursiveDeref( dd, bPos1 );
			return NULL;
		}
		cuddRef( bRes0 );
		Cudd_RecursiveDeref( dd, bPos0 );
		Cudd_RecursiveDeref( dd, bPos1 );


		bNeg0  = extraBddSpaceFromFunctionPos( dd, bF0 );
		if ( bNeg0 == NULL )
		{
			Cudd_RecursiveDeref( dd, bRes0 );
			return NULL;
		}
		cuddRef( bNeg0 );

		bNeg1  = extraBddSpaceFromFunctionPos( dd, bF1 );
		if ( bNeg1 == NULL )
		{
			Cudd_RecursiveDeref( dd, bRes0 );
			Cudd_RecursiveDeref( dd, bNeg0 );
			return NULL;
		}
		cuddRef( bNeg1 );

		bRes1  = cuddBddAndRecur( dd, bNeg0, bNeg1 );
		if ( bRes1 == NULL )
		{
			Cudd_RecursiveDeref( dd, bRes0 );
			Cudd_RecursiveDeref( dd, bNeg0 );
			Cudd_RecursiveDeref( dd, bNeg1 );
			return NULL;
		}
		cuddRef( bRes1 );
		Cudd_RecursiveDeref( dd, bNeg0 );
		Cudd_RecursiveDeref( dd, bNeg1 );


		// consider the case when Res0 and Res1 are the same node 
		if ( bRes0 == bRes1 )
			bRes = bRes1;
		// consider the case when Res1 is complemented 
		else if ( Cudd_IsComplement(bRes1) ) 
		{
			bRes = cuddUniqueInter( dd, bFR->index, Cudd_Not(bRes1), Cudd_Not(bRes0) );
			if ( bRes == NULL ) 
			{
				Cudd_RecursiveDeref(dd,bRes0);
				Cudd_RecursiveDeref(dd,bRes1);
				return NULL;
			}
			bRes = Cudd_Not(bRes);
		} 
		else 
		{
			bRes = cuddUniqueInter( dd, bFR->index, bRes1, bRes0 );
			if ( bRes == NULL ) 
			{
				Cudd_RecursiveDeref(dd,bRes0);
				Cudd_RecursiveDeref(dd,bRes1);
				return NULL;
			}
		}
		cuddDeref( bRes0 );
		cuddDeref( bRes1 );

		cuddCacheInsert1( dd, extraBddSpaceFromFunctionNeg, bF, bRes );
		return bRes;
	}
}
Ejemplo n.º 13
0
/**Function*************************************************************

  Synopsis    [Performs the recursive step of Extra_bddSpaceFromFunctionPos().]

  Description []

  SideEffects []

  SeeAlso     []

***********************************************************************/
DdNode * extraBddSpaceFromMatrixNeg( DdManager * dd, DdNode * zA )
{
	DdNode * bRes;
	statLine( dd );

	if ( zA == z0 )
		return b1;
	if ( zA == z1 )
		return b0;

    if ( (bRes = cuddCacheLookup1(dd, extraBddSpaceFromMatrixNeg, zA)) )
    	return bRes;
	else
	{
		DdNode * bP0, * bP1;
		DdNode * bN0, * bN1;
		DdNode * bRes0, * bRes1; 

		bP0  = extraBddSpaceFromMatrixNeg( dd, cuddE(zA) );
		if ( bP0 == NULL )
			return NULL;
		cuddRef( bP0 );

		bP1  = extraBddSpaceFromMatrixNeg( dd, cuddT(zA) );
		if ( bP1 == NULL )
		{
			Cudd_RecursiveDeref( dd, bP0 );
			return NULL;
		}
		cuddRef( bP1 );

		bRes0  = cuddBddAndRecur( dd, bP0, bP1 );
		if ( bRes0 == NULL )
		{
			Cudd_RecursiveDeref( dd, bP0 );
			Cudd_RecursiveDeref( dd, bP1 );
			return NULL;
		}
		cuddRef( bRes0 );
		Cudd_RecursiveDeref( dd, bP0 );
		Cudd_RecursiveDeref( dd, bP1 );


		bN0  = extraBddSpaceFromMatrixNeg( dd, cuddE(zA) );
		if ( bN0 == NULL )
		{
			Cudd_RecursiveDeref( dd, bRes0 );
			return NULL;
		}
		cuddRef( bN0 );

		bN1  = extraBddSpaceFromMatrixPos( dd, cuddT(zA) );
		if ( bN1 == NULL )
		{
			Cudd_RecursiveDeref( dd, bRes0 );
			Cudd_RecursiveDeref( dd, bN0 );
			return NULL;
		}
		cuddRef( bN1 );

		bRes1  = cuddBddAndRecur( dd, bN0, bN1 );
		if ( bRes1 == NULL )
		{
			Cudd_RecursiveDeref( dd, bRes0 );
			Cudd_RecursiveDeref( dd, bN0 );
			Cudd_RecursiveDeref( dd, bN1 );
			return NULL;
		}
		cuddRef( bRes1 );
		Cudd_RecursiveDeref( dd, bN0 );
		Cudd_RecursiveDeref( dd, bN1 );


		// consider the case when Res0 and Res1 are the same node 
		if ( bRes0 == bRes1 )
			bRes = bRes1;
		// consider the case when Res1 is complemented 
		else if ( Cudd_IsComplement(bRes1) ) 
		{
			bRes = cuddUniqueInter( dd, zA->index/2, Cudd_Not(bRes1), Cudd_Not(bRes0) );
			if ( bRes == NULL ) 
			{
				Cudd_RecursiveDeref(dd,bRes0);
				Cudd_RecursiveDeref(dd,bRes1);
				return NULL;
			}
			bRes = Cudd_Not(bRes);
		} 
		else 
		{
			bRes = cuddUniqueInter( dd, zA->index/2, bRes1, bRes0 );
			if ( bRes == NULL ) 
			{
				Cudd_RecursiveDeref(dd,bRes0);
				Cudd_RecursiveDeref(dd,bRes1);
				return NULL;
			}
		}
		cuddDeref( bRes0 );
		cuddDeref( bRes1 );

		cuddCacheInsert1( dd, extraBddSpaceFromMatrixNeg, zA, bRes );
		return bRes;
	}
}
Ejemplo n.º 14
0
/**Function********************************************************************

  Synopsis    [Performs the recursive step for Cudd_addBddBooleanMap.]

  Description [Performs the recursive step for Cudd_addBddBooleanMap.
  Returns a pointer to the BDD if successful; NULL otherwise.]

  SideEffects [None]

  SeeAlso     [addBddDoStrictThreshold]

******************************************************************************/
static DdNode *
addBddBooleanMap(
  DdManager * dd,
  DdNode * f)
{
    DdNode *res, *T, *E;
    DdNode *fv, *fvn;
    int v;

    statLine(dd);
    /* Check terminal case. */
    if (cuddIsConstant(f)) {
      if ((f != DD_TRUE(dd)) && (f != DD_FALSE(dd))) {
        (void)fprintf(dd->err, "Error: Can only convert Add with FALSE or TRUE leaves to Bdd.");
        return(NULL);
      }
      return(Cudd_NotCond(DD_TRUE(dd), f == DD_FALSE(dd)));
    }

    /* Check cache. */
    res = cuddCacheLookup1(dd,addBddBooleanMap,f);
    if (res != NULL) return(res);

    /* Recursive step. */
    v = f->index;
    fv = cuddT(f); fvn = cuddE(f);

    T = addBddBooleanMap(dd,fv);
    if (T == NULL) return(NULL);
    cuddRef(T);

    E = addBddBooleanMap(dd,fvn);
    if (E == NULL) {
	Cudd_RecursiveDeref(dd, T);
	return(NULL);
    }
    cuddRef(E);
    if (Cudd_IsComplement(T)) {
	res = (T == E) ? Cudd_Not(T) : cuddUniqueInter(dd,v,Cudd_Not(T),Cudd_Not(E));
	if (res == NULL) {
	    Cudd_RecursiveDeref(dd, T);
	    Cudd_RecursiveDeref(dd, E);
	    return(NULL);
	}
	res = Cudd_Not(res);
    } else {
	res = (T == E) ? T : cuddUniqueInter(dd,v,T,E);
	if (res == NULL) {
	    Cudd_RecursiveDeref(dd, T);
	    Cudd_RecursiveDeref(dd, E);
	    return(NULL);
	}
    }
    cuddDeref(T);    
    cuddDeref(E);

    /* Store result. */
    cuddCacheInsert1(dd,addBddBooleanMap,f,res);

    return(res);

} /* end of addBddBooleanMap */
Ejemplo n.º 15
0
/**Function********************************************************************

  Synopsis    [Performs the recursive step for Cudd_addBddPattern.]

  Description [Performs the recursive step for Cudd_addBddPattern. Returns a
  pointer to the resulting BDD if successful; NULL otherwise.]

  SideEffects [None]

  SeeAlso     []

******************************************************************************/
DdNode *
cuddAddBddDoPattern(
  DdManager * dd,
  DdNode * f)
{
    DdNode *res, *T, *E;
    DdNode *fv, *fvn;
    int v;

    /* NuSMV: begin add */
    abort(); /* NOT USED BY NUSMV */
    /* NuSMV: begin end */

    statLine(dd);
    /* Check terminal case. */
    if (cuddIsConstant(f)) {
	return(Cudd_NotCond(DD_TRUE(dd),f == DD_FALSE(dd)));
    }

    /* Check cache. */
    res = cuddCacheLookup1(dd,Cudd_addBddPattern,f);
    if (res != NULL) return(res);

    /* Recursive step. */
    v = f->index;
    fv = cuddT(f); fvn = cuddE(f);

    T = cuddAddBddDoPattern(dd,fv);
    if (T == NULL) return(NULL);
    cuddRef(T);

    E = cuddAddBddDoPattern(dd,fvn);
    if (E == NULL) {
	Cudd_RecursiveDeref(dd, T);
	return(NULL);
    }
    cuddRef(E);
    if (Cudd_IsComplement(T)) {
	res = (T == E) ? Cudd_Not(T) : cuddUniqueInter(dd,v,Cudd_Not(T),Cudd_Not(E));
	if (res == NULL) {
	    Cudd_RecursiveDeref(dd, T);
	    Cudd_RecursiveDeref(dd, E);
	    return(NULL);
	}
	res = Cudd_Not(res);
    } else {
	res = (T == E) ? T : cuddUniqueInter(dd,v,T,E);
	if (res == NULL) {
	    Cudd_RecursiveDeref(dd, T);
	    Cudd_RecursiveDeref(dd, E);
	    return(NULL);
	}
    }
    cuddDeref(T);
    cuddDeref(E);

    /* Store result. */
    cuddCacheInsert1(dd,Cudd_addBddPattern,f,res);

    return(res);

} /* end of cuddAddBddDoPattern */
Ejemplo n.º 16
0
/**Function********************************************************************

  Synopsis    [Performs the recursive step for Cudd_BddTo01Add.]

  Description [Performs the recursive step for Cudd_BddTo01Add. Returns a
  pointer to the resulting ADD if successful; NULL otherwise.]

  SideEffects [None]

  SeeAlso     []

******************************************************************************/
static DdNode *
ddBddTo01AddRecur(
  DdManager * dd,
  DdNode * B)
{
    DdNode *res, *res1, *T, *E, *Bt, *Be;
    int complement = 0;

    statLine(dd);

    if (B == DD_TRUE(dd)) {
      return DD_ONE(dd);
    } else if (B == Cudd_Not(DD_TRUE(dd))) {
      return DD_ZERO(dd);
    }

    /* Check visited table */
    res = cuddCacheLookup1(dd,ddBddTo01AddRecur,B);
    if (res != NULL) return(res);

    if (Cudd_IsComplement(B)) {
	complement = 1;
	Bt = cuddT(Cudd_Regular(B));
	Be = cuddE(Cudd_Regular(B));
    } else {
	Bt = cuddT(B);
	Be = cuddE(B);
    }

    T = ddBddTo01AddRecur(dd, Bt);
    if (T == NULL) return(NULL);
    cuddRef(T);

    E = ddBddTo01AddRecur(dd, Be);
    if (E == NULL) {
	Cudd_RecursiveDeref(dd, T);
	return(NULL);
    }
    cuddRef(E);

    /* No need to check for T == E, because it is guaranteed not to happen. */
    res = cuddUniqueInter(dd, (int) Cudd_Regular(B)->index, T, E);
    if (res == NULL) {
	Cudd_RecursiveDeref(dd ,T);
	Cudd_RecursiveDeref(dd ,E);
	return(NULL);
    }
    cuddDeref(T);
    cuddDeref(E);

    if (complement) {
	cuddRef(res);
	res1 = cuddAddCmpl01Recur(dd, res);
	if (res1 == NULL) {
	    Cudd_RecursiveDeref(dd, res);
	    return(NULL);
	}
	cuddRef(res1);
	Cudd_RecursiveDeref(dd, res);
	res = res1;
	cuddDeref(res);
    }

    /* Store result. */
    cuddCacheInsert1(dd,ddBddTo01AddRecur,B,res);

    return(res);

} /* end of ddBddTo01AddRecur */