1
0
mirror of https://github.com/ACINQ/eclair.git synced 2024-11-19 01:43:22 +01:00

Cleanup ChannelKeyManager (#2639)

There was a confusion between `fundingKeyPath` and `channelKeyPath`.

Also simplified the funding key derivation. It's not backward compatible but current version of the code doesn't run on mainnet so it's fine.

---------

Co-authored-by: Bastien Teinturier <31281497+t-bast@users.noreply.github.com>
This commit is contained in:
Pierre-Marie Padiou 2023-05-04 11:37:58 +02:00 committed by GitHub
parent a010750de8
commit 15e4986f3f
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
9 changed files with 28 additions and 42 deletions

View File

@ -27,7 +27,7 @@ import java.io.ByteArrayInputStream
import java.nio.ByteOrder
trait ChannelKeyManager {
def fundingPublicKey(keyPath: DeterministicWallet.KeyPath, fundingTxIndex: Long): ExtendedPublicKey
def fundingPublicKey(fundingKeyPath: DeterministicWallet.KeyPath, fundingTxIndex: Long): ExtendedPublicKey
def revocationPoint(channelKeyPath: DeterministicWallet.KeyPath): ExtendedPublicKey

View File

@ -38,8 +38,21 @@ object LocalChannelKeyManager {
}
/**
* This class manages channel secrets and private keys.
* It exports points and public keys, and provides signing methods
* An implementation of [[ChannelKeyManager]] that supports deterministic derivation of keys, based on the initial
* funding pubkey.
*
* Specifically, there are two paths both of length 8 (256 bits):
* - `fundingKeyPath`: chosen at random using `newFundingKeyPath()`
* - `channelKeyPath`: sha(fundingPubkey(0)) using `ChannelKeyManager.keyPath()`
*
* The resulting paths looks like so on mainnet:
* {{{
* funding txs:
* 47' / 1' / <fundingKeyPath> / <1' or 0'> / <index>'
*
* others channel basepoint keys (payment, revocation, htlc, etc.):
* 47' / 1' / <channelKeyPath> / <1'-5'>
* }}}
*
* @param seed seed from which the channel keys will be derived
*/
@ -58,19 +71,7 @@ class LocalChannelKeyManager(seed: ByteVector, chainHash: ByteVector32) extends
override def load(keyPath: KeyPath): ExtendedPublicKey = publicKey(privateKeys.get(keyPath))
})
private def internalKeyPath(channelKeyPath: DeterministicWallet.KeyPath, index: Long): KeyPath = KeyPath((LocalChannelKeyManager.keyBasePath(chainHash) ++ channelKeyPath.path) :+ index)
private def fundingPrivateKey(channelKeyPath: DeterministicWallet.KeyPath): ExtendedPrivateKey = privateKeys.get(internalKeyPath(channelKeyPath, hardened(0)))
private def revocationSecret(channelKeyPath: DeterministicWallet.KeyPath): ExtendedPrivateKey = privateKeys.get(internalKeyPath(channelKeyPath, hardened(1)))
private def paymentSecret(channelKeyPath: DeterministicWallet.KeyPath): ExtendedPrivateKey = privateKeys.get(internalKeyPath(channelKeyPath, hardened(2)))
private def delayedPaymentSecret(channelKeyPath: DeterministicWallet.KeyPath): ExtendedPrivateKey = privateKeys.get(internalKeyPath(channelKeyPath, hardened(3)))
private def htlcSecret(channelKeyPath: DeterministicWallet.KeyPath): ExtendedPrivateKey = privateKeys.get(internalKeyPath(channelKeyPath, hardened(4)))
private def shaSeed(channelKeyPath: DeterministicWallet.KeyPath): ByteVector32 = Crypto.sha256(privateKeys.get(internalKeyPath(channelKeyPath, hardened(5))).privateKey.value :+ 1.toByte)
private def internalKeyPath(keyPath: DeterministicWallet.KeyPath, index: Long): KeyPath = KeyPath((LocalChannelKeyManager.keyBasePath(chainHash) ++ keyPath.path) :+ index)
override def newFundingKeyPath(isInitiator: Boolean): KeyPath = {
val last = DeterministicWallet.hardened(if (isInitiator) 1 else 0)
@ -80,13 +81,8 @@ class LocalChannelKeyManager(seed: ByteVector, chainHash: ByteVector32) extends
DeterministicWallet.KeyPath(Seq(next(), next(), next(), next(), next(), next(), next(), next(), last))
}
override def fundingPublicKey(channelKeyPath: DeterministicWallet.KeyPath, fundingTxIndex: Long): ExtendedPublicKey = {
val keyPath = if (fundingTxIndex == 0) {
// For backward-compat with pre-splice channels, we treat the initial funding pubkey differently
internalKeyPath(channelKeyPath, hardened(0))
} else {
internalKeyPath(channelKeyPath, hardened(6)).derive(fundingTxIndex)
}
override def fundingPublicKey(fundingKeyPath: DeterministicWallet.KeyPath, fundingTxIndex: Long): ExtendedPublicKey = {
val keyPath = internalKeyPath(fundingKeyPath, hardened(fundingTxIndex))
publicKeys.get(keyPath)
}
@ -98,6 +94,8 @@ class LocalChannelKeyManager(seed: ByteVector, chainHash: ByteVector32) extends
override def htlcPoint(channelKeyPath: DeterministicWallet.KeyPath): ExtendedPublicKey = publicKeys.get(internalKeyPath(channelKeyPath, hardened(4)))
private def shaSeed(channelKeyPath: DeterministicWallet.KeyPath): ByteVector32 = Crypto.sha256(privateKeys.get(internalKeyPath(channelKeyPath, hardened(5))).privateKey.value :+ 1.toByte)
override def commitmentSecret(channelKeyPath: DeterministicWallet.KeyPath, index: Long): PrivateKey = Generators.perCommitSecret(shaSeed(channelKeyPath), index)
override def commitmentPoint(channelKeyPath: DeterministicWallet.KeyPath, index: Long): PublicKey = Generators.perCommitPoint(shaSeed(channelKeyPath), index)

View File

@ -215,7 +215,7 @@ object TransactionSerializer extends MinimalSerializer({
})
object KeyPathSerializer extends MinimalSerializer({
case x: KeyPath => JObject(JField("path", JArray(x.path.map(x => JLong(x)).toList)))
case x: KeyPath => JArray(x.path.map(x => JLong(x)).toList)
})
object TransactionWithInputInfoSerializer extends MinimalSerializer({

View File

@ -7,9 +7,7 @@
"channelFeatures" : [ ],
"localParams" : {
"nodeId" : "03933884aaf1d6b108397e5efe5c86bcf2d8ca8d2f700eda99db9214fc2712b134",
"fundingKeyPath" : {
"path" : [ 1457788542, 1007597768, 1455922339, 479707306 ]
},
"fundingKeyPath" : [ 1457788542, 1007597768, 1455922339, 479707306 ],
"dustLimit" : 546,
"maxHtlcValueInFlightMsat" : 5000000000,
"requestedChannelReserve_opt" : 167772,

View File

@ -7,9 +7,7 @@
"channelFeatures" : [ ],
"localParams" : {
"nodeId" : "03933884aaf1d6b108397e5efe5c86bcf2d8ca8d2f700eda99db9214fc2712b134",
"fundingKeyPath" : {
"path" : [ 3561221353, 3653515793, 2711311691, 2863050005 ]
},
"fundingKeyPath" : [ 3561221353, 3653515793, 2711311691, 2863050005 ],
"dustLimit" : 546,
"maxHtlcValueInFlightMsat" : 1000000000,
"requestedChannelReserve_opt" : 150000,

View File

@ -7,9 +7,7 @@
"channelFeatures" : [ "option_static_remotekey" ],
"localParams" : {
"nodeId" : "03933884aaf1d6b108397e5efe5c86bcf2d8ca8d2f700eda99db9214fc2712b134",
"fundingKeyPath" : {
"path" : [ 2353764507, 3184449568, 2809819526, 3258060413, 392846475, 1545000620, 720603293, 1808318336, 2147483649 ]
},
"fundingKeyPath" : [ 2353764507, 3184449568, 2809819526, 3258060413, 392846475, 1545000620, 720603293, 1808318336, 2147483649 ],
"dustLimit" : 546,
"maxHtlcValueInFlightMsat" : 20000000000,
"requestedChannelReserve_opt" : 150000,

View File

@ -7,9 +7,7 @@
"channelFeatures" : [ ],
"localParams" : {
"nodeId" : "02aaaa00ce2f18a967dc4f25f414e671ba6585f8ef0b8c5fb812c21064f55a2eaa",
"fundingKeyPath" : {
"path" : [ 4092535092, 4227137620, 3959690417, 2298849496, 2106263857, 1090614243, 1495530077, 1280982866, 2147483649 ]
},
"fundingKeyPath" : [ 4092535092, 4227137620, 3959690417, 2298849496, 2106263857, 1090614243, 1495530077, 1280982866, 2147483649 ],
"dustLimit" : 1100,
"maxHtlcValueInFlightMsat" : 500000000,
"requestedChannelReserve_opt" : 10000,

View File

@ -7,9 +7,7 @@
"channelFeatures" : [ ],
"localParams" : {
"nodeId" : "02aaaa00ce2f18a967dc4f25f414e671ba6585f8ef0b8c5fb812c21064f55a2eaa",
"fundingKeyPath" : {
"path" : [ 303987973, 3198768511, 3783619274, 2277156978, 1699864653, 63358126, 3265052696, 516813756, 2147483649 ]
},
"fundingKeyPath" : [ 303987973, 3198768511, 3783619274, 2277156978, 1699864653, 63358126, 3265052696, 516813756, 2147483649 ],
"dustLimit" : 1100,
"maxHtlcValueInFlightMsat" : 500000000,
"requestedChannelReserve_opt" : 10000,

View File

@ -7,9 +7,7 @@
"channelFeatures" : [ "option_static_remotekey", "option_anchors_zero_fee_htlc_tx", "option_dual_fund" ],
"localParams" : {
"nodeId" : "02aaaa00ce2f18a967dc4f25f414e671ba6585f8ef0b8c5fb812c21064f55a2eaa",
"fundingKeyPath" : {
"path" : [ 3109590638, 2571039769, 2759029525, 192289746, 3879532998, 1343053922, 3645251601, 1767821717, 2147483649 ]
},
"fundingKeyPath" : [ 3109590638, 2571039769, 2759029525, 192289746, 3879532998, 1343053922, 3645251601, 1767821717, 2147483649 ],
"dustLimit" : 1100,
"maxHtlcValueInFlightMsat" : 500000000,
"htlcMinimum" : 0,