Clearmatics Libff  0.1
C++ library for Finite Fields and Elliptic Curves
mnt6_g2.cpp
Go to the documentation of this file.
1 
15 
16 namespace libff
17 {
18 
19 #ifdef PROFILE_OP_COUNTS
20 long long mnt6_G2::add_cnt = 0;
21 long long mnt6_G2::dbl_cnt = 0;
22 #endif
23 
24 std::vector<size_t> mnt6_G2::wnaf_window_table;
25 std::vector<size_t> mnt6_G2::fixed_base_exp_window_table;
29 mnt6_G2 mnt6_G2::G2_zero;
30 mnt6_G2 mnt6_G2::G2_one;
31 bigint<mnt6_G2::h_limbs> mnt6_G2::h;
32 
34 {
35  this->X = G2_zero.X;
36  this->Y = G2_zero.Y;
37  this->Z = G2_zero.Z;
38 }
39 
41 {
42  return mnt6_Fq3(
46 }
47 
49 {
50  return mnt6_Fq3(
54 }
55 
56 void mnt6_G2::print() const
57 {
58  if (this->is_zero()) {
59  printf("O\n");
60  } else {
61  mnt6_G2 copy(*this);
62  copy.to_affine_coordinates();
63  gmp_printf(
64  "(%Nd*z^2 + %Nd*z + %Nd , %Nd*z^2 + %Nd*z + %Nd)\n",
65  copy.X.coeffs[2].as_bigint().data,
67  copy.X.coeffs[1].as_bigint().data,
69  copy.X.coeffs[0].as_bigint().data,
71  copy.Y.coeffs[2].as_bigint().data,
73  copy.Y.coeffs[1].as_bigint().data,
75  copy.Y.coeffs[0].as_bigint().data,
77  }
78 }
79 
81 {
82  if (this->is_zero()) {
83  printf("O\n");
84  } else {
85  gmp_printf(
86  "(%Nd*z^2 + %Nd*z + %Nd : %Nd*z^2 + %Nd*z + %Nd : %Nd*z^2 + %Nd*z "
87  "+ %Nd)\n",
88  this->X.coeffs[2].as_bigint().data,
90  this->X.coeffs[1].as_bigint().data,
92  this->X.coeffs[0].as_bigint().data,
94  this->Y.coeffs[2].as_bigint().data,
96  this->Y.coeffs[1].as_bigint().data,
98  this->Y.coeffs[0].as_bigint().data,
100  this->Z.coeffs[2].as_bigint().data,
102  this->Z.coeffs[1].as_bigint().data,
104  this->Z.coeffs[0].as_bigint().data,
106  }
107 }
108 
110 {
111  if (this->is_zero()) {
112  this->X = mnt6_Fq3::zero();
113  this->Y = mnt6_Fq3::one();
114  this->Z = mnt6_Fq3::zero();
115  } else {
116  const mnt6_Fq3 Z_inv = Z.inverse();
117  this->X = this->X * Z_inv;
118  this->Y = this->Y * Z_inv;
119  this->Z = mnt6_Fq3::one();
120  }
121 }
122 
124 
126 {
127  return (this->is_zero() || this->Z == mnt6_Fq3::one());
128 }
129 
130 bool mnt6_G2::is_zero() const
131 {
132  // TODO: use zero for here
133  return (this->X.is_zero() && this->Z.is_zero());
134 }
135 
136 bool mnt6_G2::operator==(const mnt6_G2 &other) const
137 {
138  if (this->is_zero()) {
139  return other.is_zero();
140  }
141 
142  if (other.is_zero()) {
143  return false;
144  }
145 
146  /* now neither is O */
147 
148  // X1/Z1 = X2/Z2 <=> X1*Z2 = X2*Z1
149  if ((this->X * other.Z) != (other.X * this->Z)) {
150  return false;
151  }
152 
153  // Y1/Z1 = Y2/Z2 <=> Y1*Z2 = Y2*Z1
154  if ((this->Y * other.Z) != (other.Y * this->Z)) {
155  return false;
156  }
157 
158  return true;
159 }
160 
161 bool mnt6_G2::operator!=(const mnt6_G2 &other) const
162 {
163  return !(operator==(other));
164 }
165 
166 mnt6_G2 mnt6_G2::operator+(const mnt6_G2 &other) const
167 {
168  // handle special cases having to do with O
169  if (this->is_zero()) {
170  return other;
171  }
172 
173  if (other.is_zero()) {
174  return *this;
175  }
176 
177  // no need to handle points of order 2,4
178  // (they cannot exist in a prime-order subgroup)
179 
180  // handle double case, and then all the rest
181  //
182  // The code below is equivalent to (but faster than) the snippet below:
183  //
184  // if (this->operator==(other))
185  // {
186  // return this->dbl();
187  // }
188  // else
189  // {
190  // return this->add(other);
191  // }
192 
193  // X1Z2 = X1*Z2
194  const mnt6_Fq3 X1Z2 = (this->X) * (other.Z);
195  // X2Z1 = X2*Z1
196  const mnt6_Fq3 X2Z1 = (this->Z) * (other.X);
197 
198  // (used both in add and double checks)
199 
200  // Y1Z2 = Y1*Z2
201  const mnt6_Fq3 Y1Z2 = (this->Y) * (other.Z);
202  // Y2Z1 = Y2*Z1
203  const mnt6_Fq3 Y2Z1 = (this->Z) * (other.Y);
204 
205  if (X1Z2 == X2Z1 && Y1Z2 == Y2Z1) {
206  // perform dbl case
207  // XX = X1^2
208  const mnt6_Fq3 XX = (this->X).squared();
209  // ZZ = Z1^2
210  const mnt6_Fq3 ZZ = (this->Z).squared();
211  // w = a*ZZ + 3*XX
212  const mnt6_Fq3 w = mnt6_G2::mul_by_a(ZZ) + (XX + XX + XX);
213  const mnt6_Fq3 Y1Z1 = (this->Y) * (this->Z);
214  // s = 2*Y1*Z1
215  const mnt6_Fq3 s = Y1Z1 + Y1Z1;
216  // ss = s^2
217  const mnt6_Fq3 ss = s.squared();
218  // sss = s*ss
219  const mnt6_Fq3 sss = s * ss;
220  // R = Y1*s
221  const mnt6_Fq3 R = (this->Y) * s;
222  // RR = R^2
223  const mnt6_Fq3 RR = R.squared();
224  // B = (X1+R)^2 - XX - RR
225  const mnt6_Fq3 B = ((this->X) + R).squared() - XX - RR;
226  // h = w^2 - 2*B
227  const mnt6_Fq3 h = w.squared() - (B + B);
228  // X3 = h*s
229  const mnt6_Fq3 X3 = h * s;
230  // Y3 = w*(B-h) - 2*RR
231  const mnt6_Fq3 Y3 = w * (B - h) - (RR + RR);
232  // Z3 = sss
233  const mnt6_Fq3 Z3 = sss;
234 
235  return mnt6_G2(X3, Y3, Z3);
236  }
237 
238  // if we have arrived here we are in the add case
239  // Z1Z2 = Z1*Z2
240  const mnt6_Fq3 Z1Z2 = (this->Z) * (other.Z);
241  // u = Y2*Z1-Y1Z2
242  const mnt6_Fq3 u = Y2Z1 - Y1Z2;
243  // uu = u^2
244  const mnt6_Fq3 uu = u.squared();
245  // v = X2*Z1-X1Z2
246  const mnt6_Fq3 v = X2Z1 - X1Z2;
247  // vv = v^2
248  const mnt6_Fq3 vv = v.squared();
249  // vvv = v*vv
250  const mnt6_Fq3 vvv = v * vv;
251  // R = vv*X1Z2
252  const mnt6_Fq3 R = vv * X1Z2;
253  // A = uu*Z1Z2 - vvv - 2*R
254  const mnt6_Fq3 A = uu * Z1Z2 - (vvv + R + R);
255  // X3 = v*A
256  const mnt6_Fq3 X3 = v * A;
257  // Y3 = u*(R-A) - vvv*Y1Z2
258  const mnt6_Fq3 Y3 = u * (R - A) - vvv * Y1Z2;
259  // Z3 = vvv*Z1Z2
260  const mnt6_Fq3 Z3 = vvv * Z1Z2;
261 
262  return mnt6_G2(X3, Y3, Z3);
263 }
264 
266 {
267  return mnt6_G2(this->X, -(this->Y), this->Z);
268 }
269 
270 mnt6_G2 mnt6_G2::operator-(const mnt6_G2 &other) const
271 {
272  return (*this) + (-other);
273 }
274 
275 mnt6_G2 mnt6_G2::add(const mnt6_G2 &other) const
276 {
277  // handle special cases having to do with O
278  if (this->is_zero()) {
279  return other;
280  }
281 
282  if (other.is_zero()) {
283  return (*this);
284  }
285 
286  // no need to handle points of order 2,4
287  // (they cannot exist in a prime-order subgroup)
288 
289  // handle double case
290  if (this->operator==(other)) {
291  return this->dbl();
292  }
293 
294 #ifdef PROFILE_OP_COUNTS
295  this->add_cnt++;
296 #endif
297  // NOTE: does not handle O and pts of order 2,4
298  // http://www.hyperelliptic.org/EFD/g1p/auto-shortw-projective.html#addition-add-1998-cmo-2
299 
300  // Y1Z2 = Y1*Z2
301  const mnt6_Fq3 Y1Z2 = (this->Y) * (other.Z);
302  // X1Z2 = X1*Z2
303  const mnt6_Fq3 X1Z2 = (this->X) * (other.Z);
304  // Z1Z2 = Z1*Z2
305  const mnt6_Fq3 Z1Z2 = (this->Z) * (other.Z);
306  // u = Y2*Z1-Y1Z2
307  const mnt6_Fq3 u = (other.Y) * (this->Z) - Y1Z2;
308  // uu = u^2
309  const mnt6_Fq3 uu = u.squared();
310  // v = X2*Z1-X1Z2
311  const mnt6_Fq3 v = (other.X) * (this->Z) - X1Z2;
312  // vv = v^2
313  const mnt6_Fq3 vv = v.squared();
314  // vvv = v*vv
315  const mnt6_Fq3 vvv = v * vv;
316  // R = vv*X1Z2
317  const mnt6_Fq3 R = vv * X1Z2;
318  // A = uu*Z1Z2 - vvv - 2*R
319  const mnt6_Fq3 A = uu * Z1Z2 - (vvv + R + R);
320  // X3 = v*A
321  const mnt6_Fq3 X3 = v * A;
322  // Y3 = u*(R-A) - vvv*Y1Z2
323  const mnt6_Fq3 Y3 = u * (R - A) - vvv * Y1Z2;
324  // Z3 = vvv*Z1Z2
325  const mnt6_Fq3 Z3 = vvv * Z1Z2;
326 
327  return mnt6_G2(X3, Y3, Z3);
328 }
329 
330 mnt6_G2 mnt6_G2::mixed_add(const mnt6_G2 &other) const
331 {
332 #ifdef PROFILE_OP_COUNTS
333  this->add_cnt++;
334 #endif
335  // NOTE: does not handle O and pts of order 2,4
336  // http://www.hyperelliptic.org/EFD/g1p/auto-shortw-projective.html#addition-add-1998-cmo-2
337  // assert(other.Z == mnt6_Fq3::one());
338 
339  if (this->is_zero()) {
340  return other;
341  }
342 
343  if (other.is_zero()) {
344  return (*this);
345  }
346 
347 #ifdef DEBUG
348  assert(other.is_special());
349 #endif
350 
351  // X1Z2 = X1*Z2 (but other is special and not zero)
352  const mnt6_Fq3 &X1Z2 = (this->X);
353  // X2Z1 = X2*Z1
354  const mnt6_Fq3 X2Z1 = (this->Z) * (other.X);
355 
356  // (used both in add and double checks)
357 
358  // Y1Z2 = Y1*Z2 (but other is special and not zero)
359  const mnt6_Fq3 &Y1Z2 = (this->Y);
360  // Y2Z1 = Y2*Z1
361  const mnt6_Fq3 Y2Z1 = (this->Z) * (other.Y);
362 
363  if (X1Z2 == X2Z1 && Y1Z2 == Y2Z1) {
364  return this->dbl();
365  }
366 
367  // u = Y2*Z1-Y1
368  const mnt6_Fq3 u = Y2Z1 - this->Y;
369  // uu = u2
370  const mnt6_Fq3 uu = u.squared();
371  // v = X2*Z1-X1
372  const mnt6_Fq3 v = X2Z1 - this->X;
373  // vv = v2
374  const mnt6_Fq3 vv = v.squared();
375  // vvv = v*vv
376  const mnt6_Fq3 vvv = v * vv;
377  // R = vv*X1
378  const mnt6_Fq3 R = vv * this->X;
379  // A = uu*Z1-vvv-2*R
380  const mnt6_Fq3 A = uu * this->Z - vvv - R - R;
381  // X3 = v*A
382  const mnt6_Fq3 X3 = v * A;
383  // Y3 = u*(R-A)-vvv*Y1
384  const mnt6_Fq3 Y3 = u * (R - A) - vvv * this->Y;
385  // Z3 = vvv*Z1
386  const mnt6_Fq3 Z3 = vvv * this->Z;
387 
388  return mnt6_G2(X3, Y3, Z3);
389 }
390 
392 {
393 #ifdef PROFILE_OP_COUNTS
394  this->dbl_cnt++;
395 #endif
396  if (this->is_zero()) {
397  return (*this);
398  } else {
399  // NOTE: does not handle O and pts of order 2,4
400  // http://www.hyperelliptic.org/EFD/g1p/auto-shortw-projective.html#doubling-dbl-2007-bl
401 
402  // XX = X1^2
403  const mnt6_Fq3 XX = (this->X).squared();
404  // ZZ = Z1^2
405  const mnt6_Fq3 ZZ = (this->Z).squared();
406  // w = a*ZZ + 3*XX
407  const mnt6_Fq3 w = mnt6_G2::mul_by_a(ZZ) + (XX + XX + XX);
408  const mnt6_Fq3 Y1Z1 = (this->Y) * (this->Z);
409  // s = 2*Y1*Z1
410  const mnt6_Fq3 s = Y1Z1 + Y1Z1;
411  // ss = s^2
412  const mnt6_Fq3 ss = s.squared();
413  // sss = s*ss
414  const mnt6_Fq3 sss = s * ss;
415  // R = Y1*s
416  const mnt6_Fq3 R = (this->Y) * s;
417  // RR = R^2
418  const mnt6_Fq3 RR = R.squared();
419  // B = (X1+R)^2 - XX - RR
420  const mnt6_Fq3 B = ((this->X) + R).squared() - XX - RR;
421  // h = w^2-2*B
422  const mnt6_Fq3 h = w.squared() - (B + B);
423  // X3 = h*s
424  const mnt6_Fq3 X3 = h * s;
425  // Y3 = w*(B-h) - 2*RR
426  const mnt6_Fq3 Y3 = w * (B - h) - (RR + RR);
427  // Z3 = sss
428  const mnt6_Fq3 Z3 = sss;
429 
430  return mnt6_G2(X3, Y3, Z3);
431  }
432 }
433 
435 {
436  return mnt6_G2(
437  mnt6_twist_mul_by_q_X * (this->X).Frobenius_map(1),
438  mnt6_twist_mul_by_q_Y * (this->Y).Frobenius_map(1),
439  (this->Z).Frobenius_map(1));
440 }
441 
442 mnt6_G2 mnt6_G2::mul_by_cofactor() const { return mnt6_G2::h * (*this); }
443 
445 {
446  if (this->is_zero()) {
447  return true;
448  } else {
449 
450  // y^2 = x^3 + ax + b
451  //
452  // We are using projective, so equation we need to check is actually
453  //
454  // (y/z)^2 = (x/z)^3 + a (x/z) + b
455  // z y^2 = x^3 + a z^2 x + b z^3
456  //
457  // z (y^2 - b z^2) = x ( x^2 + a z^2)
458  const mnt6_Fq3 X2 = this->X.squared();
459  const mnt6_Fq3 Y2 = this->Y.squared();
460  const mnt6_Fq3 Z2 = this->Z.squared();
461  const mnt6_Fq3 aZ2 = mnt6_twist_coeff_a * Z2;
462 
463  return (
464  this->Z * (Y2 - mnt6_twist_coeff_b * Z2) == this->X * (X2 + aZ2));
465  }
466 }
467 
469 {
470  return zero() == scalar_field::mod * (*this);
471 }
472 
473 const mnt6_G2 &mnt6_G2::zero() { return G2_zero; }
474 
475 const mnt6_G2 &mnt6_G2::one() { return G2_one; }
476 
478 {
479  return (mnt6_Fr::random_element().as_bigint()) * G2_one;
480 }
481 
482 void mnt6_G2::write_uncompressed(std::ostream &out) const
483 {
484  mnt6_G2 copy(*this);
485  copy.to_affine_coordinates();
486 
487  out << (copy.is_zero() ? 1 : 0) << OUTPUT_SEPARATOR;
488  out << copy.X << OUTPUT_SEPARATOR << copy.Y;
489 }
490 
491 void mnt6_G2::write_compressed(std::ostream &out) const
492 {
493  mnt6_G2 copy(*this);
494  copy.to_affine_coordinates();
495 
496  out << (copy.is_zero() ? 1 : 0) << OUTPUT_SEPARATOR;
497  /* storing LSB of Y */
498  out << copy.X << OUTPUT_SEPARATOR
499  << (copy.Y.coeffs[0].as_bigint().data[0] & 1);
500 }
501 
502 void mnt6_G2::read_uncompressed(std::istream &in, mnt6_G2 &g)
503 {
504  char is_zero;
505  mnt6_Fq3 tX, tY;
506 
507  in >> is_zero >> tX >> tY;
508  is_zero -= '0';
509 
510  // using projective coordinates
511  if (!is_zero) {
512  g.X = tX;
513  g.Y = tY;
514  g.Z = mnt6_Fq3::one();
515  } else {
516  g = mnt6_G2::zero();
517  }
518 }
519 
520 void mnt6_G2::read_compressed(std::istream &in, mnt6_G2 &g)
521 {
522  char is_zero;
523  mnt6_Fq3 tX, tY;
524 
525  // this reads is_zero;
526  in.read((char *)&is_zero, 1);
527  is_zero -= '0';
529 
530  unsigned char Y_lsb;
531  in >> tX;
533  in.read((char *)&Y_lsb, 1);
534  Y_lsb -= '0';
535 
536  // y = +/- sqrt(x^3 + a*x + b)
537  if (!is_zero) {
538  const mnt6_Fq3 tX2 = tX.squared();
539  const mnt6_Fq3 tY2 =
540  (tX2 + mnt6_twist_coeff_a) * tX + mnt6_twist_coeff_b;
541  tY = tY2.sqrt();
542 
543  if ((tY.coeffs[0].as_bigint().data[0] & 1) != Y_lsb) {
544  tY = -tY;
545  }
546  }
547 
548  // using projective coordinates
549  if (!is_zero) {
550  g.X = tX;
551  g.Y = tY;
552  g.Z = mnt6_Fq3::one();
553  } else {
554  g = mnt6_G2::zero();
555  }
556 }
557 
558 void mnt6_G2::batch_to_special_all_non_zeros(std::vector<mnt6_G2> &vec)
559 {
560  std::vector<mnt6_Fq3> Z_vec;
561  Z_vec.reserve(vec.size());
562 
563  for (auto &el : vec) {
564  Z_vec.emplace_back(el.Z);
565  }
566  batch_invert<mnt6_Fq3>(Z_vec);
567 
568  const mnt6_Fq3 one = mnt6_Fq3::one();
569 
570  for (size_t i = 0; i < vec.size(); ++i) {
571  vec[i] = mnt6_G2(vec[i].X * Z_vec[i], vec[i].Y * Z_vec[i], one);
572  }
573 }
574 
575 std::ostream &operator<<(std::ostream &out, const mnt6_G2 &g)
576 {
577 #ifdef NO_PT_COMPRESSION
578  g.write_uncompressed(out);
579 #else
580  g.write_compressed(out);
581 #endif
582  return out;
583 }
584 
585 std::istream &operator>>(std::istream &in, mnt6_G2 &g)
586 {
587 #ifdef NO_PT_COMPRESSION
589 #else
591 #endif
592  return in;
593 }
594 
595 } // namespace libff
libff::mnt6_G2::is_in_safe_subgroup
bool is_in_safe_subgroup() const
Definition: mnt6_g2.cpp:468
libff::mnt6_twist_mul_by_a_c0
mnt6_Fq mnt6_twist_mul_by_a_c0
Definition: mnt6_init.cpp:27
libff::mnt6_twist_mul_by_b_c2
mnt6_Fq mnt6_twist_mul_by_b_c2
Definition: mnt6_init.cpp:32
libff::mnt6_G2::coeff_b
static mnt6_Fq3 coeff_b
Definition: mnt6_g2.hpp:39
libff::mnt6_G2::Z
mnt6_Fq3 Z
Definition: mnt6_g2.hpp:51
libff::Fp_model::random_element
static Fp_model< n, modulus > random_element()
returns random element of Fp_model
libff::mnt6_G2::coeff_a
static mnt6_Fq3 coeff_a
Definition: mnt6_g2.hpp:38
libff::mnt6_G2::one
static const mnt6_G2 & one()
Definition: mnt6_g2.cpp:475
libff
Definition: ffi.cpp:8
libff::Fp3_model< mnt6_q_limbs, mnt6_modulus_q >::one
static Fp3_model< n, modulus > one()
libff::mnt6_twist_mul_by_b_c1
mnt6_Fq mnt6_twist_mul_by_b_c1
Definition: mnt6_init.cpp:31
libff::mnt6_twist_mul_by_q_Y
mnt6_Fq mnt6_twist_mul_by_q_Y
Definition: mnt6_init.cpp:34
libff::operator>>
std::istream & operator>>(std::istream &in, alt_bn128_G1 &g)
Definition: alt_bn128_g1.cpp:446
libff::mnt6_G2::X
mnt6_Fq3 X
Definition: mnt6_g2.hpp:51
libff::mnt6_twist_mul_by_a_c1
mnt6_Fq mnt6_twist_mul_by_a_c1
Definition: mnt6_init.cpp:28
libff::mnt6_twist_mul_by_q_X
mnt6_Fq mnt6_twist_mul_by_q_X
Definition: mnt6_init.cpp:33
libff::mnt6_G2::operator-
mnt6_G2 operator-() const
Definition: mnt6_g2.cpp:265
libff::mnt6_twist_coeff_b
mnt6_Fq3 mnt6_twist_coeff_b
Definition: mnt6_init.cpp:26
libff::mnt6_G2::print
void print() const
Definition: mnt6_g2.cpp:56
libff::mnt6_G2::G2_zero
static mnt6_G2 G2_zero
Definition: mnt6_g2.hpp:35
libff::Fp3_model::coeffs
my_Fp coeffs[3]
Definition: fp3.hpp:59
libff::mnt6_G2::print_coordinates
void print_coordinates() const
Definition: mnt6_g2.cpp:80
OUTPUT_SEPARATOR
#define OUTPUT_SEPARATOR
Definition: serialization.hpp:69
libff::mnt6_G2::is_special
bool is_special() const
Definition: mnt6_g2.cpp:125
libff::mnt6_G2
Definition: mnt6_g2.hpp:26
libff::mnt6_G2::Y
mnt6_Fq3 Y
Definition: mnt6_g2.hpp:51
libff::mnt6_G2::operator!=
bool operator!=(const mnt6_G2 &other) const
Definition: mnt6_g2.cpp:161
libff::mnt6_G2::is_well_formed
bool is_well_formed() const
Definition: mnt6_g2.cpp:444
libff::mnt6_twist_coeff_a
mnt6_Fq3 mnt6_twist_coeff_a
Definition: mnt6_init.cpp:25
libff::mnt6_G2::operator==
bool operator==(const mnt6_G2 &other) const
Definition: mnt6_g2.cpp:136
libff::mnt6_G2::dbl
mnt6_G2 dbl() const
Definition: mnt6_g2.cpp:391
libff::consume_OUTPUT_SEPARATOR
void consume_OUTPUT_SEPARATOR(std::istream &in)
libff::mnt6_G2::write_uncompressed
void write_uncompressed(std::ostream &) const
Definition: mnt6_g2.cpp:482
libff::Fp_model< mnt6_q_limbs, mnt6_modulus_q >::num_limbs
static const mp_size_t num_limbs
Definition: fp.hpp:47
mnt6_g2.hpp
libff::mnt6_G2::twist
static mnt6_Fq3 twist
Definition: mnt6_g2.hpp:37
libff::mnt6_G2::G2_one
static mnt6_G2 G2_one
Definition: mnt6_g2.hpp:36
libff::mnt6_Fq3
Fp3_model< mnt6_q_limbs, mnt6_modulus_q > mnt6_Fq3
Definition: mnt6_init.hpp:38
libff::mnt6_G2::fixed_base_exp_window_table
static std::vector< size_t > fixed_base_exp_window_table
Definition: mnt6_g2.hpp:34
libff::mnt6_G2::zero
static const mnt6_G2 & zero()
Definition: mnt6_g2.cpp:473
libff::mnt6_G2::mnt6_G2
mnt6_G2()
Definition: mnt6_g2.cpp:33
libff::mnt6_twist_mul_by_a_c2
mnt6_Fq mnt6_twist_mul_by_a_c2
Definition: mnt6_init.cpp:29
libff::Fp3_model
Definition: fp3.hpp:18
libff::mnt6_G2::wnaf_window_table
static std::vector< size_t > wnaf_window_table
Definition: mnt6_g2.hpp:33
libff::mnt6_G2::mul_by_q
mnt6_G2 mul_by_q() const
Definition: mnt6_g2.cpp:434
libff::Fp_model::as_bigint
bigint< n > as_bigint() const
libff::mnt6_G2::read_uncompressed
static void read_uncompressed(std::istream &, mnt6_G2 &)
Definition: mnt6_g2.cpp:502
libff::mnt6_G2::mul_by_a
static mnt6_Fq3 mul_by_a(const mnt6_Fq3 &elt)
Definition: mnt6_g2.cpp:40
libff::mnt6_G2::write_compressed
void write_compressed(std::ostream &) const
Definition: mnt6_g2.cpp:491
libff::mnt6_G2::h
static bigint< h_limbs > h
Definition: mnt6_g2.hpp:49
libff::mnt6_G2::operator+
mnt6_G2 operator+(const mnt6_G2 &other) const
Definition: mnt6_g2.cpp:166
libff::operator<<
std::ostream & operator<<(std::ostream &out, const alt_bn128_G1 &g)
Definition: alt_bn128_g1.cpp:436
libff::Fp3_model::inverse
Fp3_model inverse() const
libff::Fp3_model::sqrt
Fp3_model sqrt() const
HAS TO BE A SQUARE (else does not terminate)
libff::mnt6_G2::mul_by_cofactor
mnt6_G2 mul_by_cofactor() const
Definition: mnt6_g2.cpp:442
libff::Fp3_model::is_zero
bool is_zero() const
Definition: fp3.hpp:89
libff::mnt6_G2::batch_to_special_all_non_zeros
static void batch_to_special_all_non_zeros(std::vector< mnt6_G2 > &vec)
Definition: mnt6_g2.cpp:558
libff::mnt6_G2::read_compressed
static void read_compressed(std::istream &, mnt6_G2 &)
Definition: mnt6_g2.cpp:520
libff::Fp_model::mod
static const constexpr bigint< n > & mod
Definition: fp.hpp:48
libff::mnt6_G2::add
mnt6_G2 add(const mnt6_G2 &other) const
Definition: mnt6_g2.cpp:275
libff::mnt6_G2::is_zero
bool is_zero() const
Definition: mnt6_g2.cpp:130
libff::mnt6_G2::random_element
static mnt6_G2 random_element()
Definition: mnt6_g2.cpp:477
libff::mnt6_G2::mixed_add
mnt6_G2 mixed_add(const mnt6_G2 &other) const
Definition: mnt6_g2.cpp:330
libff::Fp3_model::squared
Fp3_model squared() const
libff::mnt6_G2::mul_by_b
static mnt6_Fq3 mul_by_b(const mnt6_Fq3 &elt)
Definition: mnt6_g2.cpp:48
libff::mnt6_G2::to_affine_coordinates
void to_affine_coordinates()
Definition: mnt6_g2.cpp:109
libff::mnt6_G2::to_special
void to_special()
Definition: mnt6_g2.cpp:123
libff::Fp3_model< mnt6_q_limbs, mnt6_modulus_q >::zero
static Fp3_model< n, modulus > zero()
libff::mnt6_twist_mul_by_b_c0
mnt6_Fq mnt6_twist_mul_by_b_c0
Definition: mnt6_init.cpp:30