geFromfeFrombytesVartime static method

void geFromfeFrombytesVartime(
  1. GroupElementP2 r,
  2. List<int> s
)

Implementation

static void geFromfeFrombytesVartime(GroupElementP2 r, List<int> s) {
  s.asMin32("geFromfeFrombytesVartime");
  final FieldElement u = FieldElement(),
      v = FieldElement(),
      w = FieldElement(),
      x = FieldElement(),
      y = FieldElement(),
      z = FieldElement();

  /* From fe_frombytes.c */

  BigInt h0 = _load4(s, 0);
  BigInt h1 = _load3(s, 4) << 6;
  BigInt h2 = _load3(s, 7) << 5;
  BigInt h3 = _load3(s, 10) << 3;
  BigInt h4 = _load3(s, 13) << 2;
  BigInt h5 = _load4(s, 16);
  BigInt h6 = _load3(s, 20) << 7;
  BigInt h7 = _load3(s, 23) << 5;
  BigInt h8 = _load3(s, 26) << 4;
  BigInt h9 = _load3(s, 29) << 2;
  BigInt carry0;
  BigInt carry1;
  BigInt carry2;
  BigInt carry3;
  BigInt carry4;
  BigInt carry5;
  BigInt carry6;
  BigInt carry7;
  BigInt carry8;
  BigInt carry9;

  carry9 = (h9 + _bitMaskFor24) >> 25;
  h0 += carry9 * BigInt.from(19);
  h9 -= carry9 << 25;
  carry1 = (h1 + _bitMaskFor24) >> 25;
  h2 += carry1;
  h1 -= carry1 << 25;
  carry3 = (h3 + _bitMaskFor24) >> 25;
  h4 += carry3;
  h3 -= carry3 << 25;
  carry5 = (h5 + _bitMaskFor24) >> 25;
  h6 += carry5;
  h5 -= carry5 << 25;
  carry7 = (h7 + _bitMaskFor24) >> 25;
  h8 += carry7;
  h7 -= carry7 << 25;

  carry0 = (h0 + _bitMaskFor25) >> 26;
  h1 += carry0;
  h0 -= carry0 << 26;
  carry2 = (h2 + _bitMaskFor25) >> 26;
  h3 += carry2;
  h2 -= carry2 << 26;
  carry4 = (h4 + _bitMaskFor25) >> 26;
  h5 += carry4;
  h4 -= carry4 << 26;
  carry6 = (h6 + _bitMaskFor25) >> 26;
  h7 += carry6;
  h6 -= carry6 << 26;
  carry8 = (h8 + _bitMaskFor25) >> 26;
  h9 += carry8;
  h8 -= carry8 << 26;

  u.h[0] = h0.toInt32;
  u.h[1] = h1.toInt32;
  u.h[2] = h2.toInt32;
  u.h[3] = h3.toInt32;
  u.h[4] = h4.toInt32;
  u.h[5] = h5.toInt32;
  u.h[6] = h6.toInt32;
  u.h[7] = h7.toInt32;
  u.h[8] = h8.toInt32;
  u.h[9] = h9.toInt32;

  /* End fe_frombytes.c */

  feSq2(v, u); /* 2 * u^2 */
  fe1(w);
  feAdd(w, v, w); /* w = 2 * u^2 + 1 */
  feSq(x, w); /* w^2 */
  feMul(y, CryptoOpsConst.ma2, v); /* -2 * A^2 * u^2 */
  feAdd(x, x, y); /* x = w^2 - 2 * A^2 * u^2 */
  feDivpowm1(r.x, w, x); /* (w / x)^(m + 1) */
  feSq(y, r.x);
  feMul(x, y, x);
  feSub(y, w, x);
  feCopy(z, CryptoOpsConst.ma);
  if (feIsnonzero(y) != 0) {
    feAdd(y, w, x);
    if (feIsnonzero(y) != 0) {
      return _negative(x: x, r: r, y: y, w: w, z: z);
    } else {
      feMul(r.x, r.x, CryptoOpsConst.fffb1);
    }
  } else {
    feMul(r.x, r.x, CryptoOpsConst.fffb2);
  }
  feMul(r.x, r.x, u); /* u * sqrt(2 * A * (A + 2) * w / x) */
  feMul(z, z, v); /* -2 * A * u^2 */
  _setSign(r: r, sign: 0, z: z, w: w);
}