73 auto lhs = TestFixture::generators[0];
78 x.set_origin_tag(submitted_value_origin_tag);
79 y.set_origin_tag(challenge_origin_tag);
84 cycle_group_ct
a(x, y,
true);
88 EXPECT_EQ(
a.get_origin_tag(), first_two_merged_tag);
95 x_death.set_origin_tag(instant_death_tag);
97 y_normal.set_origin_tag(constant_tag);
100 cycle_group_ct
b(x_death, y_normal,
false);
102 EXPECT_THROW(
b.get_origin_tag(), std::runtime_error);
170 auto c1 = cycle_group_ct(AffineElement::one());
171 auto cw8 = cycle_group_ct::from_constant_witness(&
builder, AffineElement::one() * 0);
172 auto w11 = cycle_group_ct::from_witness(&
builder, TestFixture::generators[0]);
178 auto w27 = w10 - w11;
181 check_circuit_and_gate_count(
builder, 44);
209 auto c0 = cycle_group_ct(TestFixture::generators[0]);
210 auto c1 = cycle_group_ct(-TestFixture::generators[0]);
211 auto w2 = cycle_group_ct::conditional_assign(bool_ct(
witness_ct(&
builder,
true)), c0, c1);
212 EXPECT_FALSE(w2.x().is_constant());
213 EXPECT_FALSE(w2.y().is_constant());
214 EXPECT_TRUE(w2.is_point_at_infinity().is_constant());
217 check_circuit_and_gate_count(
builder, 5);
303 auto affine_infinity = cycle_group_ct::AffineElement::infinity();
304 cycle_group_ct input_a = cycle_group_ct::from_witness(&
builder, Element::random_element());
305 cycle_group_ct input_b = cycle_group_ct::from_witness(&
builder, affine_infinity);
306 cycle_group_ct input_c = cycle_group_ct(Element::random_element());
307 cycle_group_ct input_d = cycle_group_ct(affine_infinity);
310 input_a.set_origin_tag(submitted_value_origin_tag);
311 input_b.set_origin_tag(challenge_origin_tag);
312 input_c.set_origin_tag(next_challenge_tag);
313 input_d.set_origin_tag(first_two_merged_tag);
315 input_a.standardize();
316 auto standard_a = input_a;
317 input_b.standardize();
318 auto standard_b = input_b;
319 input_c.standardize();
320 auto standard_c = input_c;
321 input_d.standardize();
322 auto standard_d = input_d;
324 EXPECT_EQ(standard_a.is_point_at_infinity().get_value(),
false);
325 EXPECT_EQ(standard_b.is_point_at_infinity().get_value(),
true);
326 EXPECT_EQ(standard_c.is_point_at_infinity().get_value(),
false);
327 EXPECT_EQ(standard_d.is_point_at_infinity().get_value(),
true);
330 EXPECT_EQ(standard_a.get_origin_tag(), submitted_value_origin_tag);
331 EXPECT_EQ(standard_b.get_origin_tag(), challenge_origin_tag);
332 EXPECT_EQ(standard_c.get_origin_tag(), next_challenge_tag);
333 EXPECT_EQ(standard_d.get_origin_tag(), first_two_merged_tag);
335 auto input_a_x = input_a.x().get_value();
336 auto input_a_y = input_a.y().get_value();
337 auto input_c_x = input_c.x().get_value();
338 auto input_c_y = input_c.y().get_value();
340 auto standard_a_x = standard_a.x().get_value();
341 auto standard_a_y = standard_a.y().get_value();
343 auto standard_b_x = standard_b.x().get_value();
344 auto standard_b_y = standard_b.y().get_value();
346 auto standard_c_x = standard_c.x().get_value();
347 auto standard_c_y = standard_c.y().get_value();
349 auto standard_d_x = standard_d.x().get_value();
350 auto standard_d_y = standard_d.y().get_value();
352 EXPECT_EQ(input_a_x, standard_a_x);
353 EXPECT_EQ(input_a_y, standard_a_y);
354 EXPECT_EQ(standard_b_x, 0);
355 EXPECT_EQ(standard_b_y, 0);
356 EXPECT_EQ(input_c_x, standard_c_x);
357 EXPECT_EQ(input_c_y, standard_c_y);
358 EXPECT_EQ(standard_d_x, 0);
359 EXPECT_EQ(standard_d_y, 0);
361 check_circuit_and_gate_count(
builder, 24);
368 auto lhs = TestFixture::generators[0];
369 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
370 cycle_group_ct
b = cycle_group_ct(lhs);
372 a.set_origin_tag(submitted_value_origin_tag);
373 b.set_origin_tag(challenge_origin_tag);
376 for (
size_t i = 0; i < 3; ++i) {
380 AffineElement expected(
Element(lhs).dbl());
381 AffineElement result = c.get_value();
382 EXPECT_EQ(result, expected);
383 EXPECT_EQ(d.get_value(), expected);
385 check_circuit_and_gate_count(
builder, 19);
388 EXPECT_EQ(c.get_origin_tag(), submitted_value_origin_tag);
389 EXPECT_EQ(d.get_origin_tag(), challenge_origin_tag);
399 auto lhs = TestFixture::generators[0];
400 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
403 AffineElement hint(doubled_element);
405 cycle_group_ct result =
a.dbl(hint);
407 EXPECT_EQ(result.get_value(), hint);
408 EXPECT_FALSE(result.is_point_at_infinity().get_value());
410 check_circuit_and_gate_count(
builder, 13);
416 auto lhs = TestFixture::generators[1];
417 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
419 cycle_group_ct result =
a.dbl();
422 AffineElement expected(expected_element);
423 EXPECT_EQ(result.get_value(), expected);
424 EXPECT_FALSE(result.is_point_at_infinity().get_value());
427 check_circuit_and_gate_count(
builder, 13);
433 AffineElement infinity_element;
434 infinity_element.self_set_infinity();
436 cycle_group_ct infinity = cycle_group_ct::from_witness(&
builder, infinity_element);
438 cycle_group_ct result = infinity.dbl();
440 EXPECT_TRUE(result.is_point_at_infinity().get_value());
443 EXPECT_EQ(result.x().get_value(), 0);
446 check_circuit_and_gate_count(
builder, 13);
457 auto lhs = TestFixture::generators[0];
458 cycle_group_ct
a(lhs);
461 AffineElement hint(doubled_element);
463 cycle_group_ct result =
a.dbl(hint);
465 EXPECT_EQ(result.get_value(), hint);
466 EXPECT_TRUE(result.is_constant());
467 EXPECT_FALSE(result.is_point_at_infinity().get_value());
469 check_circuit_and_gate_count(
builder, 0);
475 auto lhs = TestFixture::generators[1];
476 cycle_group_ct
a(lhs);
478 cycle_group_ct result =
a.dbl();
481 AffineElement expected(expected_element);
482 EXPECT_EQ(result.get_value(), expected);
483 EXPECT_TRUE(result.is_constant());
484 EXPECT_FALSE(result.is_point_at_infinity().get_value());
486 check_circuit_and_gate_count(
builder, 0);
492 cycle_group_ct infinity = cycle_group_ct::constant_infinity(
nullptr);
494 cycle_group_ct result = infinity.dbl();
496 EXPECT_TRUE(result.is_point_at_infinity().get_value());
497 EXPECT_TRUE(result.is_constant());
498 EXPECT_EQ(result.x().get_value(), 0);
499 EXPECT_EQ(result.y().get_value(), 0);
501 check_circuit_and_gate_count(
builder, 0);
507 cycle_group_ct infinity = cycle_group_ct::constant_infinity(
nullptr);
510 hint.self_set_infinity();
512 cycle_group_ct result = infinity.dbl(hint);
514 EXPECT_TRUE(result.is_point_at_infinity().get_value());
515 EXPECT_TRUE(result.is_constant());
516 EXPECT_EQ(result.x().get_value(), 0);
517 EXPECT_EQ(result.y().get_value(), 0);
519 check_circuit_and_gate_count(
builder, 0);
552 auto lhs = TestFixture::generators[0];
553 auto rhs = TestFixture::generators[1];
554 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
555 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, rhs);
557 cycle_group_ct result =
a.unconditional_add(
b);
560 AffineElement expected(expected_element);
561 EXPECT_EQ(result.get_value(), expected);
562 EXPECT_FALSE(result.is_point_at_infinity().get_value());
564 check_circuit_and_gate_count(
builder, 22);
570 auto lhs = TestFixture::generators[2];
571 auto rhs = TestFixture::generators[3];
572 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
573 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, rhs);
576 AffineElement hint(sum_element);
578 cycle_group_ct result =
a.unconditional_add(
b, hint);
580 EXPECT_EQ(result.get_value(), hint);
581 EXPECT_FALSE(result.is_point_at_infinity().get_value());
583 check_circuit_and_gate_count(
builder, 22);
589 auto lhs = TestFixture::generators[0];
590 auto rhs = TestFixture::generators[1];
591 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
592 cycle_group_ct
b(rhs);
594 cycle_group_ct result =
a.unconditional_add(
b);
597 AffineElement expected(expected_element);
598 EXPECT_EQ(result.get_value(), expected);
599 EXPECT_FALSE(result.is_constant());
600 EXPECT_FALSE(result.is_point_at_infinity().get_value());
602 check_circuit_and_gate_count(
builder, 14);
613 auto lhs = TestFixture::generators[0];
614 auto rhs = TestFixture::generators[1];
615 cycle_group_ct
a(lhs);
616 cycle_group_ct
b(rhs);
618 cycle_group_ct result =
a.unconditional_add(
b);
621 AffineElement expected(expected_element);
622 EXPECT_EQ(result.get_value(), expected);
623 EXPECT_TRUE(result.is_constant());
624 EXPECT_FALSE(result.is_point_at_infinity().get_value());
626 check_circuit_and_gate_count(
builder, 0);
632 auto lhs = TestFixture::generators[2];
633 auto rhs = TestFixture::generators[3];
634 cycle_group_ct
a(lhs);
635 cycle_group_ct
b(rhs);
638 AffineElement hint(sum_element);
640 cycle_group_ct result =
a.unconditional_add(
b, hint);
642 EXPECT_EQ(result.get_value(), hint);
643 EXPECT_TRUE(result.is_constant());
644 EXPECT_FALSE(result.is_point_at_infinity().get_value());
646 check_circuit_and_gate_count(
builder, 0);
657 auto lhs = TestFixture::generators[0];
658 auto rhs = TestFixture::generators[1];
659 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
660 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, rhs);
662 cycle_group_ct result =
a.unconditional_subtract(
b);
665 AffineElement expected(expected_element);
666 EXPECT_EQ(result.get_value(), expected);
667 EXPECT_FALSE(result.is_point_at_infinity().get_value());
669 check_circuit_and_gate_count(
builder, 22);
675 auto lhs = TestFixture::generators[2];
676 auto rhs = TestFixture::generators[3];
677 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
678 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, rhs);
681 AffineElement hint(diff_element);
683 cycle_group_ct result =
a.unconditional_subtract(
b, hint);
685 EXPECT_EQ(result.get_value(), hint);
686 EXPECT_FALSE(result.is_point_at_infinity().get_value());
689 check_circuit_and_gate_count(
builder, 22);
695 auto lhs = TestFixture::generators[0];
696 auto rhs = TestFixture::generators[1];
697 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
698 cycle_group_ct
b(rhs);
700 cycle_group_ct result =
a.unconditional_subtract(
b);
703 AffineElement expected(expected_element);
704 EXPECT_EQ(result.get_value(), expected);
705 EXPECT_FALSE(result.is_constant());
706 EXPECT_FALSE(result.is_point_at_infinity().get_value());
708 check_circuit_and_gate_count(
builder, 14);
719 auto lhs = TestFixture::generators[0];
720 auto rhs = TestFixture::generators[1];
721 cycle_group_ct
a(lhs);
722 cycle_group_ct
b(rhs);
724 cycle_group_ct result =
a.unconditional_subtract(
b);
727 AffineElement expected(expected_element);
728 EXPECT_EQ(result.get_value(), expected);
729 EXPECT_TRUE(result.is_constant());
730 EXPECT_FALSE(result.is_point_at_infinity().get_value());
732 check_circuit_and_gate_count(
builder, 0);
738 auto lhs = TestFixture::generators[2];
739 auto rhs = TestFixture::generators[3];
740 cycle_group_ct
a(lhs);
741 cycle_group_ct
b(rhs);
744 AffineElement hint(diff_element);
746 cycle_group_ct result =
a.unconditional_subtract(
b, hint);
748 EXPECT_EQ(result.get_value(), hint);
749 EXPECT_TRUE(result.is_constant());
750 EXPECT_FALSE(result.is_point_at_infinity().get_value());
752 check_circuit_and_gate_count(
builder, 0);
762 [&](
const AffineElement& lhs,
const AffineElement& rhs,
const bool lhs_constant,
const bool rhs_constant) {
763 cycle_group_ct
a = lhs_constant ? cycle_group_ct(lhs) : cycle_group_ct::from_witness(&
builder, lhs);
764 cycle_group_ct
b = rhs_constant ? cycle_group_ct(rhs) : cycle_group_ct::from_witness(&
builder, rhs);
766 a.set_origin_tag(submitted_value_origin_tag);
767 b.set_origin_tag(challenge_origin_tag);
768 cycle_group_ct c =
a.unconditional_add(
b);
770 AffineElement result = c.get_value();
771 EXPECT_EQ(result, expected);
773 EXPECT_EQ(c.get_origin_tag(), first_two_merged_tag);
776 add(TestFixture::generators[0], TestFixture::generators[1],
false,
false);
777 add(TestFixture::generators[0], TestFixture::generators[1],
false,
true);
778 add(TestFixture::generators[0], TestFixture::generators[1],
true,
false);
779 add(TestFixture::generators[0], TestFixture::generators[1],
true,
true);
781 check_circuit_and_gate_count(
builder, 50);
789 auto lhs = TestFixture::generators[0];
790 auto rhs = TestFixture::generators[1];
793 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
794 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, rhs);
795 cycle_group_ct c =
a.checked_unconditional_add(
b);
797 AffineElement result = c.get_value();
798 EXPECT_EQ(result, expected);
800 check_circuit_and_gate_count(
builder, 24);
828 auto lhs = TestFixture::generators[0];
829 auto rhs = -TestFixture::generators[1];
831 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
832 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, rhs);
835 a.set_origin_tag(submitted_value_origin_tag);
836 b.set_origin_tag(challenge_origin_tag);
838 cycle_group_ct c =
a +
b;
841 EXPECT_EQ(c.get_value(), expected);
842 EXPECT_EQ(c.get_origin_tag(), first_two_merged_tag);
844 check_circuit_and_gate_count(
builder, 55);
853 auto rhs = -TestFixture::generators[1];
854 auto affine_infinity = cycle_group_ct::AffineElement::infinity();
856 cycle_group_ct point_at_infinity = cycle_group_ct::from_witness(&
builder, affine_infinity);
858 cycle_group_ct
a = point_at_infinity;
859 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, rhs);
861 a.set_origin_tag(submitted_value_origin_tag);
862 b.set_origin_tag(challenge_origin_tag);
864 cycle_group_ct c =
a +
b;
867 EXPECT_EQ(c.get_value(), rhs);
868 EXPECT_EQ(c.get_origin_tag(), first_two_merged_tag);
870 check_circuit_and_gate_count(
builder, 55);
879 auto lhs = TestFixture::generators[0];
880 auto affine_infinity = cycle_group_ct::AffineElement::infinity();
882 cycle_group_ct point_at_infinity = cycle_group_ct::from_witness(&
builder, affine_infinity);
884 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
885 cycle_group_ct
b = point_at_infinity;
887 a.set_origin_tag(submitted_value_origin_tag);
888 b.set_origin_tag(challenge_origin_tag);
890 cycle_group_ct c =
a +
b;
893 EXPECT_EQ(c.get_value(), lhs);
894 EXPECT_EQ(c.get_origin_tag(), first_two_merged_tag);
897 check_circuit_and_gate_count(
builder, 55);
906 auto affine_infinity = cycle_group_ct::AffineElement::infinity();
908 cycle_group_ct point_at_infinity1 = cycle_group_ct::from_witness(&
builder, affine_infinity);
910 cycle_group_ct point_at_infinity2 = cycle_group_ct::from_witness(&
builder, affine_infinity);
912 cycle_group_ct
a = point_at_infinity1;
913 cycle_group_ct
b = point_at_infinity2;
915 a.set_origin_tag(submitted_value_origin_tag);
916 b.set_origin_tag(challenge_origin_tag);
918 cycle_group_ct c =
a +
b;
921 EXPECT_TRUE(c.is_point_at_infinity().get_value());
922 EXPECT_TRUE(c.get_value().is_point_at_infinity());
923 EXPECT_EQ(c.get_origin_tag(), first_two_merged_tag);
925 check_circuit_and_gate_count(
builder, 55);
934 auto lhs = TestFixture::generators[0];
936 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
937 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, -lhs);
939 a.set_origin_tag(submitted_value_origin_tag);
940 b.set_origin_tag(challenge_origin_tag);
942 cycle_group_ct c =
a +
b;
944 EXPECT_TRUE(c.is_point_at_infinity().get_value());
945 EXPECT_TRUE(c.get_value().is_point_at_infinity());
946 EXPECT_EQ(c.get_origin_tag(), first_two_merged_tag);
948 check_circuit_and_gate_count(
builder, 55);
957 auto lhs = TestFixture::generators[0];
959 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
960 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, lhs);
962 a.set_origin_tag(submitted_value_origin_tag);
963 b.set_origin_tag(challenge_origin_tag);
965 cycle_group_ct c =
a +
b;
967 AffineElement expected((
Element(lhs)).dbl());
968 EXPECT_EQ(c.get_value(), expected);
969 EXPECT_EQ(c.get_origin_tag(), first_two_merged_tag);
971 check_circuit_and_gate_count(
builder, 55);
982 auto lhs = TestFixture::generators[5];
983 auto rhs = TestFixture::generators[6];
985 cycle_group_ct
a(lhs);
986 cycle_group_ct
b(rhs);
988 cycle_group_ct result =
a +
b;
991 EXPECT_EQ(result.get_value(), expected);
992 EXPECT_TRUE(result.is_constant());
995 check_circuit_and_gate_count(
builder, 0);
1001 auto lhs = TestFixture::generators[7];
1003 cycle_group_ct
a(lhs);
1004 cycle_group_ct
b = cycle_group_ct::constant_infinity(&
builder);
1006 cycle_group_ct result =
a +
b;
1008 EXPECT_EQ(result.get_value(), lhs);
1009 EXPECT_TRUE(result.is_constant());
1012 check_circuit_and_gate_count(
builder, 0);
1026 auto lhs = TestFixture::generators[10];
1028 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
1029 cycle_group_ct
b = cycle_group_ct::constant_infinity(&
builder);
1031 cycle_group_ct result =
a +
b;
1033 EXPECT_EQ(result.get_value(), lhs);
1034 EXPECT_FALSE(result.is_constant());
1037 check_circuit_and_gate_count(
builder, 10);
1043 auto lhs = TestFixture::generators[11];
1044 auto rhs = TestFixture::generators[12];
1046 cycle_group_ct
a(lhs);
1047 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, rhs);
1049 cycle_group_ct result =
a +
b;
1052 EXPECT_EQ(result.get_value(), expected);
1053 EXPECT_FALSE(result.is_constant());
1056 check_circuit_and_gate_count(
builder, 27);
1068 auto point = TestFixture::generators[0];
1069 auto neg_point = -point;
1071 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, point);
1072 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, neg_point);
1074 cycle_group_ct result =
a +
b;
1077 EXPECT_TRUE(result.is_point_at_infinity().get_value());
1078 EXPECT_TRUE(result.get_value().is_point_at_infinity());
1083 cycle_group_ct inf1 = cycle_group_ct::from_witness(&
builder, Group::affine_point_at_infinity);
1084 cycle_group_ct inf2 = cycle_group_ct::from_witness(&
builder, Group::affine_point_at_infinity);
1086 cycle_group_ct result = inf1 + inf2;
1089 EXPECT_TRUE(result.is_point_at_infinity().get_value());
1090 EXPECT_TRUE(result.get_value().is_point_at_infinity());
1095 auto point = TestFixture::generators[1];
1097 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, point);
1098 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, Group::affine_point_at_infinity);
1100 cycle_group_ct result =
a +
b;
1103 EXPECT_FALSE(result.is_point_at_infinity().get_value());
1104 EXPECT_EQ(result.get_value(), point);
1109 auto point = TestFixture::generators[2];
1111 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, Group::affine_point_at_infinity);
1112 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, point);
1114 cycle_group_ct result =
a +
b;
1117 EXPECT_FALSE(result.is_point_at_infinity().get_value());
1118 EXPECT_EQ(result.get_value(), point);
1123 auto point = TestFixture::generators[3];
1125 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, point);
1126 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, point);
1128 cycle_group_ct result =
a +
b;
1131 EXPECT_FALSE(result.is_point_at_infinity().get_value());
1133 AffineElement expected(
Element(point).dbl());
1134 EXPECT_EQ(result.get_value(), expected);
1137 check_circuit_and_gate_count(
builder, 275);
1146 [&](
const AffineElement& lhs,
const AffineElement& rhs,
const bool lhs_constant,
const bool rhs_constant) {
1147 cycle_group_ct
a = lhs_constant ? cycle_group_ct(lhs) : cycle_group_ct::from_witness(&
builder, lhs);
1148 cycle_group_ct
b = rhs_constant ? cycle_group_ct(rhs) : cycle_group_ct::from_witness(&
builder, rhs);
1150 a.set_origin_tag(submitted_value_origin_tag);
1151 b.set_origin_tag(challenge_origin_tag);
1153 cycle_group_ct c =
a.unconditional_subtract(
b);
1155 AffineElement result = c.get_value();
1156 EXPECT_EQ(result, expected);
1158 EXPECT_EQ(c.get_origin_tag(), first_two_merged_tag);
1161 subtract(TestFixture::generators[0], TestFixture::generators[1],
false,
false);
1162 subtract(TestFixture::generators[0], TestFixture::generators[1],
false,
true);
1163 subtract(TestFixture::generators[0], TestFixture::generators[1],
true,
false);
1164 subtract(TestFixture::generators[0], TestFixture::generators[1],
true,
true);
1166 check_circuit_and_gate_count(
builder, 50);
1174 auto lhs = TestFixture::generators[0];
1175 auto rhs = TestFixture::generators[1];
1178 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
1179 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, rhs);
1180 cycle_group_ct c =
a.checked_unconditional_subtract(
b);
1182 AffineElement result = c.get_value();
1183 EXPECT_EQ(result, expected);
1185 check_circuit_and_gate_count(
builder, 24);
1213 auto lhs = TestFixture::generators[0];
1214 auto rhs = -TestFixture::generators[1];
1215 auto affine_infinity = cycle_group_ct::AffineElement::infinity();
1217 cycle_group_ct point_at_infinity = cycle_group_ct::from_witness(&
builder, affine_infinity);
1221 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
1222 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, rhs);
1224 a.set_origin_tag(submitted_value_origin_tag);
1225 b.set_origin_tag(challenge_origin_tag);
1227 cycle_group_ct c =
a -
b;
1229 AffineElement result = c.get_value();
1230 EXPECT_EQ(result, expected);
1232 EXPECT_EQ(c.get_origin_tag(), first_two_merged_tag);
1237 cycle_group_ct
a = point_at_infinity;
1238 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, rhs);
1239 a.set_origin_tag(submitted_value_origin_tag);
1240 b.set_origin_tag(challenge_origin_tag);
1242 cycle_group_ct c =
a -
b;
1243 AffineElement result = c.get_value();
1244 EXPECT_EQ(result, -rhs);
1245 EXPECT_EQ(c.get_origin_tag(), first_two_merged_tag);
1250 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
1251 cycle_group_ct
b = point_at_infinity;
1252 a.set_origin_tag(submitted_value_origin_tag);
1253 b.set_origin_tag(challenge_origin_tag);
1255 cycle_group_ct c =
a -
b;
1256 AffineElement result = c.get_value();
1257 EXPECT_EQ(result, lhs);
1258 EXPECT_EQ(c.get_origin_tag(), first_two_merged_tag);
1263 cycle_group_ct
a = point_at_infinity;
1264 cycle_group_ct
b = point_at_infinity;
1265 a.set_origin_tag(submitted_value_origin_tag);
1266 b.set_origin_tag(challenge_origin_tag);
1268 cycle_group_ct c =
a -
b;
1269 EXPECT_TRUE(c.is_point_at_infinity().get_value());
1270 EXPECT_TRUE(c.get_value().is_point_at_infinity());
1271 EXPECT_EQ(c.get_origin_tag(), first_two_merged_tag);
1276 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
1277 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, -lhs);
1278 a.set_origin_tag(submitted_value_origin_tag);
1279 b.set_origin_tag(challenge_origin_tag);
1281 cycle_group_ct c =
a -
b;
1282 AffineElement expected((
Element(lhs)).dbl());
1283 AffineElement result = c.get_value();
1284 EXPECT_EQ(result, expected);
1285 EXPECT_EQ(c.get_origin_tag(), first_two_merged_tag);
1290 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, lhs);
1291 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, lhs);
1292 a.set_origin_tag(submitted_value_origin_tag);
1293 b.set_origin_tag(challenge_origin_tag);
1295 cycle_group_ct c =
a -
b;
1296 EXPECT_TRUE(c.is_point_at_infinity().get_value());
1297 EXPECT_TRUE(c.get_value().is_point_at_infinity());
1298 EXPECT_EQ(c.get_origin_tag(), first_two_merged_tag);
1301 check_circuit_and_gate_count(
builder, 297);
1312 auto lhs = TestFixture::generators[5];
1313 auto rhs = TestFixture::generators[6];
1315 cycle_group_ct
a(lhs);
1316 cycle_group_ct
b(rhs);
1318 cycle_group_ct result =
a -
b;
1321 EXPECT_EQ(result.get_value(), expected);
1322 EXPECT_TRUE(result.is_constant());
1325 check_circuit_and_gate_count(
builder, 0);
1331 auto lhs = TestFixture::generators[7];
1333 cycle_group_ct
a(lhs);
1334 cycle_group_ct
b = cycle_group_ct::constant_infinity(&
builder);
1336 cycle_group_ct result =
a -
b;
1338 EXPECT_EQ(result.get_value(), lhs);
1339 EXPECT_TRUE(result.is_constant());
1342 check_circuit_and_gate_count(
builder, 0);
1348 auto rhs = TestFixture::generators[7];
1350 cycle_group_ct
a = cycle_group_ct::constant_infinity(&
builder);
1351 cycle_group_ct
b(rhs);
1353 cycle_group_ct result =
a -
b;
1355 EXPECT_EQ(result.get_value(), -rhs);
1356 EXPECT_TRUE(result.is_constant());
1359 check_circuit_and_gate_count(
builder, 0);
1388 const size_t num_muls = 1;
1392 Element expected = Group::point_at_infinity;
1394 for (
size_t i = 0; i < num_muls; ++i) {
1395 auto element = TestFixture::generators[i];
1396 typename Group::Fr scalar = Group::Fr::random_element(&
engine);
1399 expected += (element * scalar);
1400 points.emplace_back(cycle_group_ct::from_witness(&
builder, element));
1401 scalars.emplace_back(cycle_group_ct::cycle_scalar::from_witness(&
builder, scalar));
1404 expected += (element * scalar);
1405 points.emplace_back(cycle_group_ct(element));
1406 scalars.emplace_back(cycle_group_ct::cycle_scalar::from_witness(&
builder, scalar));
1409 expected += (element * scalar);
1410 points.emplace_back(cycle_group_ct::from_witness(&
builder, element));
1411 scalars.emplace_back(
typename cycle_group_ct::cycle_scalar(scalar));
1414 expected += (element * scalar);
1415 points.emplace_back(cycle_group_ct(element));
1416 scalars.emplace_back(
typename cycle_group_ct::cycle_scalar(scalar));
1422 auto result = cycle_group_ct::batch_mul(points, scalars);
1423 EXPECT_EQ(result.get_value(), AffineElement(expected));
1425 EXPECT_EQ(result.get_origin_tag(), expected_tag);
1428 check_circuit_and_gate_count(
builder, 4401);
1430 check_circuit_and_gate_count(
builder, 4404);
1443 auto element = TestFixture::generators[0];
1444 typename Group::Fr scalar = Group::Fr::random_element(&
engine);
1445 points.emplace_back(cycle_group_ct::from_witness(&
builder, element));
1446 scalars.emplace_back(cycle_group_ct::cycle_scalar::from_witness(&
builder, scalar));
1448 points.emplace_back(cycle_group_ct::from_witness(&
builder, element));
1449 scalars.emplace_back(cycle_group_ct::cycle_scalar::from_witness(&
builder, -scalar));
1453 auto result = cycle_group_ct::batch_mul(points, scalars);
1454 EXPECT_TRUE(result.is_point_at_infinity().get_value());
1456 EXPECT_EQ(result.get_origin_tag(), expected_tag);
1459 check_circuit_and_gate_count(
builder, 4027);
1461 check_circuit_and_gate_count(
builder, 4030);
1474 auto element = TestFixture::generators[0];
1475 typename Group::Fr scalar = 0;
1476 points.emplace_back(cycle_group_ct::from_witness(&
builder, element));
1477 scalars.emplace_back(cycle_group_ct::cycle_scalar::from_witness(&
builder, scalar));
1480 auto result = cycle_group_ct::batch_mul(points, scalars);
1481 EXPECT_TRUE(result.is_point_at_infinity().get_value());
1482 EXPECT_EQ(result.get_origin_tag(), expected_tag);
1485 check_circuit_and_gate_count(
builder, 3533);
1487 check_circuit_and_gate_count(
builder, 3536);
1500 typename Group::Fr scalar = Group::Fr::random_element(&
engine);
1501 auto affine_infinity = cycle_group_ct::AffineElement::infinity();
1505 cycle_group_ct point = cycle_group_ct::from_witness(&
builder, affine_infinity);
1506 points.emplace_back(point);
1507 scalars.emplace_back(cycle_group_ct::cycle_scalar::from_witness(&
builder, scalar));
1511 cycle_group_ct point = cycle_group_ct(affine_infinity);
1512 points.emplace_back(point);
1513 scalars.emplace_back(cycle_group_ct::cycle_scalar::from_witness(&
builder, scalar));
1517 auto result = cycle_group_ct::batch_mul(points, scalars);
1518 EXPECT_TRUE(result.is_point_at_infinity().get_value());
1519 EXPECT_EQ(result.get_origin_tag(), expected_tag);
1523 check_circuit_and_gate_count(
builder, 3584);
1525 check_circuit_and_gate_count(
builder, 3587);
1534 const size_t num_muls = 1;
1540 Element expected = Group::point_at_infinity;
1541 for (
size_t i = 0; i < num_muls; ++i) {
1543 typename Group::Fr scalar = Group::Fr::random_element(&
engine);
1546 expected += (element * scalar);
1547 points.emplace_back(element);
1548 scalars.emplace_back(cycle_group_ct::cycle_scalar::from_witness(&
builder, scalar));
1549 scalars_native.emplace_back(
uint256_t(scalar));
1553 expected += (element * scalar);
1554 points.emplace_back(element);
1555 scalars.emplace_back(
typename cycle_group_ct::cycle_scalar(scalar));
1556 scalars_native.emplace_back(
uint256_t(scalar));
1559 auto result = cycle_group_ct::batch_mul(points, scalars);
1560 EXPECT_EQ(result.get_value(), AffineElement(expected));
1562 EXPECT_EQ(result.get_origin_tag(), expected_tag);
1564 check_circuit_and_gate_count(
builder, 2822);
1572 const size_t num_muls = 1;
1578 Element expected = Group::point_at_infinity;
1579 for (
size_t i = 0; i < num_muls; ++i) {
1581 typename Group::Fr scalar = Group::Fr::random_element(&
engine);
1584 expected += (element * scalar);
1585 points.emplace_back(element);
1586 scalars.emplace_back(cycle_group_ct::cycle_scalar::from_witness(&
builder, scalar));
1587 scalars_native.emplace_back(scalar);
1591 expected += (element * scalar);
1592 points.emplace_back(element);
1593 scalars.emplace_back(
typename cycle_group_ct::cycle_scalar(scalar));
1594 scalars_native.emplace_back(scalar);
1597 scalar = Group::Fr::random_element(&
engine);
1598 element = Group::one * Group::Fr::random_element(&
engine);
1599 expected += (element * scalar);
1600 points.emplace_back(element);
1601 scalars.emplace_back(cycle_group_ct::cycle_scalar::from_witness(&
builder, scalar));
1602 scalars_native.emplace_back(scalar);
1605 auto result = cycle_group_ct::batch_mul(points, scalars);
1606 EXPECT_EQ(result.get_value(), AffineElement(expected));
1607 EXPECT_EQ(result.get_origin_tag(), expected_tag);
1611 check_circuit_and_gate_count(
builder, 3395);
1613 check_circuit_and_gate_count(
builder, 3398);
1622 const size_t num_muls = 1;
1627 for (
size_t i = 0; i < num_muls; ++i) {
1629 typename Group::Fr scalar = 0;
1632 points.emplace_back((element));
1633 scalars.emplace_back(cycle_group_ct::cycle_scalar::from_witness(&
builder, scalar));
1636 points.emplace_back((element));
1637 scalars.emplace_back(
typename cycle_group_ct::cycle_scalar(scalar));
1640 auto result = cycle_group_ct::batch_mul(points, scalars);
1641 EXPECT_EQ(result.is_point_at_infinity().get_value(),
true);
1642 EXPECT_EQ(result.get_origin_tag(), expected_tag);
1644 check_circuit_and_gate_count(
builder, 2837);
1652 const size_t num_muls = 5;
1656 cycle_group_ct point;
1657 typename cycle_group_ct::cycle_scalar scalar;
1658 cycle_group_ct result;
1659 for (
size_t i = 0; i < num_muls; ++i) {
1660 auto element = TestFixture::generators[i];
1661 typename Group::Fr native_scalar = Group::Fr::random_element(&
engine);
1665 point = (cycle_group_ct::from_witness(&
builder, element));
1666 scalar = (cycle_group_ct::cycle_scalar::from_witness(&
builder, native_scalar));
1667 point.set_origin_tag(submitted_value_origin_tag);
1668 scalar.set_origin_tag(challenge_origin_tag);
1669 result = point * scalar;
1673 point = (cycle_group_ct(element));
1674 scalar = (cycle_group_ct::cycle_scalar::from_witness(&
builder, native_scalar));
1675 result = point * scalar;
1679 point = (cycle_group_ct::from_witness(&
builder, element));
1680 scalar = (
typename cycle_group_ct::cycle_scalar(native_scalar));
1681 result = point * scalar;
1685 point = (cycle_group_ct(element));
1686 scalar = (
typename cycle_group_ct::cycle_scalar(native_scalar));
1687 result = point * scalar;
1694 check_circuit_and_gate_count(
builder, 12973);
1696 check_circuit_and_gate_count(
builder, 12976);
1722 const auto run_test = [](
bool construct_witnesses) {
1726 if (construct_witnesses) {
1727 big_elt = FF_ct::from_witness(&
builder, elt);
1729 big_elt = FF_ct(elt);
1731 big_elt.set_origin_tag(submitted_value_origin_tag);
1732 cycle_scalar_ct scalar_from_big_elt(big_elt);
1733 EXPECT_EQ(elt, scalar_from_big_elt.get_value());
1734 EXPECT_EQ(scalar_from_big_elt.get_origin_tag(), big_elt.get_origin_tag());
1735 if (construct_witnesses) {
1736 EXPECT_FALSE(big_elt.is_constant());
1737 EXPECT_FALSE(scalar_from_big_elt.is_constant());
1738 check_circuit_and_gate_count(
builder, 3523);
1751 const auto run_test = [](
bool construct_witnesses) {
1758 if (construct_witnesses) {
1759 big_scalar1 = FF_ct::from_witness(&
builder, scalar1);
1760 big_scalar2 = FF_ct::from_witness(&
builder, scalar2);
1762 big_scalar1 = FF_ct(scalar1);
1763 big_scalar2 = FF_ct(scalar2);
1765 cycle_group_ct result1 = cycle_group_ct::batch_mul({ TestFixture::generators[0], TestFixture::generators[1] },
1766 { big_scalar1, big_scalar2 });
1768 cycle_group_ct result2 =
1769 cycle_group_ct::batch_mul({ TestFixture::generators[0], TestFixture::generators[1] },
1770 { cycle_scalar_ct(big_scalar1), cycle_scalar_ct(big_scalar2) });
1772 AffineElement result1_native = result1.get_value();
1773 AffineElement result2_native = result2.get_value();
1774 EXPECT_EQ(result1_native.x, result2_native.x);
1775 EXPECT_EQ(result1_native.y, result2_native.y);
1776 if (construct_witnesses) {
1777 EXPECT_FALSE(result1.is_constant());
1778 EXPECT_FALSE(result2.is_constant());
1781 check_circuit_and_gate_count(
builder, 5285);
1783 check_circuit_and_gate_count(
builder, 5288);
1809 auto scalar1_val = Group::Fr::random_element(&
engine);
1810 auto scalar2_val = Group::Fr::random_element(&
engine);
1812 scalars.push_back(cycle_scalar_ct::from_witness(&
builder, scalar1_val));
1813 scalars.push_back(cycle_scalar_ct::from_witness(&
builder, scalar2_val));
1814 points.push_back(cycle_group_ct(lhs_generator));
1815 points.push_back(cycle_group_ct(rhs_generator));
1817 auto result = cycle_group_ct::batch_mul(points, scalars);
1820 AffineElement expected = lhs_generator * scalar1_val + rhs_generator * scalar2_val;
1822 EXPECT_EQ(result.get_value(), expected);
1824 check_circuit_and_gate_count(
builder, 2908);
1839 auto input = TestFixture::generators[0];
1840 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, input);
1841 cycle_group_ct inf = cycle_group_ct::constant_infinity(&
builder);
1843 cycle_group_ct temp =
a + inf;
1844 cycle_group_ct result = temp -
a;
1846 EXPECT_TRUE(result.is_point_at_infinity().get_value());
1849 EXPECT_TRUE(result.get_value().is_point_at_infinity());
1854 auto input_a = TestFixture::generators[0];
1855 auto input_b = TestFixture::generators[1];
1856 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, input_a);
1857 cycle_group_ct
b = cycle_group_ct::from_witness(&
builder, input_b);
1859 cycle_group_ct zero =
b -
b;
1860 cycle_group_ct result =
a + zero;
1862 EXPECT_FALSE(result.is_point_at_infinity().get_value());
1863 EXPECT_EQ(result.get_value().x, input_a.x);
1864 EXPECT_EQ(result.get_value().y, input_a.y);
1869 auto input = TestFixture::generators[0];
1870 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, input);
1871 cycle_group_ct inf1 = cycle_group_ct::constant_infinity(&
builder);
1872 cycle_group_ct inf2 = cycle_group_ct::constant_infinity(&
builder);
1874 cycle_group_ct zero = inf1 - inf2;
1875 cycle_group_ct result = zero +
a;
1877 EXPECT_EQ(result.get_value().x, input.x);
1878 EXPECT_EQ(result.get_value().y, input.y);
1881 EXPECT_FALSE(
builder.failed());
1895 auto input = TestFixture::generators[0];
1896 cycle_group_ct
a = cycle_group_ct::from_witness(&
builder, input);
1897 cycle_group_ct inf = cycle_group_ct::constant_infinity(&
builder);
1903 cycle_group_ct result = cycle_group_ct::conditional_assign(pred, inf,
a);
1905 EXPECT_FALSE(result.is_point_at_infinity().get_value());
1906 EXPECT_EQ(result.get_value().x, input.x);
1907 EXPECT_EQ(result.get_value().y, input.y);
1913 cycle_group_ct result = cycle_group_ct::conditional_assign(pred, inf,
a);
1915 EXPECT_TRUE(result.is_point_at_infinity().get_value());
1916 EXPECT_TRUE(result.x().get_value() == 0);
1917 EXPECT_TRUE(result.y().get_value() == 0);
1922 cycle_group_ct inf2 = cycle_group_ct::constant_infinity(&
builder);
1924 cycle_group_ct result = cycle_group_ct::conditional_assign(pred, inf, inf2);
1926 EXPECT_TRUE(result.is_point_at_infinity().get_value());
1927 EXPECT_TRUE(result.x().get_value() == 0);
1928 EXPECT_TRUE(result.y().get_value() == 0);
1931 EXPECT_FALSE(
builder.failed());
1947 auto input = TestFixture::generators[0];
1948 cycle_group_ct P = cycle_group_ct::from_witness(&
builder, input);
1949 cycle_group_ct witness_inf = P - P;
1951 EXPECT_TRUE(witness_inf.is_point_at_infinity().get_value());
1954 auto input2 = TestFixture::generators[1];
1955 cycle_group_ct Q = cycle_group_ct::from_witness(&
builder, input2);
1958 cycle_group_ct result = Q + witness_inf;
1959 EXPECT_EQ(result.get_value().x, input2.x);
1960 EXPECT_EQ(result.get_value().y, input2.y);
1963 cycle_group_ct result2 = witness_inf + Q;
1964 EXPECT_EQ(result2.get_value().x, input2.x);
1965 EXPECT_EQ(result2.get_value().y, input2.y);
1967 EXPECT_FALSE(
builder.failed());
1980 auto P_val = TestFixture::generators[0];
1981 auto Q_val = TestFixture::generators[1];
1982 auto a = Group::Fr::random_element(&
engine);
1983 auto b = Group::Fr::random_element(&
engine);
1986 cycle_group_ct::from_witness(&
builder, P_val),
1987 cycle_group_ct::from_witness(&
builder, Q_val),
1988 cycle_group_ct::from_witness(&
builder, P_val),
1989 cycle_group_ct::from_witness(&
builder, Q_val),
1993 cycle_scalar_ct::from_witness(&
builder,
a),
1994 cycle_scalar_ct::from_witness(&
builder,
b),
1995 cycle_scalar_ct::from_witness(&
builder, -
a),
1996 cycle_scalar_ct::from_witness(&
builder, -
b),
1999 cycle_group_ct result = cycle_group_ct::batch_mul(points, scalars);
2001 EXPECT_TRUE(result.is_point_at_infinity().get_value());
2003 EXPECT_TRUE(result.get_value().is_point_at_infinity());
2005 EXPECT_FALSE(
builder.failed());
2022 cycle_group_ct inf = cycle_group_ct::constant_infinity(&
builder);
2023 EXPECT_TRUE(inf.is_point_at_infinity().get_value());
2024 EXPECT_TRUE(inf.get_value().is_point_at_infinity());
2026 EXPECT_EQ(inf.x().get_value(), 0);
2027 EXPECT_EQ(inf.y().get_value(), 0);
2032 auto input = TestFixture::generators[0];
2033 cycle_group_ct P = cycle_group_ct::from_witness(&
builder, input);
2034 cycle_group_ct neg_P = -P;
2035 cycle_group_ct result = P + neg_P;
2037 EXPECT_TRUE(result.is_point_at_infinity().get_value());
2040 EXPECT_TRUE(result.get_value().is_point_at_infinity());
2045 cycle_group_ct inf = cycle_group_ct::constant_infinity(&
builder);
2046 cycle_group_ct result = inf.dbl();
2048 EXPECT_TRUE(result.is_point_at_infinity().get_value());
2050 EXPECT_TRUE(result.get_value().is_point_at_infinity());
2053 EXPECT_FALSE(
builder.failed());