mirror of
https://github.com/ACINQ/eclair.git
synced 2024-11-19 18:10:42 +01:00
Add tx signing metrics (#1659)
Monitor the rate at which we sign channel txs and the duration of the signing operations.
This commit is contained in:
parent
5d3958dd03
commit
15c1837d84
@ -22,10 +22,21 @@ object Monitoring {
|
||||
|
||||
object Metrics {
|
||||
val OnionPayloadFormat = Kamon.counter("crypto.sphinx.onion-payload-format")
|
||||
val SignTxCount = Kamon.counter("crypto.keymanager.sign.count")
|
||||
val SignTxDuration = Kamon.timer("crypto.keymanager.sign.duration")
|
||||
}
|
||||
|
||||
object Tags {
|
||||
val LegacyOnion = "legacy"
|
||||
val TxOwner = "txOwner"
|
||||
val TxType = "txType"
|
||||
|
||||
object TxTypes {
|
||||
val CommitTx = "commit"
|
||||
val HtlcTx = "htlc"
|
||||
val RevokedTx = "revoked"
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -16,9 +16,6 @@
|
||||
|
||||
package fr.acinq.eclair.crypto.keymanager
|
||||
|
||||
import java.io.ByteArrayInputStream
|
||||
import java.nio.ByteOrder
|
||||
|
||||
import fr.acinq.bitcoin.Crypto.{PrivateKey, PublicKey}
|
||||
import fr.acinq.bitcoin.DeterministicWallet.ExtendedPublicKey
|
||||
import fr.acinq.bitcoin.{ByteVector64, Crypto, DeterministicWallet, Protocol}
|
||||
@ -26,6 +23,9 @@ import fr.acinq.eclair.channel.{ChannelVersion, LocalParams}
|
||||
import fr.acinq.eclair.transactions.Transactions.{CommitmentFormat, TransactionWithInputInfo, TxOwner}
|
||||
import scodec.bits.ByteVector
|
||||
|
||||
import java.io.ByteArrayInputStream
|
||||
import java.nio.ByteOrder
|
||||
|
||||
trait ChannelKeyManager {
|
||||
def fundingPublicKey(keyPath: DeterministicWallet.KeyPath): ExtendedPublicKey
|
||||
|
||||
@ -62,8 +62,7 @@ trait ChannelKeyManager {
|
||||
* @param publicKey extended public key
|
||||
* @param txOwner owner of the transaction (local/remote)
|
||||
* @param commitmentFormat format of the commitment tx
|
||||
* @return a signature generated with the private key that matches the input
|
||||
* extended public key
|
||||
* @return a signature generated with the private key that matches the input extended public key
|
||||
*/
|
||||
def sign(tx: TransactionWithInputInfo, publicKey: ExtendedPublicKey, txOwner: TxOwner, commitmentFormat: CommitmentFormat): ByteVector64
|
||||
|
||||
@ -75,8 +74,7 @@ trait ChannelKeyManager {
|
||||
* @param remotePoint remote point
|
||||
* @param txOwner owner of the transaction (local/remote)
|
||||
* @param commitmentFormat format of the commitment tx
|
||||
* @return a signature generated with a private key generated from the input keys's matching
|
||||
* private key and the remote point.
|
||||
* @return a signature generated with a private key generated from the input key's matching private key and the remote point.
|
||||
*/
|
||||
def sign(tx: TransactionWithInputInfo, publicKey: ExtendedPublicKey, remotePoint: PublicKey, txOwner: TxOwner, commitmentFormat: CommitmentFormat): ByteVector64
|
||||
|
||||
@ -88,8 +86,7 @@ trait ChannelKeyManager {
|
||||
* @param remoteSecret remote secret
|
||||
* @param txOwner owner of the transaction (local/remote)
|
||||
* @param commitmentFormat format of the commitment tx
|
||||
* @return a signature generated with a private key generated from the input keys's matching
|
||||
* private key and the remote secret.
|
||||
* @return a signature generated with a private key generated from the input key's matching private key and the remote secret.
|
||||
*/
|
||||
def sign(tx: TransactionWithInputInfo, publicKey: ExtendedPublicKey, remoteSecret: PrivateKey, txOwner: TxOwner, commitmentFormat: CommitmentFormat): ByteVector64
|
||||
|
||||
@ -105,7 +102,7 @@ trait ChannelKeyManager {
|
||||
object ChannelKeyManager {
|
||||
/**
|
||||
* Create a BIP32 path from a public key. This path will be used to derive channel keys.
|
||||
* Having channel keys derived from the funding public keys makes it very easy to retrieve your funds when've you've lost your data:
|
||||
* Having channel keys derived from the funding public keys makes it very easy to retrieve your funds when you've lost your data:
|
||||
* - connect to your peer and use DLP to get them to publish their remote commit tx
|
||||
* - retrieve the commit tx from the bitcoin network, extract your funding pubkey from its witness data
|
||||
* - recompute your channel keys and spend your output
|
||||
|
@ -21,11 +21,13 @@ import fr.acinq.bitcoin.Crypto.{PrivateKey, PublicKey}
|
||||
import fr.acinq.bitcoin.DeterministicWallet.{derivePrivateKey, _}
|
||||
import fr.acinq.bitcoin.{Block, ByteVector32, ByteVector64, Crypto, DeterministicWallet}
|
||||
import fr.acinq.eclair.crypto.Generators
|
||||
import fr.acinq.eclair.crypto.Monitoring.{Metrics, Tags}
|
||||
import fr.acinq.eclair.router.Announcements
|
||||
import fr.acinq.eclair.secureRandom
|
||||
import fr.acinq.eclair.transactions.Transactions
|
||||
import fr.acinq.eclair.transactions.Transactions.{CommitmentFormat, TransactionWithInputInfo, TxOwner}
|
||||
import fr.acinq.eclair.{KamonExt, secureRandom}
|
||||
import grizzled.slf4j.Logging
|
||||
import kamon.tag.TagSet
|
||||
import scodec.bits.ByteVector
|
||||
|
||||
object LocalChannelKeyManager {
|
||||
@ -97,13 +99,17 @@ class LocalChannelKeyManager(seed: ByteVector, chainHash: ByteVector32) extends
|
||||
* @param publicKey extended public key
|
||||
* @param txOwner owner of the transaction (local/remote)
|
||||
* @param commitmentFormat format of the commitment tx
|
||||
* @return a signature generated with the private key that matches the input
|
||||
* extended public key
|
||||
* @return a signature generated with the private key that matches the input extended public key
|
||||
*/
|
||||
override def sign(tx: TransactionWithInputInfo, publicKey: ExtendedPublicKey, txOwner: TxOwner, commitmentFormat: CommitmentFormat): ByteVector64 = {
|
||||
// NB: not all those transactions are actually commit txs (especially during closing), but this is good enough for monitoring purposes
|
||||
val tags = TagSet.Empty.withTag(Tags.TxOwner, txOwner.toString).withTag(Tags.TxType, Tags.TxTypes.CommitTx)
|
||||
Metrics.SignTxCount.withTags(tags).increment()
|
||||
KamonExt.time(Metrics.SignTxDuration.withTags(tags)) {
|
||||
val privateKey = privateKeys.get(publicKey.path)
|
||||
Transactions.sign(tx, privateKey.privateKey, txOwner, commitmentFormat)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* This method is used to spend funds sent to htlc keys/delayed keys
|
||||
@ -113,14 +119,18 @@ class LocalChannelKeyManager(seed: ByteVector, chainHash: ByteVector32) extends
|
||||
* @param remotePoint remote point
|
||||
* @param txOwner owner of the transaction (local/remote)
|
||||
* @param commitmentFormat format of the commitment tx
|
||||
* @return a signature generated with a private key generated from the input keys's matching
|
||||
* private key and the remote point.
|
||||
* @return a signature generated with a private key generated from the input key's matching private key and the remote point.
|
||||
*/
|
||||
override def sign(tx: TransactionWithInputInfo, publicKey: ExtendedPublicKey, remotePoint: PublicKey, txOwner: TxOwner, commitmentFormat: CommitmentFormat): ByteVector64 = {
|
||||
// NB: not all those transactions are actually htlc txs (especially during closing), but this is good enough for monitoring purposes
|
||||
val tags = TagSet.Empty.withTag(Tags.TxOwner, txOwner.toString).withTag(Tags.TxType, Tags.TxTypes.HtlcTx)
|
||||
Metrics.SignTxCount.withTags(tags).increment()
|
||||
KamonExt.time(Metrics.SignTxDuration.withTags(tags)) {
|
||||
val privateKey = privateKeys.get(publicKey.path)
|
||||
val currentKey = Generators.derivePrivKey(privateKey.privateKey, remotePoint)
|
||||
Transactions.sign(tx, currentKey, txOwner, commitmentFormat)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Ths method is used to spend revoked transactions, with the corresponding revocation key
|
||||
@ -130,14 +140,17 @@ class LocalChannelKeyManager(seed: ByteVector, chainHash: ByteVector32) extends
|
||||
* @param remoteSecret remote secret
|
||||
* @param txOwner owner of the transaction (local/remote)
|
||||
* @param commitmentFormat format of the commitment tx
|
||||
* @return a signature generated with a private key generated from the input keys's matching
|
||||
* private key and the remote secret.
|
||||
* @return a signature generated with a private key generated from the input key's matching private key and the remote secret.
|
||||
*/
|
||||
override def sign(tx: TransactionWithInputInfo, publicKey: ExtendedPublicKey, remoteSecret: PrivateKey, txOwner: TxOwner, commitmentFormat: CommitmentFormat): ByteVector64 = {
|
||||
val tags = TagSet.Empty.withTag(Tags.TxOwner, txOwner.toString).withTag(Tags.TxType, Tags.TxTypes.RevokedTx)
|
||||
Metrics.SignTxCount.withTags(tags).increment()
|
||||
KamonExt.time(Metrics.SignTxDuration.withTags(tags)) {
|
||||
val privateKey = privateKeys.get(publicKey.path)
|
||||
val currentKey = Generators.revocationPrivKey(privateKey.privateKey, remoteSecret)
|
||||
Transactions.sign(tx, currentKey, txOwner, commitmentFormat)
|
||||
}
|
||||
}
|
||||
|
||||
override def signChannelAnnouncement(witness: ByteVector, fundingKeyPath: KeyPath): ByteVector64 =
|
||||
Announcements.signChannelAnnouncement(witness, privateKeys.get(fundingKeyPath).privateKey)
|
||||
|
Loading…
Reference in New Issue
Block a user