]> Cypherpunks.ru repositories - gogost.git/blobdiff - gost3410/curve.go
More thread-safe gost3410
[gogost.git] / gost3410 / curve.go
index a3685ce047e7be3b7c11ea58f649c09761255d46..a5f8d5125fe48da5d0f5573527e3a2a359da42f2 100644 (file)
@@ -1,5 +1,5 @@
 // GoGOST -- Pure Go GOST cryptographic functions library
-// Copyright (C) 2015-2020 Sergey Matveev <stargrave@stargrave.org>
+// Copyright (C) 2015-2021 Sergey Matveev <stargrave@stargrave.org>
 //
 // This program is free software: you can redistribute it and/or modify
 // it under the terms of the GNU General Public License as published by
@@ -48,11 +48,6 @@ type Curve struct {
        X *big.Int
        Y *big.Int
 
-       // Temporary variable for the add method
-       t  *big.Int
-       tx *big.Int
-       ty *big.Int
-
        // Cached s/t parameters for Edwards curve points conversion
        edS *big.Int
        edT *big.Int
@@ -67,9 +62,6 @@ func NewCurve(p, q, a, b, x, y, e, d, co *big.Int) (*Curve, error) {
                B:    b,
                X:    x,
                Y:    y,
-               t:    big.NewInt(0),
-               tx:   big.NewInt(0),
-               ty:   big.NewInt(0),
        }
        r1 := big.NewInt(0)
        r2 := big.NewInt(0)
@@ -96,6 +88,10 @@ func NewCurve(p, q, a, b, x, y, e, d, co *big.Int) (*Curve, error) {
        return &c, nil
 }
 
+func (c *Curve) PointSize() int {
+       return PointSize(c.P)
+}
+
 func (c *Curve) pos(v *big.Int) {
        if v.Cmp(zero) < 0 {
                v.Add(v, c.P)
@@ -103,38 +99,39 @@ func (c *Curve) pos(v *big.Int) {
 }
 
 func (c *Curve) add(p1x, p1y, p2x, p2y *big.Int) {
+       var t, tx, ty big.Int
        if p1x.Cmp(p2x) == 0 && p1y.Cmp(p2y) == 0 {
                // double
-               c.t.Mul(p1x, p1x)
-               c.t.Mul(c.t, bigInt3)
-               c.t.Add(c.t, c.A)
-               c.tx.Mul(bigInt2, p1y)
-               c.tx.ModInverse(c.tx, c.P)
-               c.t.Mul(c.t, c.tx)
-               c.t.Mod(c.t, c.P)
+               t.Mul(p1x, p1x)
+               t.Mul(&t, bigInt3)
+               t.Add(&t, c.A)
+               tx.Mul(bigInt2, p1y)
+               tx.ModInverse(&tx, c.P)
+               t.Mul(&t, &tx)
+               t.Mod(&t, c.P)
        } else {
-               c.tx.Sub(p2x, p1x)
-               c.tx.Mod(c.tx, c.P)
-               c.pos(c.tx)
-               c.ty.Sub(p2y, p1y)
-               c.ty.Mod(c.ty, c.P)
-               c.pos(c.ty)
-               c.t.ModInverse(c.tx, c.P)
-               c.t.Mul(c.t, c.ty)
-               c.t.Mod(c.t, c.P)
+               tx.Sub(p2x, p1x)
+               tx.Mod(&tx, c.P)
+               c.pos(&tx)
+               ty.Sub(p2y, p1y)
+               ty.Mod(&ty, c.P)
+               c.pos(&ty)
+               t.ModInverse(&tx, c.P)
+               t.Mul(&t, &ty)
+               t.Mod(&t, c.P)
        }
-       c.tx.Mul(c.t, c.t)
-       c.tx.Sub(c.tx, p1x)
-       c.tx.Sub(c.tx, p2x)
-       c.tx.Mod(c.tx, c.P)
-       c.pos(c.tx)
-       c.ty.Sub(p1x, c.tx)
-       c.ty.Mul(c.ty, c.t)
-       c.ty.Sub(c.ty, p1y)
-       c.ty.Mod(c.ty, c.P)
-       c.pos(c.ty)
-       p1x.Set(c.tx)
-       p1y.Set(c.ty)
+       tx.Mul(&t, &t)
+       tx.Sub(&tx, p1x)
+       tx.Sub(&tx, p2x)
+       tx.Mod(&tx, c.P)
+       c.pos(&tx)
+       ty.Sub(p1x, &tx)
+       ty.Mul(&ty, &t)
+       ty.Sub(&ty, p1y)
+       ty.Mod(&ty, c.P)
+       c.pos(&ty)
+       p1x.Set(&tx)
+       p1y.Set(&ty)
 }
 
 func (c *Curve) Exp(degree, xS, yS *big.Int) (*big.Int, *big.Int, error) {
@@ -155,3 +152,15 @@ func (c *Curve) Exp(degree, xS, yS *big.Int) (*big.Int, *big.Int, error) {
        }
        return tx, ty, nil
 }
+
+func (our *Curve) Equal(their *Curve) bool {
+       return our.P.Cmp(their.P) == 0 &&
+               our.Q.Cmp(their.Q) == 0 &&
+               our.A.Cmp(their.A) == 0 &&
+               our.B.Cmp(their.B) == 0 &&
+               our.X.Cmp(their.X) == 0 &&
+               our.Y.Cmp(their.Y) == 0 &&
+               ((our.E == nil && their.E == nil) || our.E.Cmp(their.E) == 0) &&
+               ((our.D == nil && their.D == nil) || our.D.Cmp(their.D) == 0) &&
+               our.Co.Cmp(their.Co) == 0
+}