fix incorrect padding in NewPublicKeyFromBigInt (#143)

This commit is contained in:
Dmitry Holodov
2022-08-01 19:19:36 -05:00
committed by GitHub
parent dbdab9519b
commit e9f437b7bb
11 changed files with 73 additions and 22 deletions

View File

@@ -1,8 +1,14 @@
package dleq
import (
"bytes"
"crypto/ecdsa"
"math/big"
"testing"
ethsecp256k1 "github.com/ethereum/go-ethereum/crypto/secp256k1"
"github.com/noot/atomic-swap/common"
mcrypto "github.com/noot/atomic-swap/crypto/monero"
ethcrypto "github.com/ethereum/go-ethereum/crypto"
@@ -25,3 +31,41 @@ func TestCGODLEq(t *testing.T) {
ed25519Pub := sk.Public().Bytes()
require.Equal(t, res.ed25519Pub[:], ed25519Pub)
}
func TestProofSecretComputesVerifyPubKeys(t *testing.T) {
// It would be nice to increase the number of iterations, but it's pretty slow even at 128. We
// previously had an issue when X or Y needed at least one high order padding byte. The chance
// of that happening is around (1/256+1/256)=1/128, so this loop will see values like that
// frequently, even if it doesn't happen on every run.
const iterations = 128
toBigInt := func(point [32]byte) *big.Int { return new(big.Int).SetBytes(point[:]) }
for i := 0; i < iterations; i++ {
proof, err := (&CGODLEq{}).Prove()
require.NoError(t, err)
res, err := (&CGODLEq{}).Verify(proof)
require.NoError(t, err)
// The ETH library needs the secret in big-endian format, while the monero library wants it
// in little endian format.
secretLE := proof.secret[:]
secretBE := common.Reverse(secretLE)
// Secp256k1 check
ethCurve := ethsecp256k1.S256()
xPub, yPub := ethCurve.ScalarBaseMult(secretBE)
ethPubFromSecret := &ecdsa.PublicKey{Curve: ethCurve, X: xPub, Y: yPub}
ethPubFromVerify := &ecdsa.PublicKey{Curve: ethCurve,
X: toBigInt(res.Secp256k1PublicKey().X()), Y: toBigInt(res.Secp256k1PublicKey().Y()),
}
require.True(t, ethPubFromSecret.Equal(ethPubFromVerify))
// ED25519 Check
sk, err := mcrypto.NewPrivateSpendKey(secretLE)
require.NoError(t, err)
xmrPubFromSecret := sk.Public().Bytes()
xmrPubFromVerify := res.ed25519Pub[:]
require.True(t, bytes.Equal(xmrPubFromSecret, xmrPubFromVerify))
}
}