Пример #1
0
/* Only call this when removing r from unique table */
void shadow_deref(shadow_mgr mgr, ref_t r) {
    if (!mgr->do_cudd)
	return;
    DdNode *n = get_ddnode(mgr, r);
    dd_type_t dtype = find_type(mgr, r);

#if RPT >= 5
    char buf[24];
    shadow_show(mgr, r, buf);
    report(5, "Deleting reference %s for node %p", buf, n);
#endif

    unreference_dd(mgr, n, dtype);

    if (!do_ref(mgr))
	return;

    keyvalue_remove(mgr->c2r_table, (word_t ) n, NULL, NULL);
    keyvalue_remove(mgr->r2c_table, (word_t ) r, NULL, NULL);


    if (dtype == IS_BDD) {
	ref_t nr = shadow_negate(mgr, r);
	DdNode *nn = get_ddnode(mgr, nr);
#if RPT >= 5
	shadow_show(mgr, nr, buf);
	report(5, "Deleting reference %s for node %p", buf, nn);
#endif
	keyvalue_remove(mgr->c2r_table, (word_t ) nn, NULL, NULL);
	keyvalue_remove(mgr->r2c_table, (word_t ) nr, NULL, NULL);
	unreference_dd(mgr, nn, IS_BDD);
    }
}
Пример #2
0
ref_t shadow_new_variable(shadow_mgr mgr) {
    ref_t r = REF_INVALID;
    DdNode *n = NULL;
    if (mgr->do_cudd) {
	n = Cudd_bddNewVar(mgr->bdd_manager);
	reference_dd(mgr, n);
    }
    if (mgr->do_local) {
	r = ref_new_variable(mgr->ref_mgr);
    }
    if (mgr->do_dist) {
	ref_t rdist = dist_var(mgr->ref_mgr);
	if (mgr->do_local) {
	    if (!check_refs(mgr, r, rdist))
		return REF_INVALID;
	} else
	    r = rdist;
    }
    if (!mgr->do_cudd)
	n = ref2dd(mgr, r);
    if (!do_ref(mgr)) 
	r = dd2ref(n, IS_BDD);
    add_ref(mgr, r, n);
    mgr->nvars++;
    return r;
}
Пример #3
0
ref_t shadow_one(shadow_mgr mgr) {
    if (do_ref(mgr))
	return REF_ONE;
    else {
	DdNode *n = Cudd_ReadOne(mgr->bdd_manager);
	reference_dd(mgr, n);
	return dd2ref(n, IS_BDD);
    }
}
Пример #4
0
void shadow_show(shadow_mgr mgr, ref_t r, char *buf) {
    if (do_ref(mgr)) {
	ref_show(r, buf);
    } else {
	dd_type_t dtype = find_type(mgr, r);
	DdNode *n = ref2dd(mgr, r);
	sprintf(buf, "%c%p", dtype == IS_ZDD ? 'Z' : dtype == IS_ADD ? 'A' : 'B', n);
    }		
}
Пример #5
0
ref_t shadow_zero(shadow_mgr mgr) {
    if (do_ref(mgr))
	return REF_ZERO;
    else {
	DdNode * n = Cudd_ReadLogicZero(mgr->bdd_manager);
	reference_dd(mgr, n);
	return dd2ref(n, IS_BDD);
    }
}
Пример #6
0
void free_shadow_mgr(shadow_mgr mgr) {
    if (mgr->do_cudd) {
	Cudd_Quit(mgr->bdd_manager);
    }
    if (do_ref(mgr)) 
	free_ref_mgr(mgr->ref_mgr);
    keyvalue_free(mgr->c2r_table);
    keyvalue_free(mgr->r2c_table);
    free_block((void *) mgr, sizeof(shadow_ele));
}
Пример #7
0
ref_t shadow_absval(shadow_mgr mgr, ref_t r) {
    if (do_ref(mgr))
	return REF_ABSVAL(r);
    else {
	dd_type_t dtype = find_type(mgr, r);
	DdNode *n = ref2dd(mgr, r);
	DdNode *an = Cudd_Regular(n);
	return dd2ref(an, dtype);
    }
}
Пример #8
0
static dd_type_t find_type(shadow_mgr mgr, ref_t r) {
    if (do_ref(mgr))
	return IS_BDD;
    int suffix = r & 0x3;
    switch (suffix) {
    case 0:
    case 1:
	return IS_BDD;
    case 2:
	return IS_ZDD;
    case 3:
	return IS_ADD;
    }
    return IS_BDD;
}
Пример #9
0
/* ADD conversion for external command */
ref_t shadow_aconvert(shadow_mgr mgr, ref_t r) {
    if (do_ref(mgr))
	/* Only applies when in pure CUDD mode */
	return r;
    DdNode *n = get_ddnode(mgr, r);
    if (is_add(mgr, r)) {
	return r;
    }
    if (is_zdd(mgr, r)) {
	err(false, "Can't convert ADD to ZDD");
	return REF_INVALID;
    }
    DdNode *an = aconvert(mgr, n);
    ref_t ar = dd2ref(an, IS_ADD);
    add_ref(mgr, ar, an);
    return ar;
}
Пример #10
0
/* ZDD conversion for external command */
ref_t shadow_zconvert(shadow_mgr mgr, ref_t r) {
    if (do_ref(mgr))
	/* Only applies when in pure CUDD mode */
	return r;
    DdNode *n = get_ddnode(mgr, r);
    if (is_zdd(mgr, r)) {
	return r;
    }
    if (is_add(mgr, r)) {
	err(false, "Can't convert ADD to ZDD");
	return REF_INVALID;
    }
    DdNode *zn = zconvert(mgr, n);
    ref_t zr = dd2ref(zn, IS_ZDD);
    add_ref(mgr, zr, zn);
    return zr;
}
Пример #11
0
/* General conversion from ref to dd */
static DdNode *get_ddnode(shadow_mgr mgr, ref_t r) {
    DdNode *n;
    if (!do_ref(mgr)) {
	n = ref2dd(mgr, r);
    } else if (REF_IS_INVALID(r)) {
	err(fatal, "No node associated with invalid ref");
	n = Cudd_ReadLogicZero(mgr->bdd_manager);
	reference_dd(mgr, n);
    } else if (!keyvalue_find(mgr->r2c_table, (word_t ) r, (word_t *) &n)) {
	char buf[24];
	shadow_show(mgr, r, buf);
	err(fatal, "No node associated with ref %s (0x%llx)", buf, r);
	n = mgr->do_cudd ? Cudd_ReadLogicZero(mgr->bdd_manager) :
	    (DdNode *) REF_ZERO;
	reference_dd(mgr, n);
    }
    return n;
}
Пример #12
0
ref_t shadow_get_variable(shadow_mgr mgr, size_t index) {
    if (index >= mgr->nvars) {
	err(fatal, "Invalid variable index %lu", index);
	index = 0;
    }
    ref_t r = 0;
    DdNode *n = NULL;
    if (mgr->do_cudd) {
	n = Cudd_bddIthVar(mgr->bdd_manager, index);
	reference_dd(mgr, n);
    }
    if (do_ref(mgr)) {
	r = REF_VAR(index);
	if (!mgr->do_cudd)
	    n = ref2dd(mgr, r);
    } else {
	r = dd2ref(n, IS_BDD);
    }
    add_ref(mgr, r, n);
    return r;
}
Пример #13
0
/* Compute negation.  Creates CUDD reference.  For ZDDs, records as reference */
ref_t shadow_negate(shadow_mgr mgr, ref_t a) {
    ref_t r = REF_INVALID;
    if (REF_IS_INVALID(a))
	return a;
    if (do_ref(mgr))
	r = REF_NEGATE(a);
    else {
	DdNode *an = get_ddnode(mgr, a);
	if (is_zdd(mgr, a)) {
	    DdNode *zone = Cudd_ReadZddOne(mgr->bdd_manager, 0);
	    reference_dd(mgr, zone);
	    DdNode *ann = Cudd_zddDiff(mgr->bdd_manager, zone, an);
	    reference_dd(mgr, ann);
	    unreference_dd(mgr, zone, IS_ZDD);
	    r = dd2ref(ann, IS_ZDD);
	    // For ZDDs, don't already have negated values recorded
	    add_ref(mgr, r, ann);
	} else if (is_add(mgr, a)) {
	    DdNode *ann = Cudd_addCmpl(mgr->bdd_manager, an);
	    reference_dd(mgr, ann);
	    r = dd2ref(ann, IS_ADD);
	    // For ADDs, don't already have negated values recorded
	    add_ref(mgr, r, ann);
	} else {
	    DdNode *ann = Cudd_Not(an);
	    reference_dd(mgr, ann);
	    r = dd2ref(ann, IS_BDD);
	}
    }
#if RPT >= 5
    char buf[24], nbuf[24];
    shadow_show(mgr, a, buf);
    shadow_show(mgr, r, nbuf);
    report(5, "Negated %s to get %s", buf, nbuf);
#endif
    return r;
}
 void do_oop(objectRef* p) {
   assert0(objectRef::is_null_or_heap(p));
   do_ref((heapRef*)p);
 }
