You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

217 lines
6.7 KiB

6 years ago
5 years ago
6 years ago
5 years ago
6 years ago
5 years ago
6 years ago
5 years ago
6 years ago
6 years ago
5 years ago
5 years ago
6 years ago
6 years ago
  1. const chai = require("chai");
  2. const path = require("path");
  3. const snarkjs = require("snarkjs");
  4. const compiler = require("circom");
  5. const smt = require("../src/smt.js");
  6. const assert = chai.assert;
  7. const bigInt = snarkjs.bigInt;
  8. function print(circuit, w, s) {
  9. console.log(s + ": " + w[circuit.getSignalIdx(s)]);
  10. }
  11. async function testInsert(tree, key, value, circuit, log ) {
  12. const res = await tree.insert(key,value);
  13. let siblings = res.siblings;
  14. while (siblings.length<10) siblings.push(bigInt(0));
  15. const w = circuit.calculateWitness({
  16. fnc: [1,0],
  17. oldRoot: res.oldRoot,
  18. siblings: siblings,
  19. oldKey: res.isOld0 ? 0 : res.oldKey,
  20. oldValue: res.isOld0 ? 0 : res.oldValue,
  21. isOld0: res.isOld0 ? 1 : 0,
  22. newKey: key,
  23. newValue: value
  24. }, log);
  25. const root1 = w[circuit.getSignalIdx("main.newRoot")];
  26. assert(circuit.checkWitness(w));
  27. assert(root1.equals(res.newRoot));
  28. }
  29. async function testDelete(tree, key, circuit) {
  30. const res = await tree.delete(key);
  31. let siblings = res.siblings;
  32. while (siblings.length<10) siblings.push(bigInt(0));
  33. const w = circuit.calculateWitness({
  34. fnc: [1,1],
  35. oldRoot: res.oldRoot,
  36. siblings: siblings,
  37. oldKey: res.isOld0 ? 0 : res.oldKey,
  38. oldValue: res.isOld0 ? 0 : res.oldValue,
  39. isOld0: res.isOld0 ? 1 : 0,
  40. newKey: res.delKey,
  41. newValue: res.delValue
  42. });
  43. const root1 = w[circuit.getSignalIdx("main.newRoot")];
  44. assert(circuit.checkWitness(w));
  45. assert(root1.equals(res.newRoot));
  46. }
  47. async function testUpdate(tree, key, newValue, circuit) {
  48. const res = await tree.update(key, newValue);
  49. let siblings = res.siblings;
  50. while (siblings.length<10) siblings.push(bigInt(0));
  51. const w = circuit.calculateWitness({
  52. fnc: [0,1],
  53. oldRoot: res.oldRoot,
  54. siblings: siblings,
  55. oldKey: res.oldKey,
  56. oldValue: res.oldValue,
  57. isOld0: 0,
  58. newKey: res.newKey,
  59. newValue: res.newValue
  60. });
  61. const root1 = w[circuit.getSignalIdx("main.newRoot")];
  62. assert(circuit.checkWitness(w));
  63. assert(root1.equals(res.newRoot));
  64. }
  65. describe("SMT test", function () {
  66. let circuit;
  67. let tree;
  68. this.timeout(10000000);
  69. before( async () => {
  70. const cirDef = await compiler(path.join(__dirname, "circuits", "smtprocessor10_test.circom"));
  71. circuit = new snarkjs.Circuit(cirDef);
  72. console.log("NConstrains SMTProcessor: " + circuit.nConstraints);
  73. tree = await smt.newMemEmptyTrie();
  74. });
  75. it("Should verify an insert to an empty tree", async () => {
  76. const key = bigInt(111);
  77. const value = bigInt(222);
  78. await testInsert(tree, key, value, circuit);
  79. });
  80. it("It should add another element", async () => {
  81. const key = bigInt(333);
  82. const value = bigInt(444);
  83. await testInsert(tree, key, value, circuit);
  84. });
  85. it("Should remove an element", async () => {
  86. await testDelete(tree, 111, circuit);
  87. await testDelete(tree, 333, circuit);
  88. });
  89. it("Should test convination of adding and removing 3 elements", async () => {
  90. const keys = [bigInt(8), bigInt(9), bigInt(32)];
  91. const values = [bigInt(88), bigInt(99), bigInt(3232)];
  92. const tree1 = await smt.newMemEmptyTrie();
  93. const tree2 = await smt.newMemEmptyTrie();
  94. const tree3 = await smt.newMemEmptyTrie();
  95. const tree4 = await smt.newMemEmptyTrie();
  96. const tree5 = await smt.newMemEmptyTrie();
  97. const tree6 = await smt.newMemEmptyTrie();
  98. await testInsert(tree1,keys[0],values[0], circuit);
  99. await testInsert(tree1,keys[1],values[1], circuit);
  100. await testInsert(tree1,keys[2],values[2], circuit);
  101. await testInsert(tree2,keys[0],values[0], circuit);
  102. await testInsert(tree2,keys[2],values[2], circuit);
  103. await testInsert(tree2,keys[1],values[1], circuit);
  104. await testInsert(tree3,keys[1],values[1], circuit);
  105. await testInsert(tree3,keys[0],values[0], circuit);
  106. await testInsert(tree3,keys[2],values[2], circuit);
  107. await testInsert(tree4,keys[1],values[1], circuit);
  108. await testInsert(tree4,keys[2],values[2], circuit);
  109. await testInsert(tree4,keys[0],values[0], circuit);
  110. await testInsert(tree5,keys[2],values[2], circuit);
  111. await testInsert(tree5,keys[0],values[0], circuit);
  112. await testInsert(tree5,keys[1],values[1], circuit);
  113. await testInsert(tree6,keys[2],values[2], circuit);
  114. await testInsert(tree6,keys[1],values[1], circuit);
  115. await testInsert(tree6,keys[0],values[0], circuit);
  116. await testDelete(tree1, keys[0], circuit);
  117. await testDelete(tree1, keys[1], circuit);
  118. await testDelete(tree2, keys[1], circuit);
  119. await testDelete(tree2, keys[0], circuit);
  120. await testDelete(tree3, keys[0], circuit);
  121. await testDelete(tree3, keys[2], circuit);
  122. await testDelete(tree4, keys[2], circuit);
  123. await testDelete(tree4, keys[0], circuit);
  124. await testDelete(tree5, keys[1], circuit);
  125. await testDelete(tree5, keys[2], circuit);
  126. await testDelete(tree6, keys[2], circuit);
  127. await testDelete(tree6, keys[1], circuit);
  128. await testDelete(tree1, keys[2], circuit);
  129. await testDelete(tree2, keys[2], circuit);
  130. await testDelete(tree3, keys[1], circuit);
  131. await testDelete(tree4, keys[1], circuit);
  132. await testDelete(tree5, keys[0], circuit);
  133. await testDelete(tree6, keys[0], circuit);
  134. });
  135. it("Should match a NOp with random vals", async () => {
  136. let siblings = [];
  137. while (siblings.length<10) siblings.push(bigInt(88));
  138. const w = circuit.calculateWitness({
  139. fnc: [0,0],
  140. oldRoot: 11,
  141. siblings: siblings,
  142. oldKey: 33,
  143. oldValue: 44,
  144. isOld0: 55,
  145. newKey: 66,
  146. newValue: 77
  147. });
  148. const root1 = w[circuit.getSignalIdx("main.oldRoot")];
  149. const root2 = w[circuit.getSignalIdx("main.newRoot")];
  150. assert(circuit.checkWitness(w));
  151. assert(root1.equals(root2));
  152. });
  153. it("Should update an element", async () => {
  154. const tree1 = await smt.newMemEmptyTrie();
  155. const tree2 = await smt.newMemEmptyTrie();
  156. await testInsert(tree1,8,88, circuit);
  157. await testInsert(tree1,9,99, circuit);
  158. await testInsert(tree1,32,3232, circuit);
  159. await testInsert(tree2,8,888, circuit);
  160. await testInsert(tree2,9,999, circuit);
  161. await testInsert(tree2,32,323232, circuit);
  162. await testUpdate(tree1, 8, 888, circuit);
  163. await testUpdate(tree1, 9, 999, circuit);
  164. await testUpdate(tree1, 32, 323232, circuit);
  165. });
  166. });