Skip to content

Commit

Permalink
refactor(crypto): replace bls12-381 kilic with gnark (#1510)
Browse files Browse the repository at this point in the history
  • Loading branch information
b00f authored Sep 28, 2024
1 parent 9de9f41 commit 1a609e1
Show file tree
Hide file tree
Showing 14 changed files with 128 additions and 135 deletions.
43 changes: 21 additions & 22 deletions crypto/bls/bls.go
Original file line number Diff line number Diff line change
@@ -1,62 +1,61 @@
package bls

import (
bls12381 "github.com/kilic/bls12-381"
bls12381 "github.com/consensys/gnark-crypto/ecc/bls12-381"
)

// set Ciphersuite for Basic mode
// https://datatracker.ietf.org/doc/html/draft-irtf-cfrg-bls-signature-04#section-4.2.1
var dst = []byte("BLS_SIG_BLS12381G1_XMD:SHA-256_SSWU_RO_NUL_")
var (
dst = []byte("BLS_SIG_BLS12381G1_XMD:SHA-256_SSWU_RO_NUL_")
gen2Aff bls12381.G2Affine
gen2Jac bls12381.G2Jac
)

func init() {
_, gen2Jac, _, gen2Aff = bls12381.Generators()
}

func SignatureAggregate(sigs ...*Signature) *Signature {
if len(sigs) == 0 {
return nil
}
g1 := bls12381.NewG1()
g1 := new(bls12381.G1Affine)
aggPointG1, err := sigs[0].PointG1()
if err != nil {
return nil
}
for i := 1; i < len(sigs); i++ {
s, err := sigs[i].PointG1()
if err != nil {
return nil
}
g1.Add(
&aggPointG1,
&aggPointG1,
&s)
pointG1, _ := sigs[i].PointG1()
aggPointG1 = g1.Add(aggPointG1, pointG1)
}

data := g1.ToCompressed(&aggPointG1)
data := aggPointG1.Bytes()

return &Signature{
data: data,
pointG1: &aggPointG1,
data: data[:],
pointG1: aggPointG1,
}
}

func PublicKeyAggregate(pubs ...*PublicKey) *PublicKey {
if len(pubs) == 0 {
return nil
}
g2 := bls12381.NewG2()
g2 := new(bls12381.G2Affine)
aggPointG2, err := pubs[0].PointG2()
if err != nil {
return nil
}
for i := 1; i < len(pubs); i++ {
pointG2, _ := pubs[i].PointG2()
g2.Add(
&aggPointG2,
&aggPointG2,
&pointG2)
aggPointG2 = g2.Add(aggPointG2, pointG2)
}

data := g2.ToCompressed(&aggPointG2)
data := aggPointG2.Bytes()

return &PublicKey{
data: data,
pointG2: &aggPointG2,
data: data[:],
pointG2: aggPointG2,
}
}
37 changes: 9 additions & 28 deletions crypto/bls/bls_bench_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,10 +11,8 @@ func BenchmarkEncode(b *testing.B) {
b.ReportAllocs()

buf := make([]byte, bls.PrivateKeySize)
_, err := rand.Read(buf)
if err != nil {
b.Fatal(err)
}
_, _ = rand.Read(buf)

prv, _ := bls.PrivateKeyFromBytes(buf)
pub := prv.PublicKeyNative()

Expand All @@ -29,10 +27,8 @@ func BenchmarkDecodeSign(b *testing.B) {
b.ReportAllocs()

buf := make([]byte, bls.PrivateKeySize)
_, err := rand.Read(buf)
if err != nil {
b.Fatal(err)
}
_, _ = rand.Read(buf)

prv, _ := bls.PrivateKeyFromBytes(buf)
bufMsg := []byte("pactus")
sig := prv.Sign(bufMsg)
Expand All @@ -41,21 +37,15 @@ func BenchmarkDecodeSign(b *testing.B) {
b.ResetTimer()

for i := 0; i < b.N; i++ {
_, err := bls.SignatureFromBytes(sigBytes)
if err != nil {
b.Fatal(err)
}
_, _ = bls.SignatureFromBytes(sigBytes)
}
}

func BenchmarkVerify(b *testing.B) {
b.ReportAllocs()

buf := make([]byte, bls.PrivateKeySize)
_, err := rand.Read(buf)
if err != nil {
b.Fatal(err)
}
_, _ = rand.Read(buf)
prv, _ := bls.PrivateKeyFromBytes(buf)
pub := prv.PublicKeyNative()

Expand All @@ -65,30 +55,21 @@ func BenchmarkVerify(b *testing.B) {
b.ResetTimer()

for i := 0; i < b.N; i++ {
err = pub.Verify(bufMsg, sig1)
if err != nil {
b.Fatal(err)
}
_ = pub.Verify(bufMsg, sig1)
}
}

func BenchmarkDecode(b *testing.B) {
b.ReportAllocs()

buf := make([]byte, bls.PrivateKeySize)
_, err := rand.Read(buf)
if err != nil {
b.Fatal(err)
}
_, _ = rand.Read(buf)
prv, _ := bls.PrivateKeyFromBytes(buf)
pub := prv.PublicKeyNative()
pubBytes := pub.Bytes()
b.ResetTimer()

for i := 0; i < b.N; i++ {
_, err := bls.PublicKeyFromBytes(pubBytes)
if err != nil {
b.Fatal(err)
}
_, _ = bls.PublicKeyFromBytes(pubBytes)
}
}
12 changes: 8 additions & 4 deletions crypto/bls/bls_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,11 +4,12 @@ import (
"encoding/hex"
"testing"

bls12381 "github.com/kilic/bls12-381"
bls12381 "github.com/consensys/gnark-crypto/ecc/bls12-381"
"github.com/pactus-project/pactus/crypto"
"github.com/pactus-project/pactus/crypto/bls"
"github.com/pactus-project/pactus/util/testsuite"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
)

func TestSigning(t *testing.T) {
Expand Down Expand Up @@ -185,11 +186,14 @@ func TestHashToCurve(t *testing.T) {
},
}

g1 := bls12381.NewG1()
for no, test := range tests {
mappedPoint, _ := g1.HashToCurve([]byte(test.msg), domain)
mappedPoint, _ := bls12381.HashToG1([]byte(test.msg), domain)
d, _ := hex.DecodeString(test.expected)
expectedPoint, _ := g1.FromBytes(d)

expectedPoint := bls12381.G1Affine{}
err := expectedPoint.Unmarshal(d)
require.NoError(t, err)

assert.Equal(t, expectedPoint, mappedPoint,
"test %v: not match", no)
}
Expand Down
50 changes: 24 additions & 26 deletions crypto/bls/private_key.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,8 @@ import (
"math/big"
"strings"

bls12381 "github.com/kilic/bls12-381"
bls12381 "github.com/consensys/gnark-crypto/ecc/bls12-381"
"github.com/consensys/gnark-crypto/ecc/bls12-381/fr"
"github.com/pactus-project/pactus/crypto"
"github.com/pactus-project/pactus/util"
"github.com/pactus-project/pactus/util/bech32m"
Expand All @@ -18,7 +19,7 @@ var _ crypto.PrivateKey = &PrivateKey{}
const PrivateKeySize = 32

type PrivateKey struct {
fr bls12381.Fr
scalar *big.Int
}

// PrivateKeyFromString decodes the input string and returns the PrivateKey
Expand Down Expand Up @@ -65,8 +66,6 @@ func KeyGen(ikm, keyInfo []byte) (*PrivateKey, error) {
pseudoRandomKey = append(pseudoRandomKey, keyInfo...)
pseudoRandomKey = append(pseudoRandomKey, util.I2OSP(big.NewInt(l), 2)...)

g1 := bls12381.NewG1()

salt := []byte("BLS-SIG-KEYGEN-SALT-")
x := big.NewInt(0)
for x.Sign() == 0 {
Expand All @@ -78,7 +77,7 @@ func KeyGen(ikm, keyInfo []byte) (*PrivateKey, error) {
reader := hkdf.Expand(sha256.New, prk, pseudoRandomKey)
_, _ = reader.Read(okm)

r := g1.Q()
r := fr.Modulus()
x = new(big.Int).Mod(util.OS2IP(okm), r)
}

Expand All @@ -94,13 +93,10 @@ func PrivateKeyFromBytes(data []byte) (*PrivateKey, error) {
return nil, crypto.InvalidLengthError(len(data))
}

fr := bls12381.NewFr()
fr.FromBytes(data)
if fr.IsZero() {
return nil, crypto.ErrInvalidPrivateKey
}
scalar := new(big.Int)
scalar = scalar.SetBytes(data)

return &PrivateKey{fr: *fr}, nil
return &PrivateKey{scalar: scalar}, nil
}

// String returns a human-readable string for the BLS private key.
Expand All @@ -115,7 +111,10 @@ func (prv *PrivateKey) String() string {

// Bytes return the raw bytes of the private key.
func (prv *PrivateKey) Bytes() []byte {
return prv.fr.ToBytes()
data := prv.scalar.Bytes()
data = util.Extend(data, PrivateKeySize)

return data
}

// Sign calculates the signature from the private key and given message.
Expand All @@ -125,30 +124,29 @@ func (prv *PrivateKey) Sign(msg []byte) crypto.Signature {
}

func (prv *PrivateKey) SignNative(msg []byte) *Signature {
g1 := bls12381.NewG1()

q, err := g1.HashToCurve(msg, dst)
qAffine, err := bls12381.HashToG1(msg, dst)
if err != nil {
panic(err)
}
pointG1 := g1.MulScalar(g1.New(), q, &prv.fr)
data := g1.ToCompressed(pointG1)
qJac := new(bls12381.G1Jac).FromAffine(&qAffine)
sigJac := qJac.ScalarMultiplication(qJac, prv.scalar)
sigAffine := new(bls12381.G1Affine).FromJacobian(sigJac)
data := sigAffine.Bytes()

return &Signature{
data: data,
pointG1: pointG1,
data: data[:],
pointG1: sigAffine,
}
}

func (prv *PrivateKey) PublicKeyNative() *PublicKey {
g2 := bls12381.NewG2()

pointG2 := g2.MulScalar(g2.New(), g2.One(), &prv.fr)
data := g2.ToCompressed(pointG2)
pkJac := new(bls12381.G2Jac).ScalarMultiplication(&gen2Jac, prv.scalar)
pkAffine := new(bls12381.G2Affine).FromJacobian(pkJac)
data := pkAffine.Bytes()

return &PublicKey{
data: data,
pointG2: pointG2,
data: data[:],
pointG2: pkAffine,
}
}

Expand All @@ -162,5 +160,5 @@ func (prv *PrivateKey) EqualsTo(x crypto.PrivateKey) bool {
return false
}

return prv.fr.Equal(&xBLS.fr)
return prv.scalar.Cmp(xBLS.scalar) == 0
}
5 changes: 0 additions & 5 deletions crypto/bls/private_key_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -49,11 +49,6 @@ func TestPrivateKeyFromString(t *testing.T) {
"SECRET1HPZZU9",
false, nil,
},
{
"invalid private key",
"SECRET1PQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQQSK004X",
false, nil,
},
{
"invalid HRP: xxx",
"XXX1PDRWTLP5PX0FAHDX39GXZJP7FKZFALML0D5U9TT9KVQHDUC99CMGQMUUMJT",
Expand Down
Loading

0 comments on commit 1a609e1

Please sign in to comment.