79 #define MV_OOM (Move *)1
94 static char rcsid[]
DD_UNUSED =
"$Id: cuddSymmetry.c,v 1.26 2009/02/19 16:23:54 fabio Exp $";
101 extern int ddTotalNISwaps;
149 int TotalSymmGroups = 0;
151 for (i = lower; i <= upper; i++) {
154 (void) fprintf(table->
out,
"Group:");
156 (void) fprintf(table->
out,
" %d",table->
invperm[x]);
166 (void) fprintf(table->
out,
"\n");
169 (void) fprintf(table->
out,
"Total Symmetric = %d\n",TotalSymm);
170 (void) fprintf(table->
out,
"Total Groups = %d\n",TotalSymmGroups);
197 DdNode *f,*f0,*f1,*f01,*f00,*f11,*f10;
223 if (table->
vars[yindex]->
ref == 1)
227 xsymmy = xsymmyp = 1;
231 for (i = 0; i < slots; i++) {
233 while (f != sentinel) {
238 if ((
int) f1->
index == yindex) {
242 if ((
int) f0->
index != yindex) {
251 if ((
int) f0->
index == yindex) {
263 xsymmy &= f01 == f10;
264 xsymmyp &= f11 == f00;
265 if ((xsymmy == 0) && (xsymmyp == 0))
277 for (i = 0; i < slots; i++) {
279 while (f != sentinel) {
280 TotalRefCount += f->
ref;
285 #if defined(DD_DEBUG) && defined(DD_VERBOSE)
286 if (arccount == TotalRefCount) {
288 (void) fprintf(table->
out,
289 "Found symmetry! x =%d\ty = %d\tPos(%d,%d)\n",
294 return(arccount == TotalRefCount);
345 goto ddSymmSiftingOutOfMem;
350 goto ddSymmSiftingOutOfMem;
353 for (i = 0; i <
size; i++) {
362 for (i = lower; i <= upper; i++) {
372 x = table->
perm[var[i]];
376 if (x < lower || x > upper)
continue;
379 if (!result)
goto ddSymmSiftingOutOfMem;
381 if (table->
keys < (
unsigned) previousSize + table->
isolated) {
382 (void) fprintf(table->
out,
"-");
383 }
else if (table->
keys > (
unsigned) previousSize +
385 (void) fprintf(table->
out,
"+");
387 (void) fprintf(table->
out,
"=");
400 (void) fprintf(table->
out,
"\n#:S_SIFTING %8d: symmetric variables\n",
402 (void) fprintf(table->
out,
"#:G_SIFTING %8d: symmetric groups",
408 ddSymmSiftingOutOfMem:
469 goto ddSymmSiftingConvOutOfMem;
474 goto ddSymmSiftingConvOutOfMem;
477 for (i = 0; i <
size; i++) {
488 for (i = lower; i <= upper; i++) {
495 x = table->
perm[var[i]];
496 if (x < lower || x > upper)
continue;
503 if (!result)
goto ddSymmSiftingConvOutOfMem;
505 if (table->
keys < (
unsigned) previousSize + table->
isolated) {
506 (void) fprintf(table->
out,
"-");
507 }
else if (table->
keys > (
unsigned) previousSize +
509 (void) fprintf(table->
out,
"+");
511 (void) fprintf(table->
out,
"=");
519 while ((
unsigned) initialSize > table->
keys - table->
isolated) {
522 (void) fprintf(table->
out,
"\n");
525 for (x = lower, classes = 0; x <= upper; x++, classes++) {
538 qsort((
void *)var,classes,
sizeof(
int),(
DD_QSFP)ddSymmUniqueCompare);
544 x = table->
perm[var[i]];
550 if (!result )
goto ddSymmSiftingConvOutOfMem;
552 if (table->
keys < (
unsigned) previousSize + table->
isolated) {
553 (void) fprintf(table->
out,
"-");
554 }
else if (table->
keys > (
unsigned) previousSize +
556 (void) fprintf(table->
out,
"+");
558 (void) fprintf(table->
out,
"=");
569 (void) fprintf(table->
out,
"\n#:S_SIFTING %8d: symmetric variables\n",
571 (void) fprintf(table->
out,
"#:G_SIFTING %8d: symmetric groups",
580 ddSymmSiftingConvOutOfMem:
614 return((*ptrX) - (*ptrY));
649 int initGroupSize, finalGroupSize;
662 if ((x - xLow) > (xHigh - x)) {
666 for (i = x; i > xLow; i--) {
679 for (i = x; i < xHigh; i++) {
684 while ((
unsigned) topbot < table->subtables[topbot].next) {
696 while ((
unsigned) x < table->subtables[x].next)
705 if (x == xHigh)
return(1);
711 if (moveDown ==
MV_OOM)
goto ddSymmSiftingAuxOutOfMem;
712 if (moveDown == NULL)
return(1);
717 while ((
unsigned) i < table->subtables[i].next) {
725 finalGroupSize = i - x + 1;
727 if (initGroupSize == finalGroupSize) {
735 if (!result)
goto ddSymmSiftingAuxOutOfMem;
742 if (x == xLow)
return(1);
744 initGroupSize = i - x + 1;
748 if (moveUp ==
MV_OOM)
goto ddSymmSiftingAuxOutOfMem;
749 if (moveUp == NULL)
return(1);
759 finalGroupSize = x - i + 1;
761 if (initGroupSize == finalGroupSize) {
769 if (!result)
goto ddSymmSiftingAuxOutOfMem;
771 }
else if ((x - xLow) > (xHigh - x)) {
775 if (moveDown ==
MV_OOM)
goto ddSymmSiftingAuxOutOfMem;
777 if (moveDown != NULL) {
780 while ((
unsigned) i < table->subtables[i].next) {
785 while ((
unsigned) i < table->subtables[i].next) {
795 initGroupSize = i - x + 1;
798 if (moveUp ==
MV_OOM)
goto ddSymmSiftingAuxOutOfMem;
800 if (moveUp != NULL) {
805 while ((
unsigned) x < table->subtables[x].next)
813 finalGroupSize = x - i + 1;
815 if (initGroupSize == finalGroupSize) {
819 while (moveDown != NULL) {
820 move = moveDown->
next;
828 if (!result)
goto ddSymmSiftingAuxOutOfMem;
836 if (moveUp ==
MV_OOM)
goto ddSymmSiftingAuxOutOfMem;
838 if (moveUp != NULL) {
842 while ((
unsigned) x < table->subtables[x].next)
851 initGroupSize = x - i + 1;
854 if (moveDown ==
MV_OOM)
goto ddSymmSiftingAuxOutOfMem;
856 if (moveDown != NULL) {
859 while ((
unsigned) i < table->subtables[i].next) {
871 finalGroupSize = i - x + 1;
873 if (initGroupSize == finalGroupSize) {
877 while (moveUp != NULL) {
886 if (!result)
goto ddSymmSiftingAuxOutOfMem;
889 while (moveDown != NULL) {
890 move = moveDown->
next;
894 while (moveUp != NULL) {
902 ddSymmSiftingAuxOutOfMem:
904 while (moveDown != NULL) {
905 move = moveDown->
next;
911 while (moveUp != NULL) {
950 int initGroupSize, finalGroupSize;
964 initGroupSize = x - i + 1;
968 if (moveDown ==
MV_OOM)
goto ddSymmSiftingConvAuxOutOfMem;
969 if (moveDown == NULL)
return(1);
973 while ((
unsigned) i < table->subtables[i].next) {
981 finalGroupSize = i - x + 1;
983 if (initGroupSize == finalGroupSize) {
991 if (!result)
goto ddSymmSiftingConvAuxOutOfMem;
995 while ((
unsigned) x < table->subtables[x].next)
1000 if (x == xLow)
return(1);
1002 initGroupSize = i - x + 1;
1006 if (moveUp ==
MV_OOM)
goto ddSymmSiftingConvAuxOutOfMem;
1007 if (moveUp == NULL)
return(1);
1016 finalGroupSize = x - i + 1;
1018 if (initGroupSize == finalGroupSize) {
1027 goto ddSymmSiftingConvAuxOutOfMem;
1029 }
else if ((x - xLow) > (xHigh - x)) {
1032 if (moveDown ==
MV_OOM)
goto ddSymmSiftingConvAuxOutOfMem;
1034 if (moveDown != NULL) {
1037 while ((
unsigned) i < table->subtables[i].next) {
1041 while ((
unsigned) x < table->subtables[x].next)
1051 initGroupSize = i - x + 1;
1054 if (moveUp ==
MV_OOM)
goto ddSymmSiftingConvAuxOutOfMem;
1056 if (moveUp != NULL) {
1061 while ((
unsigned) x < table->subtables[x].next)
1069 finalGroupSize = x - i + 1;
1071 if (initGroupSize == finalGroupSize) {
1075 while (moveDown != NULL) {
1076 move = moveDown->
next;
1084 if (!result)
goto ddSymmSiftingConvAuxOutOfMem;
1092 if (moveUp ==
MV_OOM)
goto ddSymmSiftingConvAuxOutOfMem;
1094 if (moveUp != NULL) {
1099 while ((
unsigned) x < table->subtables[x].next)
1107 initGroupSize = x - i + 1;
1110 if (moveDown ==
MV_OOM)
goto ddSymmSiftingConvAuxOutOfMem;
1112 if (moveDown != NULL) {
1115 while ((
unsigned) i < table->subtables[i].next) {
1127 finalGroupSize = i - x + 1;
1129 if (initGroupSize == finalGroupSize) {
1133 while (moveUp != NULL) {
1134 move = moveUp->
next;
1142 if (!result)
goto ddSymmSiftingConvAuxOutOfMem;
1145 while (moveDown != NULL) {
1146 move = moveDown->
next;
1150 while (moveUp != NULL) {
1151 move = moveUp->
next;
1158 ddSymmSiftingConvAuxOutOfMem:
1159 if (moveDown !=
MV_OOM) {
1160 while (moveDown != NULL) {
1161 move = moveDown->
next;
1167 while (moveUp != NULL) {
1168 move = moveUp->
next;
1228 while ((
unsigned) gybot < table->subtables[gybot].next)
1230 for (z = xLow + 1; z <= gybot; z++) {
1233 isolated = table->
vars[zindex]->
ref == 1;
1239 while (x >= xLow && L <= limitSize) {
1242 while ((
unsigned) gybot < table->subtables[gybot].next)
1245 for (z = xLow + 1; z <= gybot; z++) {
1248 isolated = table->
vars[zindex]->
ref == 1;
1271 if (size == 0)
goto ddSymmSiftingUpOutOfMem;
1274 isolated = table->
vars[xindex]->
ref == 1;
1278 if (move == NULL)
goto ddSymmSiftingUpOutOfMem;
1284 if ((
double) size > (double) limitSize * table->
maxGrowth)
1286 if (size < limitSize) limitSize =
size;
1289 if (size == 0)
goto ddSymmSiftingUpOutOfMem;
1295 isolated = table->
vars[zindex]->
ref == 1;
1299 }
while (z != (
int) moves->
y);
1300 if ((
double) size > (
double) limitSize * table->
maxGrowth)
1302 if (size < limitSize) limitSize =
size;
1310 ddSymmSiftingUpOutOfMem:
1311 while (moves != NULL) {
1363 for (z = xHigh; z > gxtop; z--) {
1366 isolated = table->
vars[zindex]->
ref == 1;
1372 while (y <= xHigh && size - R < limitSize) {
1376 for (z = xHigh; z > gxtop; z--) {
1379 isolated = table->
vars[zindex]->
ref == 1;
1399 isolated = table->
vars[yindex]->
ref == 1;
1407 if (size == 0)
goto ddSymmSiftingDownOutOfMem;
1409 if (move == NULL)
goto ddSymmSiftingDownOutOfMem;
1415 if ((
double) size > (double) limitSize * table->
maxGrowth)
1417 if (size < limitSize) limitSize =
size;
1425 isolated = table->
vars[zindex]->
ref == 1;
1429 }
while (z <= gybot);
1431 if (size == 0)
goto ddSymmSiftingDownOutOfMem;
1432 if ((
double) size > (
double) limitSize * table->
maxGrowth)
1434 if (size < limitSize) limitSize =
size;
1437 for (z = gxtop + 1; z <= gybot; z++) {
1440 isolated = table->
vars[zindex]->
ref == 1;
1451 ddSymmSiftingDownOutOfMem:
1452 while (moves != NULL) {
1484 int xtop,xbot,xsize,ytop,ybot,ysize,newxtop;
1485 int swapx = -1,swapy = -1;
1493 xsize = xbot - xtop + 1;
1495 while ((
unsigned) ybot < table->subtables[ybot].next)
1498 ysize = ybot - ytop + 1;
1501 for (i = 1; i <= ysize; i++) {
1502 for (j = 1; j <= xsize; j++) {
1504 if (size == 0)
return(0);
1505 swapx = x; swapy = y;
1515 for (i = 0; i < ysize-1 ; i++) {
1523 for (i = 0; i < xsize - 1 ; i++) {
1531 if (move == NULL)
return(0);
1535 move->
next = *moves;
1563 int xtop,xbot,xsize,ytop,ybot,ysize,newxtop;
1572 xsize = xbot - xtop + 1;
1574 while ((
unsigned) ybot < table->subtables[ybot].next)
1577 ysize = ybot - ytop + 1;
1580 for (i = 1; i <= ysize; i++) {
1581 for (j = 1; j <= xsize; j++) {
1583 if (size == 0)
return(0);
1593 for (i = 0; i < ysize-1 ; i++) {
1601 for (i = 0; i < xsize-1 ; i++) {
1635 for (move = moves; move != NULL; move = move->
next) {
1636 if (move->
size < size) {
1641 for (move = moves; move != NULL; move = move->
next) {
1642 if (move->
size == size)
return(1);
1652 if (!res)
return(0);
1680 int TotalSymmGroups = 0;
1682 for (i = lower; i <= upper; i++) {
1697 *symvars = TotalSymm;
1698 *symgroups = TotalSymmGroups;
#define cuddDeallocMove(unique, node)
void Cudd_SymmProfile(DdManager *table, int lower, int upper)
static Move * ddSymmSiftingDown(DdManager *table, int x, int xHigh)
static int ddSymmGroupMoveBackward(DdManager *table, int x, int y)
int cuddSymmCheck(DdManager *table, int x, int y)
int(* DD_QSFP)(const void *, const void *)
#define Cudd_Regular(node)
int cuddNextLow(DdManager *table, int x)
#define ABC_ALLOC(type, num)
static abctime Abc_Clock()
#define Cudd_IsComplement(node)
static void ddSymmSummary(DdManager *table, int lower, int upper, int *symvars, int *symgroups)
#define ABC_NAMESPACE_IMPL_END
int cuddSymmSiftingConv(DdManager *table, int lower, int upper)
DdNode * cuddDynamicAllocNode(DdManager *table)
static int ddSymmSiftingConvAux(DdManager *table, int x, int xLow, int xHigh)
static int ddSymmSiftingBackward(DdManager *table, Move *moves, int size)
static Move * ddSymmSiftingUp(DdManager *table, int y, int xLow)
#define ABC_NAMESPACE_IMPL_START
int cuddNextHigh(DdManager *table, int x)
int cuddSwapInPlace(DdManager *table, int x, int y)
static char rcsid[] DD_UNUSED
int ddTotalNumberSwapping
int cuddTestInteract(DdManager *table, int x, int y)
static int ddSymmUniqueCompare(int *ptrX, int *ptrY)
static int ddSymmGroupMove(DdManager *table, int x, int y, Move **moves)
int cuddSymmSifting(DdManager *table, int lower, int upper)
static int ddSymmSiftingAux(DdManager *table, int x, int xLow, int xHigh)