From 3cb0eb371924a30eab83a5b4492017643d1b5e2c Mon Sep 17 00:00:00 2001 From: Ignacio Hagopian Date: Tue, 5 Sep 2023 10:45:49 -0300 Subject: [PATCH] edwards: improve the performance of Add, MixedAdd and IsOnCurve (#441) * edwards: add benchmark for Add, MixedAdd and IsOnCurve Signed-off-by: Ignacio Hagopian * edwards: avoid allocation in MixedAdd, Add and IsOnCurve Signed-off-by: Ignacio Hagopian * go generate Signed-off-by: Ignacio Hagopian * tests/edwards: double check IsOnCurve expectation Signed-off-by: Ignacio Hagopian --------- Signed-off-by: Ignacio Hagopian --- ecc/bls12-377/twistededwards/point.go | 20 ++-- ecc/bls12-377/twistededwards/point_test.go | 104 ++++++++++++++++++ ecc/bls12-378/twistededwards/point.go | 20 ++-- ecc/bls12-378/twistededwards/point_test.go | 104 ++++++++++++++++++ ecc/bls12-381/bandersnatch/point.go | 20 ++-- ecc/bls12-381/bandersnatch/point_test.go | 104 ++++++++++++++++++ ecc/bls12-381/twistededwards/point.go | 20 ++-- ecc/bls12-381/twistededwards/point_test.go | 104 ++++++++++++++++++ ecc/bls24-315/twistededwards/point.go | 20 ++-- ecc/bls24-315/twistededwards/point_test.go | 104 ++++++++++++++++++ ecc/bls24-317/twistededwards/point.go | 20 ++-- ecc/bls24-317/twistededwards/point_test.go | 104 ++++++++++++++++++ ecc/bn254/twistededwards/point.go | 20 ++-- ecc/bn254/twistededwards/point_test.go | 104 ++++++++++++++++++ ecc/bw6-633/twistededwards/point.go | 20 ++-- ecc/bw6-633/twistededwards/point_test.go | 104 ++++++++++++++++++ ecc/bw6-756/twistededwards/point.go | 20 ++-- ecc/bw6-756/twistededwards/point_test.go | 104 ++++++++++++++++++ ecc/bw6-761/twistededwards/point.go | 20 ++-- ecc/bw6-761/twistededwards/point_test.go | 104 ++++++++++++++++++ .../generator/edwards/template/point.go.tmpl | 20 ++-- .../edwards/template/tests/point.go.tmpl | 104 ++++++++++++++++++ 22 files changed, 1232 insertions(+), 132 deletions(-) diff --git a/ecc/bls12-377/twistededwards/point.go b/ecc/bls12-377/twistededwards/point.go index 225c89e0c..f8e953b2f 100644 --- a/ecc/bls12-377/twistededwards/point.go +++ b/ecc/bls12-377/twistededwards/point.go @@ -161,8 +161,7 @@ func NewPointAffine(x, y fr.Element) PointAffine { // IsOnCurve checks if a point is on the twisted Edwards curve func (p *PointAffine) IsOnCurve() bool { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var lhs, rhs, tmp fr.Element @@ -174,7 +173,7 @@ func (p *PointAffine) IsOnCurve() bool { tmp.Mul(&p.X, &p.X). Mul(&tmp, &p.Y). Mul(&tmp, &p.Y). - Mul(&tmp, &ecurve.D) + Mul(&tmp, &curveParams.D) rhs.SetOne().Add(&rhs, &tmp) return lhs.Equal(&rhs) @@ -190,8 +189,7 @@ func (p *PointAffine) Neg(p1 *PointAffine) *PointAffine { // Add adds two points (x,y), (u,v) on a twisted Edwards curve with parameters a, d // modifies p func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var xu, yv, xv, yu, dxyuv, one, denx, deny fr.Element pRes := new(PointAffine) @@ -204,7 +202,7 @@ func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { yv.Mul(&p1.Y, &p2.Y) pRes.Y.Sub(&yv, &xu) - dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &ecurve.D) + dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &curveParams.D) one.SetOne() denx.Add(&one, &dxyuv) deny.Sub(&one, &dxyuv) @@ -330,14 +328,13 @@ func (p *PointProj) FromAffine(p1 *PointAffine) *PointProj { // MixedAdd adds a point in projective to a point in affine coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-madd-2008-bbjlp func (p *PointProj) MixedAdd(p1 *PointProj, p2 *PointAffine) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var B, C, D, E, F, G, H, I fr.Element B.Square(&p1.Z) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) @@ -382,15 +379,14 @@ func (p *PointProj) Double(p1 *PointProj) *PointProj { // Add adds points in projective coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-add-2008-bbjlp func (p *PointProj) Add(p1, p2 *PointProj) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var A, B, C, D, E, F, G, H, I fr.Element A.Mul(&p1.Z, &p2.Z) B.Square(&A) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) diff --git a/ecc/bls12-377/twistededwards/point_test.go b/ecc/bls12-377/twistededwards/point_test.go index adf7fde3d..33770efbe 100644 --- a/ecc/bls12-377/twistededwards/point_test.go +++ b/ecc/bls12-377/twistededwards/point_test.go @@ -817,3 +817,107 @@ func BenchmarkNeg(b *testing.B) { } }) } + +func BenchmarkMixedAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + b.Run("Projective", func(b *testing.B) { + var accum PointProj + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var accum PointExtended + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) +} + +func BenchmarkAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("Affine", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + var accum PointAffine + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Projective", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointProj + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointExtended + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) +} + +func BenchmarkIsOnCurve(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("positive", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + if !point.IsOnCurve() { + b.Fatal("point should must be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) + + b.Run("negative", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + point.X.Add(&point.X, &point.X) + + if point.IsOnCurve() { + b.Fatal("point should not be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) +} diff --git a/ecc/bls12-378/twistededwards/point.go b/ecc/bls12-378/twistededwards/point.go index 93812b904..ba15bd171 100644 --- a/ecc/bls12-378/twistededwards/point.go +++ b/ecc/bls12-378/twistededwards/point.go @@ -161,8 +161,7 @@ func NewPointAffine(x, y fr.Element) PointAffine { // IsOnCurve checks if a point is on the twisted Edwards curve func (p *PointAffine) IsOnCurve() bool { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var lhs, rhs, tmp fr.Element @@ -174,7 +173,7 @@ func (p *PointAffine) IsOnCurve() bool { tmp.Mul(&p.X, &p.X). Mul(&tmp, &p.Y). Mul(&tmp, &p.Y). - Mul(&tmp, &ecurve.D) + Mul(&tmp, &curveParams.D) rhs.SetOne().Add(&rhs, &tmp) return lhs.Equal(&rhs) @@ -190,8 +189,7 @@ func (p *PointAffine) Neg(p1 *PointAffine) *PointAffine { // Add adds two points (x,y), (u,v) on a twisted Edwards curve with parameters a, d // modifies p func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var xu, yv, xv, yu, dxyuv, one, denx, deny fr.Element pRes := new(PointAffine) @@ -204,7 +202,7 @@ func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { yv.Mul(&p1.Y, &p2.Y) pRes.Y.Sub(&yv, &xu) - dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &ecurve.D) + dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &curveParams.D) one.SetOne() denx.Add(&one, &dxyuv) deny.Sub(&one, &dxyuv) @@ -330,14 +328,13 @@ func (p *PointProj) FromAffine(p1 *PointAffine) *PointProj { // MixedAdd adds a point in projective to a point in affine coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-madd-2008-bbjlp func (p *PointProj) MixedAdd(p1 *PointProj, p2 *PointAffine) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var B, C, D, E, F, G, H, I fr.Element B.Square(&p1.Z) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) @@ -382,15 +379,14 @@ func (p *PointProj) Double(p1 *PointProj) *PointProj { // Add adds points in projective coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-add-2008-bbjlp func (p *PointProj) Add(p1, p2 *PointProj) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var A, B, C, D, E, F, G, H, I fr.Element A.Mul(&p1.Z, &p2.Z) B.Square(&A) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) diff --git a/ecc/bls12-378/twistededwards/point_test.go b/ecc/bls12-378/twistededwards/point_test.go index 3926b8715..152d4b8bf 100644 --- a/ecc/bls12-378/twistededwards/point_test.go +++ b/ecc/bls12-378/twistededwards/point_test.go @@ -817,3 +817,107 @@ func BenchmarkNeg(b *testing.B) { } }) } + +func BenchmarkMixedAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + b.Run("Projective", func(b *testing.B) { + var accum PointProj + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var accum PointExtended + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) +} + +func BenchmarkAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("Affine", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + var accum PointAffine + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Projective", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointProj + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointExtended + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) +} + +func BenchmarkIsOnCurve(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("positive", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + if !point.IsOnCurve() { + b.Fatal("point should must be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) + + b.Run("negative", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + point.X.Add(&point.X, &point.X) + + if point.IsOnCurve() { + b.Fatal("point should not be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) +} diff --git a/ecc/bls12-381/bandersnatch/point.go b/ecc/bls12-381/bandersnatch/point.go index 28bae3e95..62edd905b 100644 --- a/ecc/bls12-381/bandersnatch/point.go +++ b/ecc/bls12-381/bandersnatch/point.go @@ -160,8 +160,7 @@ func NewPointAffine(x, y fr.Element) PointAffine { // IsOnCurve checks if a point is on the twisted Edwards curve func (p *PointAffine) IsOnCurve() bool { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var lhs, rhs, tmp fr.Element @@ -173,7 +172,7 @@ func (p *PointAffine) IsOnCurve() bool { tmp.Mul(&p.X, &p.X). Mul(&tmp, &p.Y). Mul(&tmp, &p.Y). - Mul(&tmp, &ecurve.D) + Mul(&tmp, &curveParams.D) rhs.SetOne().Add(&rhs, &tmp) return lhs.Equal(&rhs) @@ -189,8 +188,7 @@ func (p *PointAffine) Neg(p1 *PointAffine) *PointAffine { // Add adds two points (x,y), (u,v) on a twisted Edwards curve with parameters a, d // modifies p func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var xu, yv, xv, yu, dxyuv, one, denx, deny fr.Element pRes := new(PointAffine) @@ -203,7 +201,7 @@ func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { yv.Mul(&p1.Y, &p2.Y) pRes.Y.Sub(&yv, &xu) - dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &ecurve.D) + dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &curveParams.D) one.SetOne() denx.Add(&one, &dxyuv) deny.Sub(&one, &dxyuv) @@ -329,14 +327,13 @@ func (p *PointProj) FromAffine(p1 *PointAffine) *PointProj { // MixedAdd adds a point in projective to a point in affine coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-madd-2008-bbjlp func (p *PointProj) MixedAdd(p1 *PointProj, p2 *PointAffine) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var B, C, D, E, F, G, H, I fr.Element B.Square(&p1.Z) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) @@ -381,15 +378,14 @@ func (p *PointProj) Double(p1 *PointProj) *PointProj { // Add adds points in projective coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-add-2008-bbjlp func (p *PointProj) Add(p1, p2 *PointProj) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var A, B, C, D, E, F, G, H, I fr.Element A.Mul(&p1.Z, &p2.Z) B.Square(&A) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) diff --git a/ecc/bls12-381/bandersnatch/point_test.go b/ecc/bls12-381/bandersnatch/point_test.go index d5e6c7b53..ccc05c079 100644 --- a/ecc/bls12-381/bandersnatch/point_test.go +++ b/ecc/bls12-381/bandersnatch/point_test.go @@ -817,3 +817,107 @@ func BenchmarkNeg(b *testing.B) { } }) } + +func BenchmarkMixedAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + b.Run("Projective", func(b *testing.B) { + var accum PointProj + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var accum PointExtended + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) +} + +func BenchmarkAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("Affine", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + var accum PointAffine + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Projective", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointProj + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointExtended + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) +} + +func BenchmarkIsOnCurve(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("positive", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + if !point.IsOnCurve() { + b.Fatal("point should must be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) + + b.Run("negative", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + point.X.Add(&point.X, &point.X) + + if point.IsOnCurve() { + b.Fatal("point should not be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) +} diff --git a/ecc/bls12-381/twistededwards/point.go b/ecc/bls12-381/twistededwards/point.go index f7800fc9e..5e6d156d0 100644 --- a/ecc/bls12-381/twistededwards/point.go +++ b/ecc/bls12-381/twistededwards/point.go @@ -161,8 +161,7 @@ func NewPointAffine(x, y fr.Element) PointAffine { // IsOnCurve checks if a point is on the twisted Edwards curve func (p *PointAffine) IsOnCurve() bool { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var lhs, rhs, tmp fr.Element @@ -174,7 +173,7 @@ func (p *PointAffine) IsOnCurve() bool { tmp.Mul(&p.X, &p.X). Mul(&tmp, &p.Y). Mul(&tmp, &p.Y). - Mul(&tmp, &ecurve.D) + Mul(&tmp, &curveParams.D) rhs.SetOne().Add(&rhs, &tmp) return lhs.Equal(&rhs) @@ -190,8 +189,7 @@ func (p *PointAffine) Neg(p1 *PointAffine) *PointAffine { // Add adds two points (x,y), (u,v) on a twisted Edwards curve with parameters a, d // modifies p func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var xu, yv, xv, yu, dxyuv, one, denx, deny fr.Element pRes := new(PointAffine) @@ -204,7 +202,7 @@ func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { yv.Mul(&p1.Y, &p2.Y) pRes.Y.Sub(&yv, &xu) - dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &ecurve.D) + dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &curveParams.D) one.SetOne() denx.Add(&one, &dxyuv) deny.Sub(&one, &dxyuv) @@ -330,14 +328,13 @@ func (p *PointProj) FromAffine(p1 *PointAffine) *PointProj { // MixedAdd adds a point in projective to a point in affine coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-madd-2008-bbjlp func (p *PointProj) MixedAdd(p1 *PointProj, p2 *PointAffine) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var B, C, D, E, F, G, H, I fr.Element B.Square(&p1.Z) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) @@ -382,15 +379,14 @@ func (p *PointProj) Double(p1 *PointProj) *PointProj { // Add adds points in projective coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-add-2008-bbjlp func (p *PointProj) Add(p1, p2 *PointProj) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var A, B, C, D, E, F, G, H, I fr.Element A.Mul(&p1.Z, &p2.Z) B.Square(&A) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) diff --git a/ecc/bls12-381/twistededwards/point_test.go b/ecc/bls12-381/twistededwards/point_test.go index 25716347f..e41a23421 100644 --- a/ecc/bls12-381/twistededwards/point_test.go +++ b/ecc/bls12-381/twistededwards/point_test.go @@ -817,3 +817,107 @@ func BenchmarkNeg(b *testing.B) { } }) } + +func BenchmarkMixedAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + b.Run("Projective", func(b *testing.B) { + var accum PointProj + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var accum PointExtended + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) +} + +func BenchmarkAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("Affine", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + var accum PointAffine + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Projective", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointProj + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointExtended + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) +} + +func BenchmarkIsOnCurve(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("positive", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + if !point.IsOnCurve() { + b.Fatal("point should must be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) + + b.Run("negative", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + point.X.Add(&point.X, &point.X) + + if point.IsOnCurve() { + b.Fatal("point should not be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) +} diff --git a/ecc/bls24-315/twistededwards/point.go b/ecc/bls24-315/twistededwards/point.go index df1e23557..134acfe0d 100644 --- a/ecc/bls24-315/twistededwards/point.go +++ b/ecc/bls24-315/twistededwards/point.go @@ -161,8 +161,7 @@ func NewPointAffine(x, y fr.Element) PointAffine { // IsOnCurve checks if a point is on the twisted Edwards curve func (p *PointAffine) IsOnCurve() bool { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var lhs, rhs, tmp fr.Element @@ -174,7 +173,7 @@ func (p *PointAffine) IsOnCurve() bool { tmp.Mul(&p.X, &p.X). Mul(&tmp, &p.Y). Mul(&tmp, &p.Y). - Mul(&tmp, &ecurve.D) + Mul(&tmp, &curveParams.D) rhs.SetOne().Add(&rhs, &tmp) return lhs.Equal(&rhs) @@ -190,8 +189,7 @@ func (p *PointAffine) Neg(p1 *PointAffine) *PointAffine { // Add adds two points (x,y), (u,v) on a twisted Edwards curve with parameters a, d // modifies p func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var xu, yv, xv, yu, dxyuv, one, denx, deny fr.Element pRes := new(PointAffine) @@ -204,7 +202,7 @@ func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { yv.Mul(&p1.Y, &p2.Y) pRes.Y.Sub(&yv, &xu) - dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &ecurve.D) + dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &curveParams.D) one.SetOne() denx.Add(&one, &dxyuv) deny.Sub(&one, &dxyuv) @@ -330,14 +328,13 @@ func (p *PointProj) FromAffine(p1 *PointAffine) *PointProj { // MixedAdd adds a point in projective to a point in affine coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-madd-2008-bbjlp func (p *PointProj) MixedAdd(p1 *PointProj, p2 *PointAffine) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var B, C, D, E, F, G, H, I fr.Element B.Square(&p1.Z) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) @@ -382,15 +379,14 @@ func (p *PointProj) Double(p1 *PointProj) *PointProj { // Add adds points in projective coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-add-2008-bbjlp func (p *PointProj) Add(p1, p2 *PointProj) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var A, B, C, D, E, F, G, H, I fr.Element A.Mul(&p1.Z, &p2.Z) B.Square(&A) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) diff --git a/ecc/bls24-315/twistededwards/point_test.go b/ecc/bls24-315/twistededwards/point_test.go index e78428116..c684004f4 100644 --- a/ecc/bls24-315/twistededwards/point_test.go +++ b/ecc/bls24-315/twistededwards/point_test.go @@ -817,3 +817,107 @@ func BenchmarkNeg(b *testing.B) { } }) } + +func BenchmarkMixedAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + b.Run("Projective", func(b *testing.B) { + var accum PointProj + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var accum PointExtended + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) +} + +func BenchmarkAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("Affine", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + var accum PointAffine + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Projective", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointProj + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointExtended + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) +} + +func BenchmarkIsOnCurve(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("positive", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + if !point.IsOnCurve() { + b.Fatal("point should must be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) + + b.Run("negative", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + point.X.Add(&point.X, &point.X) + + if point.IsOnCurve() { + b.Fatal("point should not be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) +} diff --git a/ecc/bls24-317/twistededwards/point.go b/ecc/bls24-317/twistededwards/point.go index fb2ae82fe..5195a1740 100644 --- a/ecc/bls24-317/twistededwards/point.go +++ b/ecc/bls24-317/twistededwards/point.go @@ -161,8 +161,7 @@ func NewPointAffine(x, y fr.Element) PointAffine { // IsOnCurve checks if a point is on the twisted Edwards curve func (p *PointAffine) IsOnCurve() bool { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var lhs, rhs, tmp fr.Element @@ -174,7 +173,7 @@ func (p *PointAffine) IsOnCurve() bool { tmp.Mul(&p.X, &p.X). Mul(&tmp, &p.Y). Mul(&tmp, &p.Y). - Mul(&tmp, &ecurve.D) + Mul(&tmp, &curveParams.D) rhs.SetOne().Add(&rhs, &tmp) return lhs.Equal(&rhs) @@ -190,8 +189,7 @@ func (p *PointAffine) Neg(p1 *PointAffine) *PointAffine { // Add adds two points (x,y), (u,v) on a twisted Edwards curve with parameters a, d // modifies p func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var xu, yv, xv, yu, dxyuv, one, denx, deny fr.Element pRes := new(PointAffine) @@ -204,7 +202,7 @@ func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { yv.Mul(&p1.Y, &p2.Y) pRes.Y.Sub(&yv, &xu) - dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &ecurve.D) + dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &curveParams.D) one.SetOne() denx.Add(&one, &dxyuv) deny.Sub(&one, &dxyuv) @@ -330,14 +328,13 @@ func (p *PointProj) FromAffine(p1 *PointAffine) *PointProj { // MixedAdd adds a point in projective to a point in affine coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-madd-2008-bbjlp func (p *PointProj) MixedAdd(p1 *PointProj, p2 *PointAffine) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var B, C, D, E, F, G, H, I fr.Element B.Square(&p1.Z) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) @@ -382,15 +379,14 @@ func (p *PointProj) Double(p1 *PointProj) *PointProj { // Add adds points in projective coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-add-2008-bbjlp func (p *PointProj) Add(p1, p2 *PointProj) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var A, B, C, D, E, F, G, H, I fr.Element A.Mul(&p1.Z, &p2.Z) B.Square(&A) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) diff --git a/ecc/bls24-317/twistededwards/point_test.go b/ecc/bls24-317/twistededwards/point_test.go index fe55b8e03..beb1fb883 100644 --- a/ecc/bls24-317/twistededwards/point_test.go +++ b/ecc/bls24-317/twistededwards/point_test.go @@ -817,3 +817,107 @@ func BenchmarkNeg(b *testing.B) { } }) } + +func BenchmarkMixedAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + b.Run("Projective", func(b *testing.B) { + var accum PointProj + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var accum PointExtended + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) +} + +func BenchmarkAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("Affine", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + var accum PointAffine + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Projective", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointProj + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointExtended + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) +} + +func BenchmarkIsOnCurve(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("positive", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + if !point.IsOnCurve() { + b.Fatal("point should must be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) + + b.Run("negative", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + point.X.Add(&point.X, &point.X) + + if point.IsOnCurve() { + b.Fatal("point should not be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) +} diff --git a/ecc/bn254/twistededwards/point.go b/ecc/bn254/twistededwards/point.go index c9fcc9364..d883b553f 100644 --- a/ecc/bn254/twistededwards/point.go +++ b/ecc/bn254/twistededwards/point.go @@ -161,8 +161,7 @@ func NewPointAffine(x, y fr.Element) PointAffine { // IsOnCurve checks if a point is on the twisted Edwards curve func (p *PointAffine) IsOnCurve() bool { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var lhs, rhs, tmp fr.Element @@ -174,7 +173,7 @@ func (p *PointAffine) IsOnCurve() bool { tmp.Mul(&p.X, &p.X). Mul(&tmp, &p.Y). Mul(&tmp, &p.Y). - Mul(&tmp, &ecurve.D) + Mul(&tmp, &curveParams.D) rhs.SetOne().Add(&rhs, &tmp) return lhs.Equal(&rhs) @@ -190,8 +189,7 @@ func (p *PointAffine) Neg(p1 *PointAffine) *PointAffine { // Add adds two points (x,y), (u,v) on a twisted Edwards curve with parameters a, d // modifies p func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var xu, yv, xv, yu, dxyuv, one, denx, deny fr.Element pRes := new(PointAffine) @@ -204,7 +202,7 @@ func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { yv.Mul(&p1.Y, &p2.Y) pRes.Y.Sub(&yv, &xu) - dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &ecurve.D) + dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &curveParams.D) one.SetOne() denx.Add(&one, &dxyuv) deny.Sub(&one, &dxyuv) @@ -330,14 +328,13 @@ func (p *PointProj) FromAffine(p1 *PointAffine) *PointProj { // MixedAdd adds a point in projective to a point in affine coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-madd-2008-bbjlp func (p *PointProj) MixedAdd(p1 *PointProj, p2 *PointAffine) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var B, C, D, E, F, G, H, I fr.Element B.Square(&p1.Z) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) @@ -382,15 +379,14 @@ func (p *PointProj) Double(p1 *PointProj) *PointProj { // Add adds points in projective coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-add-2008-bbjlp func (p *PointProj) Add(p1, p2 *PointProj) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var A, B, C, D, E, F, G, H, I fr.Element A.Mul(&p1.Z, &p2.Z) B.Square(&A) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) diff --git a/ecc/bn254/twistededwards/point_test.go b/ecc/bn254/twistededwards/point_test.go index 8ee794316..43df981bd 100644 --- a/ecc/bn254/twistededwards/point_test.go +++ b/ecc/bn254/twistededwards/point_test.go @@ -817,3 +817,107 @@ func BenchmarkNeg(b *testing.B) { } }) } + +func BenchmarkMixedAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + b.Run("Projective", func(b *testing.B) { + var accum PointProj + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var accum PointExtended + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) +} + +func BenchmarkAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("Affine", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + var accum PointAffine + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Projective", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointProj + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointExtended + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) +} + +func BenchmarkIsOnCurve(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("positive", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + if !point.IsOnCurve() { + b.Fatal("point should must be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) + + b.Run("negative", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + point.X.Add(&point.X, &point.X) + + if point.IsOnCurve() { + b.Fatal("point should not be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) +} diff --git a/ecc/bw6-633/twistededwards/point.go b/ecc/bw6-633/twistededwards/point.go index 59d01c0a8..6c4125e75 100644 --- a/ecc/bw6-633/twistededwards/point.go +++ b/ecc/bw6-633/twistededwards/point.go @@ -161,8 +161,7 @@ func NewPointAffine(x, y fr.Element) PointAffine { // IsOnCurve checks if a point is on the twisted Edwards curve func (p *PointAffine) IsOnCurve() bool { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var lhs, rhs, tmp fr.Element @@ -174,7 +173,7 @@ func (p *PointAffine) IsOnCurve() bool { tmp.Mul(&p.X, &p.X). Mul(&tmp, &p.Y). Mul(&tmp, &p.Y). - Mul(&tmp, &ecurve.D) + Mul(&tmp, &curveParams.D) rhs.SetOne().Add(&rhs, &tmp) return lhs.Equal(&rhs) @@ -190,8 +189,7 @@ func (p *PointAffine) Neg(p1 *PointAffine) *PointAffine { // Add adds two points (x,y), (u,v) on a twisted Edwards curve with parameters a, d // modifies p func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var xu, yv, xv, yu, dxyuv, one, denx, deny fr.Element pRes := new(PointAffine) @@ -204,7 +202,7 @@ func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { yv.Mul(&p1.Y, &p2.Y) pRes.Y.Sub(&yv, &xu) - dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &ecurve.D) + dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &curveParams.D) one.SetOne() denx.Add(&one, &dxyuv) deny.Sub(&one, &dxyuv) @@ -330,14 +328,13 @@ func (p *PointProj) FromAffine(p1 *PointAffine) *PointProj { // MixedAdd adds a point in projective to a point in affine coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-madd-2008-bbjlp func (p *PointProj) MixedAdd(p1 *PointProj, p2 *PointAffine) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var B, C, D, E, F, G, H, I fr.Element B.Square(&p1.Z) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) @@ -382,15 +379,14 @@ func (p *PointProj) Double(p1 *PointProj) *PointProj { // Add adds points in projective coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-add-2008-bbjlp func (p *PointProj) Add(p1, p2 *PointProj) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var A, B, C, D, E, F, G, H, I fr.Element A.Mul(&p1.Z, &p2.Z) B.Square(&A) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) diff --git a/ecc/bw6-633/twistededwards/point_test.go b/ecc/bw6-633/twistededwards/point_test.go index 4da1e9b6d..f50541d1e 100644 --- a/ecc/bw6-633/twistededwards/point_test.go +++ b/ecc/bw6-633/twistededwards/point_test.go @@ -817,3 +817,107 @@ func BenchmarkNeg(b *testing.B) { } }) } + +func BenchmarkMixedAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + b.Run("Projective", func(b *testing.B) { + var accum PointProj + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var accum PointExtended + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) +} + +func BenchmarkAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("Affine", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + var accum PointAffine + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Projective", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointProj + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointExtended + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) +} + +func BenchmarkIsOnCurve(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("positive", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + if !point.IsOnCurve() { + b.Fatal("point should must be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) + + b.Run("negative", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + point.X.Add(&point.X, &point.X) + + if point.IsOnCurve() { + b.Fatal("point should not be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) +} diff --git a/ecc/bw6-756/twistededwards/point.go b/ecc/bw6-756/twistededwards/point.go index 8ad7af866..3714d6f4c 100644 --- a/ecc/bw6-756/twistededwards/point.go +++ b/ecc/bw6-756/twistededwards/point.go @@ -161,8 +161,7 @@ func NewPointAffine(x, y fr.Element) PointAffine { // IsOnCurve checks if a point is on the twisted Edwards curve func (p *PointAffine) IsOnCurve() bool { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var lhs, rhs, tmp fr.Element @@ -174,7 +173,7 @@ func (p *PointAffine) IsOnCurve() bool { tmp.Mul(&p.X, &p.X). Mul(&tmp, &p.Y). Mul(&tmp, &p.Y). - Mul(&tmp, &ecurve.D) + Mul(&tmp, &curveParams.D) rhs.SetOne().Add(&rhs, &tmp) return lhs.Equal(&rhs) @@ -190,8 +189,7 @@ func (p *PointAffine) Neg(p1 *PointAffine) *PointAffine { // Add adds two points (x,y), (u,v) on a twisted Edwards curve with parameters a, d // modifies p func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var xu, yv, xv, yu, dxyuv, one, denx, deny fr.Element pRes := new(PointAffine) @@ -204,7 +202,7 @@ func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { yv.Mul(&p1.Y, &p2.Y) pRes.Y.Sub(&yv, &xu) - dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &ecurve.D) + dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &curveParams.D) one.SetOne() denx.Add(&one, &dxyuv) deny.Sub(&one, &dxyuv) @@ -330,14 +328,13 @@ func (p *PointProj) FromAffine(p1 *PointAffine) *PointProj { // MixedAdd adds a point in projective to a point in affine coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-madd-2008-bbjlp func (p *PointProj) MixedAdd(p1 *PointProj, p2 *PointAffine) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var B, C, D, E, F, G, H, I fr.Element B.Square(&p1.Z) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) @@ -382,15 +379,14 @@ func (p *PointProj) Double(p1 *PointProj) *PointProj { // Add adds points in projective coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-add-2008-bbjlp func (p *PointProj) Add(p1, p2 *PointProj) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var A, B, C, D, E, F, G, H, I fr.Element A.Mul(&p1.Z, &p2.Z) B.Square(&A) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) diff --git a/ecc/bw6-756/twistededwards/point_test.go b/ecc/bw6-756/twistededwards/point_test.go index 7d41f749b..13648781f 100644 --- a/ecc/bw6-756/twistededwards/point_test.go +++ b/ecc/bw6-756/twistededwards/point_test.go @@ -817,3 +817,107 @@ func BenchmarkNeg(b *testing.B) { } }) } + +func BenchmarkMixedAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + b.Run("Projective", func(b *testing.B) { + var accum PointProj + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var accum PointExtended + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) +} + +func BenchmarkAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("Affine", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + var accum PointAffine + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Projective", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointProj + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointExtended + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) +} + +func BenchmarkIsOnCurve(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("positive", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + if !point.IsOnCurve() { + b.Fatal("point should must be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) + + b.Run("negative", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + point.X.Add(&point.X, &point.X) + + if point.IsOnCurve() { + b.Fatal("point should not be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) +} diff --git a/ecc/bw6-761/twistededwards/point.go b/ecc/bw6-761/twistededwards/point.go index 10c91f5c0..27910c378 100644 --- a/ecc/bw6-761/twistededwards/point.go +++ b/ecc/bw6-761/twistededwards/point.go @@ -161,8 +161,7 @@ func NewPointAffine(x, y fr.Element) PointAffine { // IsOnCurve checks if a point is on the twisted Edwards curve func (p *PointAffine) IsOnCurve() bool { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var lhs, rhs, tmp fr.Element @@ -174,7 +173,7 @@ func (p *PointAffine) IsOnCurve() bool { tmp.Mul(&p.X, &p.X). Mul(&tmp, &p.Y). Mul(&tmp, &p.Y). - Mul(&tmp, &ecurve.D) + Mul(&tmp, &curveParams.D) rhs.SetOne().Add(&rhs, &tmp) return lhs.Equal(&rhs) @@ -190,8 +189,7 @@ func (p *PointAffine) Neg(p1 *PointAffine) *PointAffine { // Add adds two points (x,y), (u,v) on a twisted Edwards curve with parameters a, d // modifies p func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var xu, yv, xv, yu, dxyuv, one, denx, deny fr.Element pRes := new(PointAffine) @@ -204,7 +202,7 @@ func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { yv.Mul(&p1.Y, &p2.Y) pRes.Y.Sub(&yv, &xu) - dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &ecurve.D) + dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &curveParams.D) one.SetOne() denx.Add(&one, &dxyuv) deny.Sub(&one, &dxyuv) @@ -330,14 +328,13 @@ func (p *PointProj) FromAffine(p1 *PointAffine) *PointProj { // MixedAdd adds a point in projective to a point in affine coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-madd-2008-bbjlp func (p *PointProj) MixedAdd(p1 *PointProj, p2 *PointAffine) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var B, C, D, E, F, G, H, I fr.Element B.Square(&p1.Z) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) @@ -382,15 +379,14 @@ func (p *PointProj) Double(p1 *PointProj) *PointProj { // Add adds points in projective coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-add-2008-bbjlp func (p *PointProj) Add(p1, p2 *PointProj) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var A, B, C, D, E, F, G, H, I fr.Element A.Mul(&p1.Z, &p2.Z) B.Square(&A) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) diff --git a/ecc/bw6-761/twistededwards/point_test.go b/ecc/bw6-761/twistededwards/point_test.go index 4bbbbd257..80be8ff2d 100644 --- a/ecc/bw6-761/twistededwards/point_test.go +++ b/ecc/bw6-761/twistededwards/point_test.go @@ -817,3 +817,107 @@ func BenchmarkNeg(b *testing.B) { } }) } + +func BenchmarkMixedAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + b.Run("Projective", func(b *testing.B) { + var accum PointProj + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var accum PointExtended + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum, &point) + } + }) +} + +func BenchmarkAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("Affine", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + var accum PointAffine + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Projective", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointProj + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointExtended + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) +} + +func BenchmarkIsOnCurve(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("positive", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + if !point.IsOnCurve() { + b.Fatal("point should must be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) + + b.Run("negative", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + point.X.Add(&point.X, &point.X) + + if point.IsOnCurve() { + b.Fatal("point should not be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) +} diff --git a/internal/generator/edwards/template/point.go.tmpl b/internal/generator/edwards/template/point.go.tmpl index 3eb72370b..6a32519ec 100644 --- a/internal/generator/edwards/template/point.go.tmpl +++ b/internal/generator/edwards/template/point.go.tmpl @@ -145,8 +145,7 @@ func NewPointAffine(x, y fr.Element) PointAffine { // IsOnCurve checks if a point is on the twisted Edwards curve func (p *PointAffine) IsOnCurve() bool { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var lhs, rhs, tmp fr.Element @@ -158,7 +157,7 @@ func (p *PointAffine) IsOnCurve() bool { tmp.Mul(&p.X, &p.X). Mul(&tmp, &p.Y). Mul(&tmp, &p.Y). - Mul(&tmp, &ecurve.D) + Mul(&tmp, &curveParams.D) rhs.SetOne().Add(&rhs, &tmp) return lhs.Equal(&rhs) @@ -174,8 +173,7 @@ func (p *PointAffine) Neg(p1 *PointAffine) *PointAffine { // Add adds two points (x,y), (u,v) on a twisted Edwards curve with parameters a, d // modifies p func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var xu, yv, xv, yu, dxyuv, one, denx, deny fr.Element pRes := new(PointAffine) @@ -188,7 +186,7 @@ func (p *PointAffine) Add(p1, p2 *PointAffine) *PointAffine { yv.Mul(&p1.Y, &p2.Y) pRes.Y.Sub(&yv, &xu) - dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &ecurve.D) + dxyuv.Mul(&xv, &yu).Mul(&dxyuv, &curveParams.D) one.SetOne() denx.Add(&one, &dxyuv) deny.Sub(&one, &dxyuv) @@ -314,14 +312,13 @@ func (p *PointProj) FromAffine(p1 *PointAffine) *PointProj { // MixedAdd adds a point in projective to a point in affine coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-madd-2008-bbjlp func (p *PointProj) MixedAdd(p1 *PointProj, p2 *PointAffine) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var B, C, D, E, F, G, H, I fr.Element B.Square(&p1.Z) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) @@ -366,15 +363,14 @@ func (p *PointProj) Double(p1 *PointProj) *PointProj { // Add adds points in projective coordinates // cf https://hyperelliptic.org/EFD/g1p/auto-twisted-projective.html#addition-add-2008-bbjlp func (p *PointProj) Add(p1, p2 *PointProj) *PointProj { - - ecurve := GetEdwardsCurve() + initOnce.Do(initCurveParams) var A, B, C, D, E, F, G, H, I fr.Element A.Mul(&p1.Z, &p2.Z) B.Square(&A) C.Mul(&p1.X, &p2.X) D.Mul(&p1.Y, &p2.Y) - E.Mul(&ecurve.D, &C).Mul(&E, &D) + E.Mul(&curveParams.D, &C).Mul(&E, &D) F.Sub(&B, &E) G.Add(&B, &E) H.Add(&p1.X, &p1.Y) diff --git a/internal/generator/edwards/template/tests/point.go.tmpl b/internal/generator/edwards/template/tests/point.go.tmpl index ae31881b5..960ff0ca5 100644 --- a/internal/generator/edwards/template/tests/point.go.tmpl +++ b/internal/generator/edwards/template/tests/point.go.tmpl @@ -800,4 +800,108 @@ func BenchmarkNeg(b *testing.B) { point.Neg(&point) } }) +} + +func BenchmarkMixedAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + b.Run("Projective", func(b *testing.B) { + var accum PointProj + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum , &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var accum PointExtended + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.MixedAdd(&accum , &point) + } + }) +} + +func BenchmarkAdd(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("Affine", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + var accum PointAffine + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Projective", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointProj + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) + b.Run("Extended", func(b *testing.B) { + var pointAff PointAffine + pointAff.ScalarMultiplication(¶ms.Base, &s) + var accum, point PointExtended + point.FromAffine(&pointAff) + accum.setInfinity() + + b.ResetTimer() + for i := 0; i < b.N; i++ { + accum.Add(&accum, &point) + } + }) +} + +func BenchmarkIsOnCurve(b *testing.B) { + params := GetEdwardsCurve() + var s big.Int + s.SetString("52435875175126190479447705081859658376581184513", 10) + + b.Run("positive", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + + if !point.IsOnCurve() { + b.Fatal("point should must be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) + + b.Run("negative", func(b *testing.B) { + var point PointAffine + point.ScalarMultiplication(¶ms.Base, &s) + point.X.Add(&point.X, &point.X) + + if point.IsOnCurve() { + b.Fatal("point should not be on curve") + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _ = point.IsOnCurve() + } + }) } \ No newline at end of file