State.java 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164
  1. // Copyright (C) 2010 by Yan Huang <yhuang@virginia.edu>
  2. package YaoGC;
  3. import java.math.*;
  4. public class State {
  5. public static class StaticWire {
  6. public int value = Wire.UNKNOWN_SIG;
  7. public BigInteger lbl = null;
  8. public boolean invd = false;
  9. StaticWire() {
  10. }
  11. public StaticWire(int v) {
  12. value = v;
  13. }
  14. public StaticWire(BigInteger label) {
  15. lbl = label;
  16. }
  17. }
  18. public StaticWire wires[];
  19. public BigInteger plainValue = null; // The non-negative integer the state
  20. // object represents.
  21. public State(StaticWire[] ws) {
  22. wires = ws;
  23. for (int i = 0; i < ws.length; i++) {
  24. if (ws[i].value == Wire.UNKNOWN_SIG) {
  25. plainValue = null;
  26. return;
  27. }
  28. }
  29. plainValue = BigInteger.ZERO;
  30. for (int i = 0; i < ws.length; i++) {
  31. if (ws[i].value == 1)
  32. plainValue = plainValue.setBit(i);
  33. }
  34. }
  35. public State(BigInteger v, int length) {
  36. wires = new StaticWire[length];
  37. for (int i = 0; i < length; i++) {
  38. wires[i] = new StaticWire();
  39. wires[i].value = v.testBit(i) ? 1 : 0;
  40. }
  41. plainValue = v;
  42. }
  43. private State(int length) {
  44. wires = new StaticWire[length];
  45. plainValue = null;
  46. }
  47. public static State flattenStateArray(State[] as) {
  48. State res = new State(as.length * as[0].wires.length);
  49. for (int i = 0; i < as.length; i++)
  50. for (int j = 0; j < as[0].wires.length; j++) {
  51. res.wires[i * 8 + j] = new StaticWire();
  52. res.wires[i * 8 + j].value = as[i].wires[j].value;
  53. res.wires[i * 8 + j].lbl = as[i].wires[j].lbl;
  54. res.wires[i * 8 + j].invd = as[i].wires[j].invd;
  55. }
  56. return res;
  57. }
  58. public static State extractState(State s, int start, int end) {
  59. State res = new State(end - start);
  60. for (int i = 0; i < end - start; i++) {
  61. res.wires[i] = new StaticWire();
  62. res.wires[i].value = s.wires[i + start].value;
  63. res.wires[i].lbl = s.wires[i + start].lbl;
  64. res.wires[i].invd = s.wires[i + start].invd;
  65. }
  66. return res;
  67. }
  68. public static State fromWires(Wire[] ws) {
  69. State.StaticWire[] swires = new State.StaticWire[ws.length];
  70. for (int i = 0; i < ws.length; i++) {
  71. swires[i] = new StaticWire();
  72. swires[i].value = ws[i].value;
  73. swires[i].lbl = ws[i].lbl;
  74. swires[i].invd = ws[i].invd;
  75. }
  76. return new State(swires);
  77. }
  78. public static State fromLabels(BigInteger[] lbs) {
  79. State res = new State(lbs.length);
  80. for (int i = 0; i < lbs.length; i++)
  81. res.wires[i] = new StaticWire(lbs[i]);
  82. return res;
  83. }
  84. public int getWidth() {
  85. return wires.length;
  86. }
  87. /*
  88. * Return "true" ONLY IF it is CERTAIN that the value denoted by "this"
  89. * object is larger than that denoted by "s". Namely, if "false" is
  90. * returned, it is still possible that ("this" > "s").
  91. */
  92. public boolean largerThan(State s) {
  93. if (plainValue != null && s.plainValue != null)
  94. return plainValue.compareTo(s.plainValue) > 0;
  95. return false; // this line should never be reached.
  96. }
  97. public static State signExtend(State s, int width) {
  98. if (s.getWidth() > width) {
  99. (new Exception("s is already wider than width.")).printStackTrace();
  100. System.exit(1);
  101. } else if (s.getWidth() == width)
  102. return s;
  103. State res = new State(width);
  104. for (int i = 0; i < width; i++)
  105. if (i < s.wires.length)
  106. res.wires[i] = s.wires[i];
  107. else
  108. res.wires[i] = s.wires[s.wires.length - 1];
  109. res.plainValue = s.plainValue;
  110. return res;
  111. }
  112. public static State concatenate(State s1, State s2) {
  113. int width = s1.getWidth() + s2.getWidth();
  114. State res = new State(width);
  115. for (int i = 0; i < width; i++)
  116. if (i < s2.wires.length)
  117. res.wires[i] = s2.wires[i];
  118. else
  119. res.wires[i] = s1.wires[i - s2.wires.length];
  120. if (s1.plainValue == null || s2.plainValue == null)
  121. res.plainValue = null;
  122. else
  123. res.plainValue = s1.plainValue.shiftLeft(s2.getWidth()).xor(
  124. s2.plainValue);
  125. return res;
  126. }
  127. public BigInteger[] toLabels() {
  128. BigInteger[] res = new BigInteger[getWidth()];
  129. for (int i = 0; i < res.length; i++)
  130. res[i] = wires[i].lbl;
  131. return res;
  132. }
  133. }