ABC: A System for Sequential Synthesis and Verification
 
Loading...
Searching...
No Matches
extraBddTime.c
Go to the documentation of this file.
1
18
19#include "extraBdd.h"
20
22
23
24/*---------------------------------------------------------------------------*/
25/* Constant declarations */
26/*---------------------------------------------------------------------------*/
27
28#define CHECK_FACTOR 10
29
30/*---------------------------------------------------------------------------*/
31/* Stucture declarations */
32/*---------------------------------------------------------------------------*/
33
34/*---------------------------------------------------------------------------*/
35/* Type declarations */
36/*---------------------------------------------------------------------------*/
37
38
39/*---------------------------------------------------------------------------*/
40/* Variable declarations */
41/*---------------------------------------------------------------------------*/
42
43
44
45/*---------------------------------------------------------------------------*/
46/* Macro declarations */
47/*---------------------------------------------------------------------------*/
48
49
51
52/*---------------------------------------------------------------------------*/
53/* Static function prototypes */
54/*---------------------------------------------------------------------------*/
55
56static DdNode * cuddBddAndRecurTime( DdManager * manager, DdNode * f, DdNode * g, int * pRecCalls, int TimeOut );
57static DdNode * cuddBddAndAbstractRecurTime( DdManager * manager, DdNode * f, DdNode * g, DdNode * cube, int * pRecCalls, int TimeOut );
58static DdNode * extraTransferPermuteTime( DdManager * ddS, DdManager * ddD, DdNode * f, int * Permute, int TimeOut );
59static DdNode * extraTransferPermuteRecurTime( DdManager * ddS, DdManager * ddD, DdNode * f, st__table * table, int * Permute, int TimeOut );
60
62
63
64/*---------------------------------------------------------------------------*/
65/* Definition of exported functions */
66/*---------------------------------------------------------------------------*/
67
82DdNode *
84 DdManager * dd,
85 DdNode * f,
86 DdNode * g,
87 int TimeOut)
88{
89 DdNode *res;
90 int Counter = 0;
91
92 do {
93 dd->reordered = 0;
94 res = cuddBddAndRecurTime(dd,f,g, &Counter, TimeOut);
95 } while (dd->reordered == 1);
96 return(res);
97
98} /* end of Extra_bddAndTime */
99
116DdNode *
118 DdManager * manager,
119 DdNode * f,
120 DdNode * g,
121 DdNode * cube,
122 int TimeOut)
123{
124 DdNode *res;
125 int Counter = 0;
126
127 do {
128 manager->reordered = 0;
129 res = cuddBddAndAbstractRecurTime(manager, f, g, cube, &Counter, TimeOut);
130 } while (manager->reordered == 1);
131 return(res);
132
133} /* end of Extra_bddAndAbstractTime */
134
150DdNode * Extra_TransferPermuteTime( DdManager * ddSource, DdManager * ddDestination, DdNode * f, int * Permute, int TimeOut )
151{
152 DdNode * bRes;
153 do
154 {
155 ddDestination->reordered = 0;
156 bRes = extraTransferPermuteTime( ddSource, ddDestination, f, Permute, TimeOut );
157 }
158 while ( ddDestination->reordered == 1 );
159 return ( bRes );
160
161} /* end of Extra_TransferPermuteTime */
162
163
164/*---------------------------------------------------------------------------*/
165/* Definition of internal functions */
166/*---------------------------------------------------------------------------*/
167
181DdNode *
182cuddBddAndRecurTime(
183 DdManager * manager,
184 DdNode * f,
185 DdNode * g,
186 int * pRecCalls,
187 int TimeOut)
188{
189 DdNode *F, *fv, *fnv, *G, *gv, *gnv;
190 DdNode *one, *r, *t, *e;
191 unsigned int topf, topg, index;
192
193 statLine(manager);
194 one = DD_ONE(manager);
195
196 /* Terminal cases. */
197 F = Cudd_Regular(f);
198 G = Cudd_Regular(g);
199 if (F == G) {
200 if (f == g) return(f);
201 else return(Cudd_Not(one));
202 }
203 if (F == one) {
204 if (f == one) return(g);
205 else return(f);
206 }
207 if (G == one) {
208 if (g == one) return(f);
209 else return(g);
210 }
211
212 /* At this point f and g are not constant. */
213 if (f > g) { /* Try to increase cache efficiency. */
214 DdNode *tmp = f;
215 f = g;
216 g = tmp;
217 F = Cudd_Regular(f);
218 G = Cudd_Regular(g);
219 }
220
221 /* Check cache. */
222 if (F->ref != 1 || G->ref != 1) {
223 r = cuddCacheLookup2(manager, Cudd_bddAnd, f, g);
224 if (r != NULL) return(r);
225 }
226
227// if ( TimeOut && ((*pRecCalls)++ % CHECK_FACTOR) == 0 && TimeOut < Abc_Clock() )
228 if ( TimeOut && Abc_Clock() > TimeOut )
229 return NULL;
230
231 /* Here we can skip the use of cuddI, because the operands are known
232 ** to be non-constant.
233 */
234 topf = manager->perm[F->index];
235 topg = manager->perm[G->index];
236
237 /* Compute cofactors. */
238 if (topf <= topg) {
239 index = F->index;
240 fv = cuddT(F);
241 fnv = cuddE(F);
242 if (Cudd_IsComplement(f)) {
243 fv = Cudd_Not(fv);
244 fnv = Cudd_Not(fnv);
245 }
246 } else {
247 index = G->index;
248 fv = fnv = f;
249 }
250
251 if (topg <= topf) {
252 gv = cuddT(G);
253 gnv = cuddE(G);
254 if (Cudd_IsComplement(g)) {
255 gv = Cudd_Not(gv);
256 gnv = Cudd_Not(gnv);
257 }
258 } else {
259 gv = gnv = g;
260 }
261
262 t = cuddBddAndRecurTime(manager, fv, gv, pRecCalls, TimeOut);
263 if (t == NULL) return(NULL);
264 cuddRef(t);
265
266 e = cuddBddAndRecurTime(manager, fnv, gnv, pRecCalls, TimeOut);
267 if (e == NULL) {
268 Cudd_IterDerefBdd(manager, t);
269 return(NULL);
270 }
271 cuddRef(e);
272
273 if (t == e) {
274 r = t;
275 } else {
276 if (Cudd_IsComplement(t)) {
277 r = cuddUniqueInter(manager,(int)index,Cudd_Not(t),Cudd_Not(e));
278 if (r == NULL) {
279 Cudd_IterDerefBdd(manager, t);
280 Cudd_IterDerefBdd(manager, e);
281 return(NULL);
282 }
283 r = Cudd_Not(r);
284 } else {
285 r = cuddUniqueInter(manager,(int)index,t,e);
286 if (r == NULL) {
287 Cudd_IterDerefBdd(manager, t);
288 Cudd_IterDerefBdd(manager, e);
289 return(NULL);
290 }
291 }
292 }
293 cuddDeref(e);
294 cuddDeref(t);
295 if (F->ref != 1 || G->ref != 1)
296 cuddCacheInsert2(manager, Cudd_bddAnd, f, g, r);
297 return(r);
298
299} /* end of cuddBddAndRecur */
300
301
316DdNode *
317cuddBddAndAbstractRecurTime(
318 DdManager * manager,
319 DdNode * f,
320 DdNode * g,
321 DdNode * cube,
322 int * pRecCalls,
323 int TimeOut)
324{
325 DdNode *F, *ft, *fe, *G, *gt, *ge;
326 DdNode *one, *zero, *r, *t, *e;
327 unsigned int topf, topg, topcube, top, index;
328
329 statLine(manager);
330 one = DD_ONE(manager);
331 zero = Cudd_Not(one);
332
333 /* Terminal cases. */
334 if (f == zero || g == zero || f == Cudd_Not(g)) return(zero);
335 if (f == one && g == one) return(one);
336
337 if (cube == one) {
338 return(cuddBddAndRecurTime(manager, f, g, pRecCalls, TimeOut));
339 }
340 if (f == one || f == g) {
341 return(cuddBddExistAbstractRecur(manager, g, cube));
342 }
343 if (g == one) {
344 return(cuddBddExistAbstractRecur(manager, f, cube));
345 }
346 /* At this point f, g, and cube are not constant. */
347
348 if (f > g) { /* Try to increase cache efficiency. */
349 DdNode *tmp = f;
350 f = g;
351 g = tmp;
352 }
353
354 /* Here we can skip the use of cuddI, because the operands are known
355 ** to be non-constant.
356 */
357 F = Cudd_Regular(f);
358 G = Cudd_Regular(g);
359 topf = manager->perm[F->index];
360 topg = manager->perm[G->index];
361 top = ddMin(topf, topg);
362 topcube = manager->perm[cube->index];
363
364 while (topcube < top) {
365 cube = cuddT(cube);
366 if (cube == one) {
367 return(cuddBddAndRecurTime(manager, f, g, pRecCalls, TimeOut));
368 }
369 topcube = manager->perm[cube->index];
370 }
371 /* Now, topcube >= top. */
372
373 /* Check cache. */
374 if (F->ref != 1 || G->ref != 1) {
375 r = cuddCacheLookup(manager, DD_BDD_AND_ABSTRACT_TAG, f, g, cube);
376 if (r != NULL) {
377 return(r);
378 }
379 }
380
381// if ( TimeOut && ((*pRecCalls)++ % CHECK_FACTOR) == 0 && TimeOut < Abc_Clock() )
382 if ( TimeOut && Abc_Clock() > TimeOut )
383 return NULL;
384
385 if (topf == top) {
386 index = F->index;
387 ft = cuddT(F);
388 fe = cuddE(F);
389 if (Cudd_IsComplement(f)) {
390 ft = Cudd_Not(ft);
391 fe = Cudd_Not(fe);
392 }
393 } else {
394 index = G->index;
395 ft = fe = f;
396 }
397
398 if (topg == top) {
399 gt = cuddT(G);
400 ge = cuddE(G);
401 if (Cudd_IsComplement(g)) {
402 gt = Cudd_Not(gt);
403 ge = Cudd_Not(ge);
404 }
405 } else {
406 gt = ge = g;
407 }
408
409 if (topcube == top) { /* quantify */
410 DdNode *Cube = cuddT(cube);
411 t = cuddBddAndAbstractRecurTime(manager, ft, gt, Cube, pRecCalls, TimeOut);
412 if (t == NULL) return(NULL);
413 /* Special case: 1 OR anything = 1. Hence, no need to compute
414 ** the else branch if t is 1. Likewise t + t * anything == t.
415 ** Notice that t == fe implies that fe does not depend on the
416 ** variables in Cube. Likewise for t == ge.
417 */
418 if (t == one || t == fe || t == ge) {
419 if (F->ref != 1 || G->ref != 1)
420 cuddCacheInsert(manager, DD_BDD_AND_ABSTRACT_TAG,
421 f, g, cube, t);
422 return(t);
423 }
424 cuddRef(t);
425 /* Special case: t + !t * anything == t + anything. */
426 if (t == Cudd_Not(fe)) {
427 e = cuddBddExistAbstractRecur(manager, ge, Cube);
428 } else if (t == Cudd_Not(ge)) {
429 e = cuddBddExistAbstractRecur(manager, fe, Cube);
430 } else {
431 e = cuddBddAndAbstractRecurTime(manager, fe, ge, Cube, pRecCalls, TimeOut);
432 }
433 if (e == NULL) {
434 Cudd_IterDerefBdd(manager, t);
435 return(NULL);
436 }
437 if (t == e) {
438 r = t;
439 cuddDeref(t);
440 } else {
441 cuddRef(e);
442 r = cuddBddAndRecurTime(manager, Cudd_Not(t), Cudd_Not(e), pRecCalls, TimeOut);
443 if (r == NULL) {
444 Cudd_IterDerefBdd(manager, t);
445 Cudd_IterDerefBdd(manager, e);
446 return(NULL);
447 }
448 r = Cudd_Not(r);
449 cuddRef(r);
450 Cudd_DelayedDerefBdd(manager, t);
451 Cudd_DelayedDerefBdd(manager, e);
452 cuddDeref(r);
453 }
454 } else {
455 t = cuddBddAndAbstractRecurTime(manager, ft, gt, cube, pRecCalls, TimeOut);
456 if (t == NULL) return(NULL);
457 cuddRef(t);
458 e = cuddBddAndAbstractRecurTime(manager, fe, ge, cube, pRecCalls, TimeOut);
459 if (e == NULL) {
460 Cudd_IterDerefBdd(manager, t);
461 return(NULL);
462 }
463 if (t == e) {
464 r = t;
465 cuddDeref(t);
466 } else {
467 cuddRef(e);
468 if (Cudd_IsComplement(t)) {
469 r = cuddUniqueInter(manager, (int) index,
470 Cudd_Not(t), Cudd_Not(e));
471 if (r == NULL) {
472 Cudd_IterDerefBdd(manager, t);
473 Cudd_IterDerefBdd(manager, e);
474 return(NULL);
475 }
476 r = Cudd_Not(r);
477 } else {
478 r = cuddUniqueInter(manager,(int)index,t,e);
479 if (r == NULL) {
480 Cudd_IterDerefBdd(manager, t);
481 Cudd_IterDerefBdd(manager, e);
482 return(NULL);
483 }
484 }
485 cuddDeref(e);
486 cuddDeref(t);
487 }
488 }
489
490 if (F->ref != 1 || G->ref != 1)
491 cuddCacheInsert(manager, DD_BDD_AND_ABSTRACT_TAG, f, g, cube, r);
492 return (r);
493
494} /* end of cuddBddAndAbstractRecur */
495
496/*---------------------------------------------------------------------------*/
497/* Definition of static functions */
498/*---------------------------------------------------------------------------*/
499
513DdNode * extraTransferPermuteTime( DdManager * ddS, DdManager * ddD, DdNode * f, int * Permute, int TimeOut )
514{
515 DdNode *res;
516 st__table *table = NULL;
517 st__generator *gen = NULL;
518 DdNode *key, *value;
519
521 if ( table == NULL )
522 goto failure;
523 res = extraTransferPermuteRecurTime( ddS, ddD, f, table, Permute, TimeOut );
524 if ( res != NULL )
525 cuddRef( res );
526
527 /* Dereference all elements in the table and dispose of the table.
528 ** This must be done also if res is NULL to avoid leaks in case of
529 ** reordering. */
530 gen = st__init_gen( table );
531 if ( gen == NULL )
532 goto failure;
533 while ( st__gen( gen, ( const char ** ) &key, ( char ** ) &value ) )
534 {
535 Cudd_RecursiveDeref( ddD, value );
536 }
537 st__free_gen( gen );
538 gen = NULL;
539 st__free_table( table );
540 table = NULL;
541
542 if ( res != NULL )
543 cuddDeref( res );
544 return ( res );
545
546 failure:
547 if ( table != NULL )
548 st__free_table( table );
549 if ( gen != NULL )
550 st__free_gen( gen );
551 return ( NULL );
552
553} /* end of extraTransferPermuteTime */
554
555
568static DdNode *
569extraTransferPermuteRecurTime(
570 DdManager * ddS,
571 DdManager * ddD,
572 DdNode * f,
573 st__table * table,
574 int * Permute,
575 int TimeOut )
576{
577 DdNode *ft, *fe, *t, *e, *var, *res;
578 DdNode *one, *zero;
579 int index;
580 int comple = 0;
581
582 statLine( ddD );
583 one = DD_ONE( ddD );
584 comple = Cudd_IsComplement( f );
585
586 /* Trivial cases. */
587 if ( Cudd_IsConstant( f ) )
588 return ( Cudd_NotCond( one, comple ) );
589
590
591 /* Make canonical to increase the utilization of the cache. */
592 f = Cudd_NotCond( f, comple );
593 /* Now f is a regular pointer to a non-constant node. */
594
595 /* Check the cache. */
596 if ( st__lookup( table, ( char * ) f, ( char ** ) &res ) )
597 return ( Cudd_NotCond( res, comple ) );
598
599 if ( TimeOut && Abc_Clock() > TimeOut )
600 return NULL;
601
602 /* Recursive step. */
603 if ( Permute )
604 index = Permute[f->index];
605 else
606 index = f->index;
607
608 ft = cuddT( f );
609 fe = cuddE( f );
610
611 t = extraTransferPermuteRecurTime( ddS, ddD, ft, table, Permute, TimeOut );
612 if ( t == NULL )
613 {
614 return ( NULL );
615 }
616 cuddRef( t );
617
618 e = extraTransferPermuteRecurTime( ddS, ddD, fe, table, Permute, TimeOut );
619 if ( e == NULL )
620 {
621 Cudd_RecursiveDeref( ddD, t );
622 return ( NULL );
623 }
624 cuddRef( e );
625
626 zero = Cudd_Not(ddD->one);
627 var = cuddUniqueInter( ddD, index, one, zero );
628 if ( var == NULL )
629 {
630 Cudd_RecursiveDeref( ddD, t );
631 Cudd_RecursiveDeref( ddD, e );
632 return ( NULL );
633 }
634 res = cuddBddIteRecur( ddD, var, t, e );
635
636 if ( res == NULL )
637 {
638 Cudd_RecursiveDeref( ddD, t );
639 Cudd_RecursiveDeref( ddD, e );
640 return ( NULL );
641 }
642 cuddRef( res );
643 Cudd_RecursiveDeref( ddD, t );
644 Cudd_RecursiveDeref( ddD, e );
645
646 if ( st__add_direct( table, ( char * ) f, ( char * ) res ) ==
648 {
649 Cudd_RecursiveDeref( ddD, res );
650 return ( NULL );
651 }
652 return ( Cudd_NotCond( res, comple ) );
653
654} /* end of extraTransferPermuteRecurTime */
655
660
#define ABC_NAMESPACE_IMPL_START
#define ABC_NAMESPACE_IMPL_END
ABC_NAMESPACE_IMPL_START typedef signed char value
struct cube Cube
DdNode * Extra_TransferPermuteTime(DdManager *ddSource, DdManager *ddDestination, DdNode *f, int *Permute, int TimeOut)
DdNode * Extra_bddAndTime(DdManager *dd, DdNode *f, DdNode *g, int TimeOut)
DdNode * Extra_bddAndAbstractTime(DdManager *manager, DdNode *f, DdNode *g, DdNode *cube, int TimeOut)
enum keys key
Definition main.h:25
unsigned short var
Definition giaNewBdd.h:35
int st__gen(st__generator *gen, const char **key_p, char **value_p)
Definition st.c:501
int st__ptrhash(const char *, int)
Definition st.c:467
int st__ptrcmp(const char *, const char *)
Definition st.c:479
void st__free_gen(st__generator *gen)
Definition st.c:555
int st__lookup(st__table *table, const char *key, char **value)
Definition st.c:114
st__table * st__init_table(st__compare_func_type compare, st__hash_func_type hash)
Definition st.c:72
st__generator * st__init_gen(st__table *table)
Definition st.c:485
int st__add_direct(st__table *table, char *key, char *value)
Definition st.c:205
void st__free_table(st__table *table)
Definition st.c:81
#define st__OUT_OF_MEM
Definition st.h:113
Definition exor.h:123
Definition st.h:52