/// <summary> /// Point dooubling over the curve /// </summary> private bool PointDouble( BigInteger.ModulusRing ring, ECPoint p1, out ECPoint p3) { if (p1 is ECPointAtInfinity) { p3 = p1; return true; } if (p1.Y == 0) { p3 = new ECPointAtInfinity(); return true; } // x3 = {(3 * x1^2 + a)/(2 * y1)}^2 - (2 * x1) // y3 = {(3 * x1^2 + a)/(2 * y1)} * (x1 - x3) - y1 try { BigInteger x1 = p1.X; BigInteger y1 = p1.Y; BigInteger x1_2 = ring.Multiply(x1, x1); BigInteger lambda = ring.Multiply(x1_2 + x1_2 + x1_2 + a, (y1 + y1).ModInverse(p)); BigInteger x3 = ring.Difference(ring.Multiply(lambda, lambda), x1 + x1); BigInteger y3 = ring.Difference(ring.Multiply(lambda, ring.Difference(x1, x3)), y1); p3 = new ECPoint(x3, y3); return true; } catch (Exception) { p3 = null; return false; } }
/// <summary> /// Point addition over the curve /// </summary> private bool PointAdd( BigInteger.ModulusRing ring, ECPoint p1, ECPoint p2, out ECPoint p3) { if (p1 is ECPointAtInfinity) { p3 = p2; return true; } if (p2 is ECPointAtInfinity) { p3 = p1; return true; } if (p1.X == p2.X) { if (p1.Y == p2.Y) { return PointDouble(ring, p1, out p3); } else { p3 = new ECPointAtInfinity(); return true; } } // x3 = {(y2 - y1)/(x2 - x1)}^2 - (x1 + x2) // y3 = {(y2 - y1)/(x2 - x1)} * (x1 - x3) - y1 try { BigInteger x1 = p1.X; BigInteger y1 = p1.Y; BigInteger x2 = p2.X; BigInteger y2 = p2.Y; BigInteger lambda = ring.Multiply(ring.Difference(y2, y1), ring.Difference(x2, x1).ModInverse(p)); BigInteger x3 = ring.Difference(ring.Multiply(lambda, lambda), x1 + x2); BigInteger y3 = ring.Difference(ring.Multiply(lambda, ring.Difference(x1, x3)), y1); p3 = new ECPoint(x3, y3); return true; } catch (Exception) { p3 = null; return false; } }