Skip to content

Commit 9403d31

Browse files
committed
Support signing BOLT 12 messages in NodeSigner
BOLT 12 messages need to be signed in the following scenarios: - constructing an InvoiceRequest after scanning an Offer, - constructing an Invoice after scanning a Refund, and - constructing an Invoice when handling an InvoiceRequest. Extend the NodeSigner trait to support signing BOLT 12 messages such that it can be used in these contexts. The method could be used then in OnionMessenger and an OffersMessageHandler.
1 parent 35914dd commit 9403d31

File tree

5 files changed

+64
-1
lines changed

5 files changed

+64
-1
lines changed

fuzz/src/chanmon_consistency.rs

+8
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@ use lightning::ln::channel::FEE_SPIKE_BUFFER_FEE_INCREASE_MULTIPLE;
4444
use lightning::ln::msgs::{self, CommitmentUpdate, ChannelMessageHandler, DecodeError, UpdateAddHTLC, Init};
4545
use lightning::ln::script::ShutdownScript;
4646
use lightning::ln::functional_test_utils::*;
47+
use lightning::offers::merkle::TaggedHash;
4748
use lightning::util::enforcing_trait_impls::{EnforcingSigner, EnforcementState};
4849
use lightning::util::errors::APIError;
4950
use lightning::util::logger::Logger;
@@ -57,6 +58,7 @@ use crate::utils::test_persister::TestPersister;
5758
use bitcoin::secp256k1::{Message, PublicKey, SecretKey, Scalar, Secp256k1};
5859
use bitcoin::secp256k1::ecdh::SharedSecret;
5960
use bitcoin::secp256k1::ecdsa::{RecoverableSignature, Signature};
61+
use bitcoin::secp256k1::schnorr;
6062

6163
use std::mem;
6264
use std::cmp::{self, Ordering};
@@ -211,6 +213,12 @@ impl NodeSigner for KeyProvider {
211213
unreachable!()
212214
}
213215

