#include "mdd.h"
Go to the source code of this file.
Functions | |
int | integer_get_num_of_digits (int value) |
static void | mdd_name_variables (array_t *mvar_list, int no_mvars, array_t **mvar_names_ptr) |
static void | mdd_record_variables (mdd_manager *mgr, int current_vertex_before, int start_mvar, int no_mvars, array_t *mvar_names, array_t *mvar_values, array_t *mvar_strides) |
mdd_manager * | mdd_init (array_t *mvar_values, array_t *mvar_names, array_t *mvar_strides) |
unsigned int | mdd_create_variables (mdd_manager *mgr, array_t *mvar_values, array_t *mvar_names, array_t *mvar_strides) |
unsigned int | mdd_create_variables_after (mdd_manager *mgr, int after_mvar_id, array_t *mvar_values, array_t *mvar_names, array_t *mvar_strides) |
unsigned int | mdd_create_variables_interleaved (mdd_manager *mgr, int inter_var_id, int no_mvars, array_t *mvar_names) |
void | mdd_array_free (array_t *mddArray) |
void | mdd_array_array_free (array_t *arrayBddArray) |
array_t * | mdd_array_duplicate (array_t *mddArray) |
boolean | mdd_array_equal (array_t *array1, array_t *array2) |
mdd_manager * | mdd_init_empty (void) |
void | mdd_var_expunge_bdd_variable (mdd_manager *mgr, int bddId, int val) |
int integer_get_num_of_digits | ( | int | value | ) |
Definition at line 19 of file mdd_init.c.
00020 { 00021 double x; 00022 int num_of_digits; 00023 00024 if (value > 0) x = log10((double) value); 00025 else if (value == 0) x = 0; 00026 else fail("mdd_init: internal error, value less than 0\n"); 00027 00028 /* 00029 * Notice that floor(x) return a double, 00030 * so it needs to be cast into an integer using 00031 * this following expression. 00032 */ 00033 num_of_digits = (int) floor(x) + 1; 00034 00035 return num_of_digits; 00036 }
void mdd_array_array_free | ( | array_t * | arrayBddArray | ) |
Definition at line 485 of file mdd_init.c.
00486 { 00487 int i; 00488 array_t *bddArray; 00489 00490 if (arrayBddArray != NIL(array_t)) { 00491 for (i = 0; i < array_n(arrayBddArray); i++) { 00492 bddArray = array_fetch(array_t *, arrayBddArray, i); 00493 mdd_array_free(bddArray); 00494 } 00495 array_free(arrayBddArray); 00496 } 00497 }
Definition at line 500 of file mdd_init.c.
00501 { 00502 int i; 00503 int length = array_n(mddArray); 00504 array_t *result = array_alloc(mdd_t *, length); 00505 for (i = 0; i < length; i++) { 00506 mdd_t *tempMdd = array_fetch(mdd_t *, mddArray, i); 00507 array_insert(mdd_t *, result, i, mdd_dup(tempMdd)); 00508 } 00509 00510 return (result); 00511 }
Definition at line 517 of file mdd_init.c.
00518 { 00519 int i; 00520 00521 assert(array1 != NIL(array_t) && array2 != NIL(array_t)); 00522 00523 if(array_n(array1) != array_n(array2)) 00524 return FALSE; 00525 00526 for(i = 0; i < array_n(array1); i++) { 00527 mdd_t *mdd1 = array_fetch(mdd_t *, array1, i); 00528 mdd_t *mdd2 = array_fetch(mdd_t *, array2, i); 00529 if(!mdd_equal(mdd1, mdd2)) 00530 return FALSE; 00531 } 00532 00533 return TRUE; 00534 }
void mdd_array_free | ( | array_t * | mddArray | ) |
Definition at line 471 of file mdd_init.c.
00472 { 00473 int i; 00474 00475 if (mddArray != NIL(array_t)) { 00476 for (i = 0; i < array_n(mddArray); i++) { 00477 mdd_t *tempMdd = array_fetch(mdd_t *, mddArray, i); 00478 mdd_free(tempMdd); 00479 } 00480 array_free(mddArray); 00481 } 00482 }
unsigned int mdd_create_variables | ( | mdd_manager * | mgr, | |
array_t * | mvar_values, | |||
array_t * | mvar_names, | |||
array_t * | mvar_strides | |||
) |
Definition at line 258 of file mdd_init.c.
00263 { 00264 array_t *mvar_list = mdd_ret_mvar_list(mgr); 00265 array_t *bvar_list = mdd_ret_bvar_list(mgr); 00266 int i, no_mvars, current_vertex, start_mvar; 00267 int vertex_sum; 00268 bdd_t *temp; 00269 boolean free_mvar_strides_flag; 00270 boolean free_mvar_names_flag; 00271 00272 00273 /* if some array arguments are NIL */ 00274 no_mvars = array_n(mvar_values); 00275 00276 free_mvar_names_flag = (mvar_names == NIL(array_t)); 00277 mdd_name_variables(mvar_list, no_mvars, &mvar_names); 00278 00279 if (mvar_strides == NIL(array_t)) { 00280 /* if no strides are specified, the variables are not interleaved */ 00281 /* i.e. mvar_strides = 1 */ 00282 /* must set a flag to know that this array needs to be freed */ 00283 free_mvar_strides_flag = TRUE; 00284 mvar_strides = array_alloc(int, 0); 00285 for (i=0; i<no_mvars; i++) { 00286 array_insert_last(int, mvar_strides, 1); 00287 } 00288 } 00289 else { 00290 free_mvar_strides_flag = FALSE; 00291 if (no_mvars != array_n(mvar_strides)) 00292 fail("mdd_init: inconsistent size of mvar_strides\n"); 00293 } 00294 00295 vertex_sum = 0; 00296 for (i=0; i<no_mvars; i++) { 00297 vertex_sum = vertex_sum + no_bit_encode(array_fetch(int,mvar_values,i)); 00298 } 00299 current_vertex = array_n(bvar_list); 00300 for (i=0; i<vertex_sum; i++) { 00301 temp = bdd_get_variable(mgr, i+current_vertex); 00302 bdd_free(temp); 00303 } 00304 00305 start_mvar = array_n(mvar_list); 00306 00307 mdd_record_variables(mgr, current_vertex, start_mvar, no_mvars, mvar_names, mvar_values, mvar_strides); 00308 00309 if (free_mvar_strides_flag) { 00310 array_free(mvar_strides); 00311 } 00312 00313 if (free_mvar_names_flag) { 00314 for (i = 0; i < array_n(mvar_names); i++) { 00315 char *name = array_fetch(char *, mvar_names, i); 00316 FREE(name); 00317 } 00318 array_free(mvar_names); 00319 } 00320 00321 return start_mvar; 00322 }
unsigned int mdd_create_variables_after | ( | mdd_manager * | mgr, | |
int | after_mvar_id, | |||
array_t * | mvar_values, | |||
array_t * | mvar_names, | |||
array_t * | mvar_strides | |||
) |
Definition at line 326 of file mdd_init.c.
00332 { 00333 array_t *mvar_list = mdd_ret_mvar_list(mgr); 00334 array_t *bvar_list = mdd_ret_bvar_list(mgr); 00335 mvar_type after_mv, fol_mv; 00336 int i, no_mvars, current_vertex, start_mvar; 00337 int vertex_sum; 00338 int after_bv_id; 00339 bdd_t *temp; 00340 bvar_type sec_bit_of_mv; 00341 int sec_bit_level, fol_id; 00342 boolean free_mvar_strides_flag; 00343 boolean free_mvar_names_flag; 00344 00345 after_mv = array_fetch( mvar_type, mvar_list, after_mvar_id ); 00346 00347 if (after_mv.encode_length > 1) { 00348 sec_bit_of_mv = mdd_ret_bvar(&after_mv, 1, bvar_list); 00349 sec_bit_level = bdd_top_var_level( mgr, sec_bit_of_mv.node ); 00350 /* first_bit_of_last_interleaved_mvar */ 00351 fol_id = bdd_get_id_from_level( mgr, sec_bit_level - 1 ); 00352 } 00353 else 00354 fol_id = mdd_ret_bvar_id(&after_mv, 0); 00355 00356 fol_mv = array_fetch( mvar_type, mvar_list, fol_id ); 00357 00358 after_bv_id = mdd_ret_bvar_id(&fol_mv, fol_mv.encode_length - 1); 00359 00360 /* if some array arguments are NIL */ 00361 no_mvars = array_n(mvar_values); 00362 00363 free_mvar_names_flag = (mvar_names == NIL(array_t)); 00364 mdd_name_variables(mvar_list, no_mvars, &mvar_names); 00365 00366 if (mvar_strides == NIL(array_t)) { 00367 /* if no strides are specified, the variables are not interleaved */ 00368 /* i.e. mvar_strides = 1 */ 00369 /* must set a flag to know that this array needs to be freed */ 00370 free_mvar_strides_flag = TRUE; 00371 mvar_strides = array_alloc(int, 0); 00372 for (i=0; i<no_mvars; i++) { 00373 array_insert_last(int, mvar_strides, 1); 00374 } 00375 } 00376 else { 00377 free_mvar_strides_flag = FALSE; 00378 if (no_mvars != array_n(mvar_strides)) 00379 fail("mdd_init: inconsistent size of mvar_strides\n"); 00380 } 00381 00382 vertex_sum = 0; 00383 for (i=0; i<no_mvars; i++) { 00384 vertex_sum = vertex_sum + no_bit_encode(array_fetch(int,mvar_values,i)); 00385 } 00386 for (i=0; i<vertex_sum; i++) { 00387 temp = bdd_create_variable_after(mgr, after_bv_id + i); 00388 bdd_free(temp); 00389 } 00390 00391 current_vertex = array_n(bvar_list); 00392 start_mvar = array_n(mvar_list); 00393 00394 mdd_record_variables(mgr, current_vertex, start_mvar, no_mvars, mvar_names, mvar_values, mvar_strides); 00395 00396 if (free_mvar_strides_flag) { 00397 array_free(mvar_strides); 00398 } 00399 00400 if (free_mvar_names_flag) { 00401 for (i = 0; i < array_n(mvar_names); i++) { 00402 char *name = array_fetch(char *, mvar_names, i); 00403 FREE(name); 00404 } 00405 array_free(mvar_names); 00406 } 00407 00408 return start_mvar; 00409 00410 }
unsigned int mdd_create_variables_interleaved | ( | mdd_manager * | mgr, | |
int | inter_var_id, | |||
int | no_mvars, | |||
array_t * | mvar_names | |||
) |
Definition at line 414 of file mdd_init.c.
00419 { 00420 array_t *mvar_list = mdd_ret_mvar_list(mgr); 00421 array_t *bvar_list = mdd_ret_bvar_list(mgr); 00422 mvar_type inter_var; 00423 int i, j, current_vertex, start_mvar; 00424 bdd_t *temp; 00425 array_t *mvar_values; 00426 array_t *mvar_strides; 00427 boolean free_mvar_names_flag; 00428 00429 inter_var = array_fetch( mvar_type, mvar_list, inter_var_id ); 00430 00431 /* if some array arguments are NIL */ 00432 free_mvar_names_flag = (mvar_names == NIL(array_t)); 00433 mdd_name_variables(mvar_list, no_mvars, &mvar_names); 00434 00435 00436 for (j=0; j<inter_var.encode_length; j++) { 00437 for (i=0; i<no_mvars; i++) { 00438 temp = bdd_create_variable_after( mgr, mdd_ret_bvar_id(&inter_var, j) ); 00439 bdd_free( temp ); 00440 } 00441 } 00442 00443 current_vertex = array_n(bvar_list); 00444 start_mvar = array_n(mvar_list); 00445 00446 mvar_values = array_alloc(int, 0); 00447 mvar_strides = array_alloc(int, 0); 00448 for(i=0; i<no_mvars; i++) { 00449 array_insert_last(int, mvar_values, inter_var.values); 00450 array_insert_last(int, mvar_strides, no_mvars); 00451 } 00452 00453 mdd_record_variables(mgr, current_vertex, start_mvar, no_mvars, mvar_names, mvar_values, mvar_strides); 00454 00455 array_free(mvar_values); 00456 array_free(mvar_strides); 00457 00458 if (free_mvar_names_flag) { 00459 for (i = 0; i < array_n(mvar_names); i++) { 00460 char *name = array_fetch(char *, mvar_names, i); 00461 FREE(name); 00462 } 00463 array_free(mvar_names); 00464 } 00465 00466 return start_mvar; 00467 }
mdd_manager* mdd_init | ( | array_t * | mvar_values, | |
array_t * | mvar_names, | |||
array_t * | mvar_strides | |||
) |
Definition at line 176 of file mdd_init.c.
00180 { 00181 array_t *mvar_list; 00182 array_t *bvar_list; 00183 int i, no_mvars, current_vertex; 00184 int vertex_sum; 00185 mdd_manager *mgr; 00186 mdd_hook_type *mdd_hook; 00187 bdd_external_hooks *hook; 00188 boolean free_mvar_strides_flag; 00189 boolean free_mvar_names_flag; 00190 00191 mdd_hook = ALLOC(mdd_hook_type, 1); 00192 00193 /* global information about all mvar for mdd_manager */ 00194 mvar_list = array_alloc(mvar_type, 0); 00195 00196 /* global information about all bvar for mdd_manager */ 00197 bvar_list = array_alloc(bvar_type, 0); 00198 00199 /* create the hook to the bdd_manager */ 00200 mdd_hook->mvar_list = mvar_list; 00201 mdd_hook->bvar_list = bvar_list; 00202 00203 /* if some array arguments are NIL */ 00204 no_mvars = array_n(mvar_values); 00205 00206 free_mvar_names_flag = (mvar_names == NIL(array_t)); 00207 mdd_name_variables(mvar_list, no_mvars, &mvar_names); 00208 00209 /* create mdd manager */ 00210 vertex_sum = 0; 00211 for (i=0; i<no_mvars; i++) { 00212 vertex_sum = vertex_sum + no_bit_encode(array_fetch(int,mvar_values,i)); 00213 } 00214 mgr = bdd_start(vertex_sum); 00215 00216 hook = bdd_get_external_hooks(mgr); 00217 00218 hook->mdd = (char *) mdd_hook; 00219 00220 current_vertex = 0; 00221 00222 if (mvar_strides == NIL(array_t)) { 00223 /* if no strides are specified, the variables are not interleaved */ 00224 /* i.e. mvar_strides = 1 */ 00225 /* must set a flag to know that this array needs to be freed */ 00226 free_mvar_strides_flag = TRUE; 00227 mvar_strides = array_alloc(int, 0); 00228 for (i=0; i<no_mvars; i++) { 00229 array_insert_last(int, mvar_strides, 1); 00230 } 00231 } 00232 else { 00233 free_mvar_strides_flag = FALSE; 00234 if (no_mvars != array_n(mvar_strides)) 00235 fail("mdd_init: inconsistent size of mvar_strides\n"); 00236 } 00237 00238 00239 mdd_record_variables(mgr, current_vertex, 0, no_mvars, mvar_names, mvar_values, mvar_strides); 00240 00241 if (free_mvar_strides_flag) { 00242 array_free(mvar_strides); 00243 } 00244 00245 if (free_mvar_names_flag) { 00246 for (i = 0; i < array_n(mvar_names); i++) { 00247 char *name = array_fetch(char *, mvar_names, i); 00248 FREE(name); 00249 } 00250 array_free(mvar_names); 00251 } 00252 00253 return mgr; 00254 }
mdd_manager* mdd_init_empty | ( | void | ) |
Definition at line 538 of file mdd_init.c.
00539 { 00540 array_t *empty_array = array_alloc(int, 0); 00541 mdd_manager *mdd_mgr = mdd_init(empty_array, NIL(array_t), NIL(array_t)); 00542 00543 array_free(empty_array); 00544 return mdd_mgr; 00545 }
static void mdd_name_variables | ( | array_t * | mvar_list, | |
int | no_mvars, | |||
array_t ** | mvar_names_ptr | |||
) | [static] |
Definition at line 39 of file mdd_init.c.
00043 { 00044 00045 char *istr; 00046 int i; 00047 00048 if (*mvar_names_ptr == NIL(array_t)) { 00049 /* if no variable names are given, use generic naming */ 00050 /* mv_0, mv_1, ... for variable 0, 1, ... */ 00051 *mvar_names_ptr = array_alloc(char *, 0); 00052 for (i=0; i<no_mvars; i++) { 00053 /* compose a name for the mvar */ 00054 istr = ALLOC(char, integer_get_num_of_digits(i + array_n(mvar_list)) + 4); 00055 sprintf(istr, "mv_%d", (i + array_n(mvar_list))); 00056 array_insert_last(char *, *mvar_names_ptr, istr); 00057 00058 } 00059 } 00060 else { 00061 if (no_mvars != array_n(*mvar_names_ptr)) 00062 fail("mdd_init: inconsistent size of mvar_names\n"); 00063 } 00064 }
static void mdd_record_variables | ( | mdd_manager * | mgr, | |
int | current_vertex_before, | |||
int | start_mvar, | |||
int | no_mvars, | |||
array_t * | mvar_names, | |||
array_t * | mvar_values, | |||
array_t * | mvar_strides | |||
) | [static] |
Definition at line 68 of file mdd_init.c.
00076 { 00077 00078 array_t *mvar_list = mdd_ret_mvar_list(mgr); 00079 array_t *bvar_list = mdd_ret_bvar_list(mgr); 00080 int stride_count = 1; 00081 int prev_stride = -1; 00082 int current_vertex = current_vertex_before; 00083 int stride, i, j, 00084 bits, n_bytes; 00085 mvar_type mv; 00086 bvar_type bv; 00087 char *name_str, *mv_name; 00088 00089 #if MDD_VERBOSE 00090 printf("bdd variable insertion ordering: "); 00091 #endif 00092 00093 /* mvar_values -> mvar_list */ 00094 for (i=0; i<no_mvars; i++) { 00095 mv.mvar_id = start_mvar + i; 00096 00097 /* compose a name for the mvar */ 00098 name_str = array_fetch(char *, mvar_names, i); 00099 n_bytes = strlen (name_str) + 1; 00100 mv_name = ALLOC(char, n_bytes); 00101 strcpy(mv_name, name_str); 00102 mv.name = mv_name; 00103 00104 /* register no. of values for the mvar */ 00105 mv.values = array_fetch(int, mvar_values, i); 00106 00107 /* length of ecoding bits for mvar */ 00108 bits = no_bit_encode(mv.values); 00109 mv.encode_length = bits; 00110 00111 /* register the starting bdd vertex no. for the mvar */ 00112 mv.bvars = array_alloc(int, 0); 00113 00114 if (bits > 0) 00115 stride = array_fetch(int, mvar_strides, i); 00116 else 00117 stride = 1; 00118 for(j=0; j<bits; j++) array_insert_last(int, mv.bvars, current_vertex + (j * stride) ); 00119 00120 00121 /* create place-holder for bit-encoding of the mvar */ 00122 mv.encoding = ALLOC(int, bits); 00123 00124 /* create bdd variables and put them in bvar_list */ 00125 for (j=0; j<bits; j++) { 00126 bv.node = bdd_get_variable(mgr, current_vertex + stride*j); 00127 bv.mvar_id = mv.mvar_id; 00128 00129 #if MDD_VERBOSE 00130 printf("%d ", current_vertex + stride*j); 00131 #endif 00132 00133 array_insert(bvar_type, bvar_list, current_vertex + stride*j, bv); 00134 } 00135 00136 /* insert the completed mvar_type element to mvar_list */ 00137 mv.status = MDD_ACTIVE; 00138 array_insert_last(mvar_type, mvar_list, mv); 00139 00140 if ((prev_stride != -1 ) && (stride != prev_stride)) { 00141 printf("mdd_record_variables: processing %s\n", mv.name); 00142 fail("mdd_record_variables: inconsistency found in mvar_stride\n"); 00143 } 00144 00145 /* register the stride for mvar interleaving */ 00146 /* and update current bdd vertex count */ 00147 if (stride_count == stride) { 00148 stride_count = 1; 00149 current_vertex = current_vertex + stride*(bits-1) + 1; 00150 prev_stride = -1; 00151 } 00152 else { 00153 stride_count++; 00154 current_vertex++; 00155 prev_stride = stride; 00156 } 00157 } 00158 00159 #if MDD_VERBOSE 00160 printf("\n"); 00161 #endif 00162 00163 /* init all encodings to 2's */ 00164 clear_all_marks(mgr); 00165 00166 #if MONITOR 00167 print_mvar_list(mgr); 00168 (void) printf("%d bdd variables created\n", array_n(bvar_list)); 00169 print_bvar_list_id(mgr); 00170 #endif 00171 00172 }
void mdd_var_expunge_bdd_variable | ( | mdd_manager * | mgr, | |
int | bddId, | |||
int | val | |||
) |
Definition at line 551 of file mdd_init.c.
00556 { 00557 array_t *mvar_list = mdd_ret_mvar_list(mgr); 00558 array_t *bvar_list = mdd_ret_bvar_list(mgr); 00559 array_t *bvars; 00560 00561 bvar_type bddVar; 00562 mvar_type mvVar; 00563 int position, i, id, shift, values; 00564 00565 /* Check arguments. */ 00566 if (val != 0 && val != 1) fail("value must be either 0 or 1"); 00567 if (bddId < 0 || bddId >= array_n(bvar_list)) fail("bddId out of range"); 00568 00569 /* Extract info. */ 00570 bddVar = array_fetch(bvar_type, bvar_list, bddId); 00571 mvVar = array_fetch(mvar_type, mvar_list, bddVar.mvar_id); 00572 bvars = array_alloc(int,array_n(mvVar.bvars)-1); 00573 00574 /* Expunge fixed variable from list of BDD variables. */ 00575 position = array_n(mvVar.bvars); /* initialization for later checking */ 00576 arrayForEachItem(int, mvVar.bvars, i, id) { 00577 if (id != bddId) 00578 array_insert_last(int, bvars, id); 00579 else 00580 position = i; 00581 } 00582 /* Make sure we wrote position in the loop. */ 00583 assert(position < array_n(mvVar.bvars)); 00584 00585 /* Count number of surviving values. */ 00586 shift = (mvVar.encode_length - position - 1); 00587 00588 for (i = 0, values = 0; i < mvVar.values; i++) { 00589 values += (i >> shift) ^ ~val; 00590 } 00591 00592 /* Update mvar_list */ 00593 array_free(mvVar.bvars); 00594 mvVar.bvars = bvars; 00595 mvVar.values = values; 00596 mvVar.encode_length--; 00597 array_insert(mvar_type, mvar_list, bddVar.mvar_id, mvVar); 00598 00599 /* Update bvar_list. */ 00600 bvar_type bv = array_fetch(bvar_type, bvar_list, bddId); 00601 bv.mvar_id = -1; 00602 array_insert(bvar_type, bvar_list, bddId, bv); 00603 00604 } /* mdd_var_expunge_bdd_variable */