Пример #15
0
/* Associate n with reference r.  For non-Zdd/Add's, also cross reference complements.
   Incoming n has recorded reference count.
   Create single reference to node.  For non-ZDD/ADD, create single reference to its complement
*/
static void add_ref(shadow_mgr mgr, ref_t r, DdNode *n) {
    ref_t rother;
    DdNode *nother;
    if (do_ref(mgr) && REF_IS_INVALID(r)) {
	/* Don't record matches with invalid refs */
	return;
    }

    if (!do_ref(mgr))
	return;

    dd_type_t dtype = find_type(mgr, r);

    bool rother_found = keyvalue_find(mgr->c2r_table, (word_t ) n,
				      (word_t *) &rother);
    bool nother_found = keyvalue_find(mgr->r2c_table, (word_t ) r,
				      (word_t *) &nother);
    char buf1[24];
    char buf2[24];
    /* See if already found entry */
    if (rother_found) {
	if (nother_found) {
	    /* Already exists.  Check if match */
	    if (nother == n && rother == r) {
		// Remove reference 
		unreference_dd(mgr, n, dtype);
	    } else {
		shadow_show(mgr, r, buf1);
		shadow_show(mgr, rother, buf2);
		err(fatal,
"Inconsistency.  New node 0x%p.  Old node 0x%p.  New ref %s.  Old ref %s",
		    n, nother, buf1, buf2);
	    }
	} else {
	    if (find_type(mgr, rother) == dtype) {
		shadow_show(mgr, r, buf1);
		shadow_show(mgr, rother, buf2);
		err(fatal, "Ref Collision.  Refs %s and %s map to BDD node %p",
		    buf1, buf2, n);
	    }
	}
    } else {
	if (nother_found) {
	    shadow_show(mgr, r, buf1);
	    err(fatal, "Node collision.  Nodes 0x%p and 0x%p map to ref %s\n",
		n, nother, buf1);
	} else {
	    /* Normal case.  Create both entries */
#if RPT >= 5
	    char buf[24];
	    shadow_show(mgr, r, buf);
	    report(5, "Added ref %s for node %p", buf, n);
#endif
	    keyvalue_insert(mgr->c2r_table, (word_t ) n, (word_t ) r);
	    keyvalue_insert(mgr->r2c_table, (word_t ) r, (word_t ) n);
	    if (dtype == IS_BDD) {
		/* Create entries for negations */
		ref_t rn = shadow_negate(mgr, r);  // Creates reference
		DdNode *nn;
		if (mgr->do_cudd) {
		    nn = Cudd_Not(n);
		} else {
		    nn = ref2dd(mgr, rn);
		}
#if RPT >= 5
		shadow_show(mgr, rn, buf);
		report(5, "Added ref %s for node %p", buf, nn);
#endif
		keyvalue_insert(mgr->c2r_table, (word_t ) nn, (word_t ) rn);
		keyvalue_insert(mgr->r2c_table, (word_t ) rn, (word_t ) nn);
	    }
	}
    }
}
Пример #16
0
shadow_mgr new_shadow_mgr(bool do_cudd, bool do_local, bool do_dist, chaining_t chaining) {
    if (!(do_cudd || do_local || do_dist)) {
	err(true, "Must have at least one active evaluation mode");
    }
    shadow_mgr mgr = (shadow_mgr) malloc_or_fail(sizeof(shadow_ele),
						 "new_shadow_mgr");
    mgr->do_cudd = do_cudd;
    mgr->do_local = do_local;
    mgr->do_dist = do_dist;

    mgr->c2r_table = word_keyvalue_new();
    mgr->r2c_table = word_keyvalue_new();
    mgr->nvars = 0;
    mgr->nzvars = 0;

    ref_t r = REF_ZERO;
    DdNode *n = NULL;

    if (do_cudd) {
	/* Modified CUDD Parameters */
	unsigned int numVars = 0; /* Default 0 */
	unsigned int numVarsZ = 0; /* Default 0 */
	unsigned int numSlots = 1u<<18; /* Default 256 */
	unsigned int cacheSize = 1u<<22; /* Default 262144 */
	/* Default 67,108,864 */
	unsigned long int maxMemory = (1u<<31) + 32UL * 1024 * 1024 * 1024;
#if 0
	// Use defaults
	numSlots = 256;
	cacheSize = 262144;
	maxMemory = 67108864;
#endif
	mgr->bdd_manager = Cudd_Init(numVars, numVarsZ, numSlots, cacheSize, maxMemory);
	Cudd_AutodynDisable(mgr->bdd_manager);
	Cudd_AutodynDisableZdd(mgr->bdd_manager);
#ifndef NO_CHAINING
	Cudd_ChainingType ct = CUDD_CHAIN_NONE;
	switch (chaining) {
	case CHAIN_NONE:
	    ct = CUDD_CHAIN_NONE;
	    report(0, "No chaining enabled");
	    break;
	case CHAIN_CONSTANT:
	    ct = CUDD_CHAIN_CONSTANT;
	    report(0, "Constant chaining enabled");
	    break;
	case CHAIN_ALL:
	    ct = CUDD_CHAIN_ALL;
	    report(0, "Or chaining enabled");
	    break;
	default:
	    err(true, "Invalid chaining mode %d\n", chaining);
	}
	Cudd_SetChaining(mgr->bdd_manager, ct);
#endif	
	n = Cudd_ReadLogicZero(mgr->bdd_manager);
	report(0, "Using CUDD Version %s", CUDD_VERSION);
    }
    if (do_ref(mgr)) {
	mgr->ref_mgr = new_ref_mgr();
	if (!do_cudd) {
	    n = ref2dd(mgr, r);
	}
    } else {
	r = dd2ref(n, IS_BDD);
    }
    reference_dd(mgr, n);
    add_ref(mgr, r, n);
    return mgr;
}
Пример #17
0
ref_t shadow_ite(shadow_mgr mgr, ref_t iref, ref_t tref, ref_t eref) {
    DdNode *in = get_ddnode(mgr, iref);
    DdNode *tn = get_ddnode(mgr, tref);
    DdNode *en = get_ddnode(mgr, eref);
    DdNode *n = NULL;
    ref_t r = REF_INVALID;
    dd_type_t dtype = IS_BDD;

    if (mgr->do_local) {
	r = ref_ite(mgr->ref_mgr, iref, tref, eref);
    }
    if (mgr->do_dist) {
	ref_t rdist = dist_ite(mgr->ref_mgr, iref, tref, eref);
	if (mgr->do_local) {
	    if (!check_refs(mgr, r, rdist)) {
		return REF_INVALID;
	    }
	} else {
	    r = rdist;
	}
    }

    if (mgr->do_cudd) {

	if (mgr->nzvars > 0) {
	    bool zi = is_zdd(mgr, iref);
	    bool zt = is_zdd(mgr, tref);
	    bool ze = is_zdd(mgr, eref);
	    if (zi || zt || ze) {
		dtype = IS_ZDD;
		if (is_add(mgr, iref) || is_add(mgr, tref) || is_add(mgr, eref)) {
		    err(false, "Can't mix ADDs with ZDDs");
		}
		if (!zi) {
		    in = zconvert(mgr, in);
		}
		if (!zt) {
		    tn = zconvert(mgr, tn);
		}
		if (!ze) {
		    en = zconvert(mgr, en);
		}
		n = Cudd_zddIte(mgr->bdd_manager, in, tn, en);
		reference_dd(mgr, n);
		if (!zi)
		    unreference_dd(mgr, in, IS_ZDD);
		if (!zt)
		    unreference_dd(mgr, tn, IS_ZDD);
		if (!ze)
		    unreference_dd(mgr, en, IS_ZDD);
	    }
	}
	{
	    bool ai = is_add(mgr, iref);
	    bool at = is_add(mgr, tref);
	    bool ae = is_add(mgr, eref);

	    if (ai || at || ae) {
		dtype = IS_ADD;
		if (!ai) {
		    in = aconvert(mgr, in);
		}
		if (!at) {
		    tn = aconvert(mgr, tn);
		}
		if (!ae) {
		    en = aconvert(mgr, en);
		}
		n = Cudd_addIte(mgr->bdd_manager, in, tn, en);
		reference_dd(mgr, n);
		if (!ai)
		    unreference_dd(mgr, in, IS_ADD);
		if (!at)
		    unreference_dd(mgr, tn, IS_ADD);
		if (!ae)
		    unreference_dd(mgr, en, IS_ADD);
	    }
	}
	if (dtype == IS_BDD) {
	    n = Cudd_bddIte(mgr->bdd_manager, in, tn, en);
	    reference_dd(mgr, n);
	}
    } else {
	n = ref2dd(mgr, r);
    }
    if (!do_ref(mgr))
	r = dd2ref(n, dtype);
    add_ref(mgr, r, n);
    return r;
}