From 512b23ba638b1bda304051b3ca61d0f9b4c89a37 Mon Sep 17 00:00:00 2001 From: Nadav Kohen Date: Tue, 21 Jan 2020 14:30:28 -0700 Subject: [PATCH] Added PubKey addition functionality (#1051) --- .../org/bitcoins/core/crypto/ECPublicKeyTest.scala | 14 ++++++++++++++ .../scala/org/bitcoins/core/crypto/ECKey.scala | 11 +++++++++++ 2 files changed, 25 insertions(+) diff --git a/core-test/src/test/scala/org/bitcoins/core/crypto/ECPublicKeyTest.scala b/core-test/src/test/scala/org/bitcoins/core/crypto/ECPublicKeyTest.scala index 4187fc4809..57f94acb25 100644 --- a/core-test/src/test/scala/org/bitcoins/core/crypto/ECPublicKeyTest.scala +++ b/core-test/src/test/scala/org/bitcoins/core/crypto/ECPublicKeyTest.scala @@ -1,5 +1,6 @@ package org.bitcoins.core.crypto +import org.bitcoin.NativeSecp256k1 import org.bitcoins.testkit.core.gen.CryptoGenerators import org.bitcoins.testkit.util.BitcoinSUnitTest import scodec.bits._ @@ -35,4 +36,17 @@ class ECPublicKeyTest extends BitcoinSUnitTest { assert(pubKey == pub2) } } + + it must "add keys correctly" in { + forAll(CryptoGenerators.publicKey, CryptoGenerators.privateKey) { + case (pubKey, privKey) => + val sumKeyBytes = NativeSecp256k1.pubKeyTweakAdd(pubKey.bytes.toArray, + privKey.bytes.toArray, + true) + val sumKeyExpected = ECPublicKey.fromBytes(ByteVector(sumKeyBytes)) + val sumKey = pubKey.add(privKey.publicKey) + + assert(sumKey == sumKeyExpected) + } + } } diff --git a/core/src/main/scala/org/bitcoins/core/crypto/ECKey.scala b/core/src/main/scala/org/bitcoins/core/crypto/ECKey.scala index 1516e762ab..0812a3b17c 100644 --- a/core/src/main/scala/org/bitcoins/core/crypto/ECKey.scala +++ b/core/src/main/scala/org/bitcoins/core/crypto/ECKey.scala @@ -347,6 +347,17 @@ sealed abstract class ECPublicKey extends BaseECKey { def toPoint: ECPoint = { CryptoParams.curve.getCurve.decodePoint(bytes.toArray) } + + /** Adds this ECPublicKey to another as points and returns the resulting ECPublicKey. + * + * Note: if this ever becomes a bottleneck, secp256k1_ec_pubkey_combine should + * get wrapped in NativeSecp256k1 to speed things up. + */ + def add(otherKey: ECPublicKey): ECPublicKey = { + val sumPoint = toPoint.add(otherKey.toPoint) + + ECPublicKey.fromPoint(sumPoint) + } } object ECPublicKey extends Factory[ECPublicKey] {