216+
fn sign_bolt12_message(
217+
&self, _message: &TaggedHash, _metadata: &[u8]
218+
) -> Result<schnorr::Signature, ()> {
219+
unreachable!()
220+
}
221+
214222
fn sign_gossip_message(&self, msg: lightning::ln::msgs::UnsignedGossipMessage) -> Result<Signature, ()> {
215223
let msg_hash = Message::from_slice(&Sha256dHash::hash(&msg.encode()[..])[..]).map_err(|_| ())?;
216224
let secp_ctx = Secp256k1::signing_only();

fuzz/src/full_stack.rs

+8
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ use lightning::ln::peer_handler::{MessageHandler,PeerManager,SocketDescriptor,Ig
4040
use lightning::ln::msgs::{self, DecodeError};
4141
use lightning::ln::script::ShutdownScript;
4242
use lightning::ln::functional_test_utils::*;
43+
use lightning::offers::merkle::TaggedHash;
4344
use lightning::routing::gossip::{P2PGossipSync, NetworkGraph};
4445
use lightning::routing::utxo::UtxoLookup;
4546
use lightning::routing::router::{InFlightHtlcs, PaymentParameters, Route, RouteParameters, Router};
@@ -55,6 +56,7 @@ use crate::utils::test_persister::TestPersister;
5556
use bitcoin::secp256k1::{Message, PublicKey, SecretKey, Scalar, Secp256k1};
5657
use bitcoin::secp256k1::ecdh::SharedSecret;
5758
use bitcoin::secp256k1::ecdsa::{RecoverableSignature, Signature};
59+
use bitcoin::secp256k1::schnorr;
5860

5961
use std::cell::RefCell;
6062
use hashbrown::{HashMap, hash_map};
@@ -316,6 +318,12 @@ impl NodeSigner for KeyProvider {
316318
unreachable!()
317319
}
318320

321+
fn sign_bolt12_message(
322+
&self, _message: &TaggedHash, _metadata: &[u8]
323+
) -> Result<schnorr::Signature, ()> {
324+
unreachable!()
325+
}
326+
319327
fn sign_gossip_message(&self, msg: lightning::ln::msgs::UnsignedGossipMessage) -> Result<Signature, ()> {
320328
let msg_hash = Message::from_slice(&Sha256dHash::hash(&msg.encode()[..])[..]).map_err(|_| ())?;
321329
let secp_ctx = Secp256k1::signing_only();

fuzz/src/onion_message.rs

+8
Original file line numberDiff line numberDiff line change
@@ -4,10 +4,12 @@ use bitcoin::blockdata::script::Script;
44
use bitcoin::secp256k1::{PublicKey, Scalar, Secp256k1, SecretKey};
55
use bitcoin::secp256k1::ecdh::SharedSecret;
66
use bitcoin::secp256k1::ecdsa::RecoverableSignature;
7+
use bitcoin::secp256k1::schnorr;
78

89
use lightning::sign::{Recipient, KeyMaterial, EntropySource, NodeSigner, SignerProvider};
910
use lightning::ln::msgs::{self, DecodeError, OnionMessageHandler};
1011
use lightning::ln::script::ShutdownScript;
12+
use lightning::offers::merkle::TaggedHash;
1113
use lightning::util::enforcing_trait_impls::EnforcingSigner;
1214
use lightning::util::logger::Logger;
1315
use lightning::util::ser::{Readable, Writeable, Writer};
@@ -153,6 +155,12 @@ impl NodeSigner for KeyProvider {
153155
unreachable!()
154156
}
155157

158+
fn sign_bolt12_message(
159+
&self, _message: &TaggedHash, _metadata: &[u8]
160+
) -> Result<schnorr::Signature, ()> {
161+
unreachable!()
162+
}
163+
156164
fn sign_gossip_message(&self, _msg: lightning::ln::msgs::UnsignedGossipMessage) -> Result<bitcoin::secp256k1::ecdsa::Signature, ()> {
157165
unreachable!()
158166
}

lightning/src/sign/mod.rs

+26-1
Original file line numberDiff line numberDiff line change
@@ -26,9 +26,10 @@ use bitcoin::hashes::sha256::Hash as Sha256;
2626
use bitcoin::hashes::sha256d::Hash as Sha256dHash;
2727
use bitcoin::hash_types::WPubkeyHash;
2828

29-
use bitcoin::secp256k1::{PublicKey, Scalar, Secp256k1, SecretKey, Signing};
29+
use bitcoin::secp256k1::{KeyPair, PublicKey, Scalar, Secp256k1, SecretKey, Signing};
3030
use bitcoin::secp256k1::ecdh::SharedSecret;
3131
use bitcoin::secp256k1::ecdsa::{RecoverableSignature, Signature};
32+
use bitcoin::secp256k1::schnorr;
3233
use bitcoin::{PackedLockTime, secp256k1, Sequence, Witness};
3334

3435
use crate::util::transaction_utils;
@@ -41,6 +42,7 @@ use crate::ln::{chan_utils, PaymentPreimage};
4142
use crate::ln::chan_utils::{HTLCOutputInCommitment, make_funding_redeemscript, ChannelPublicKeys, HolderCommitmentTransaction, ChannelTransactionParameters, CommitmentTransaction, ClosingTransaction};
4243
use crate::ln::msgs::{UnsignedChannelAnnouncement, UnsignedGossipMessage};
4344
use crate::ln::script::ShutdownScript;
45+
use crate::offers::merkle::TaggedHash;
4446

4547
use crate::prelude::*;
4648
use core::convert::TryInto;
@@ -619,6 +621,15 @@ pub trait NodeSigner {
619621
/// Errors if the [`Recipient`] variant is not supported by the implementation.
620622
fn sign_invoice(&self, hrp_bytes: &[u8], invoice_data: &[u5], recipient: Recipient) -> Result<RecoverableSignature, ()>;
621623

624+
/// Signs a BOLT 12 message.
625+
///
626+
/// See [`SignFunction`] for details.
627+
///
628+
/// [`SignFunction`]: crate::offers::merkle::SignFunction
629+
fn sign_bolt12_message(
630+
&self, message: &TaggedHash, metadata: &[u8]
631+
) -> Result<schnorr::Signature, ()>;
632+
622633
/// Sign a gossip message.
623634
///
624635
/// Note that if this fails, LDK may panic and the message will not be broadcast to the network
@@ -1449,6 +1460,14 @@ impl NodeSigner for KeysManager {
14491460
Ok(self.secp_ctx.sign_ecdsa_recoverable(&hash_to_message!(&Sha256::hash(&preimage)), secret))
14501461
}
14511462

1463+
fn sign_bolt12_message(
1464+
&self, message: &TaggedHash, _metadata: &[u8]
1465+
) -> Result<schnorr::Signature, ()> {
1466+
let keys = KeyPair::from_secret_key(&self.secp_ctx, &self.node_secret);
1467+
let aux_rand = self.get_secure_random_bytes();
1468+
Ok(self.secp_ctx.sign_schnorr_with_aux_rand(&message.to_digest(), &keys, &aux_rand))
1469+
}
1470+
14521471
fn sign_gossip_message(&self, msg: UnsignedGossipMessage) -> Result<Signature, ()> {
14531472
let msg_hash = hash_to_message!(&Sha256dHash::hash(&msg.encode()[..])[..]);
14541473
Ok(self.secp_ctx.sign_ecdsa(&msg_hash, &self.node_secret))
@@ -1557,6 +1576,12 @@ impl NodeSigner for PhantomKeysManager {
15571576
Ok(self.inner.secp_ctx.sign_ecdsa_recoverable(&hash_to_message!(&Sha256::hash(&preimage)), secret))
15581577
}
15591578

1579+
fn sign_bolt12_message(
1580+
&self, message: &TaggedHash, metadata: &[u8]
1581+
) -> Result<schnorr::Signature, ()> {
1582+
self.inner.sign_bolt12_message(message, metadata)
1583+
}
1584+
15601585
fn sign_gossip_message(&self, msg: UnsignedGossipMessage) -> Result<Signature, ()> {
15611586
self.inner.sign_gossip_message(msg)
15621587
}

lightning/src/util/test_utils.rs

+14
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ use crate::ln::features::{ChannelFeatures, InitFeatures, NodeFeatures};
2424
use crate::ln::{msgs, wire};
2525
use crate::ln::msgs::LightningError;
2626
use crate::ln::script::ShutdownScript;
27+
use crate::offers::merkle::TaggedHash;
2728
use crate::routing::gossip::{EffectiveCapacity, NetworkGraph, NodeId};
2829
use crate::routing::utxo::{UtxoLookup, UtxoLookupError, UtxoResult};
2930
use crate::routing::router::{find_route, InFlightHtlcs, Path, Route, RouteParameters, Router, ScorerAccountingForInFlightHtlcs};
@@ -47,6 +48,7 @@ use bitcoin::util::sighash::SighashCache;
4748
use bitcoin::secp256k1::{PublicKey, Scalar, Secp256k1, SecretKey};
4849
use bitcoin::secp256k1::ecdh::SharedSecret;
4950
use bitcoin::secp256k1::ecdsa::{RecoverableSignature, Signature};
51+
use bitcoin::secp256k1::schnorr;
5052

5153
#[cfg(any(test, feature = "_test_utils"))]
5254
use regex;
@@ -800,6 +802,12 @@ impl NodeSigner for TestNodeSigner {
800802
unreachable!()
801803
}
802804

805+
fn sign_bolt12_message(
806+
&self, _message: &TaggedHash, _metadata: &[u8]
807+
) -> Result<schnorr::Signature, ()> {
808+
unreachable!()
809+
}
810+
803811
fn sign_gossip_message(&self, _msg: msgs::UnsignedGossipMessage) -> Result<Signature, ()> {
804812
unreachable!()
805813
}
@@ -840,6 +848,12 @@ impl NodeSigner for TestKeysInterface {
840848
self.backing.sign_invoice(hrp_bytes, invoice_data, recipient)
841849
}
842850

851+
fn sign_bolt12_message(
852+
&self, message: &TaggedHash, metadata: &[u8]
853+
) -> Result<schnorr::Signature, ()> {
854+
self.backing.sign_bolt12_message(message, metadata)
855+
}
856+
843857
fn sign_gossip_message(&self, msg: msgs::UnsignedGossipMessage) -> Result<Signature, ()> {
844858
self.backing.sign_gossip_message(msg)
845859
}

0 commit comments

Comments
 (0)