Skip to content

Commit 5b4d556

Browse files
KeysInterface::sign_invoice: indicate whether invoice is a phantom
1 parent 771a6d8 commit 5b4d556

File tree

6 files changed

+39
-17
lines changed

6 files changed

+39
-17
lines changed

fuzz/src/chanmon_consistency.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,7 @@ use lightning::chain::{BestBlock, ChannelMonitorUpdateErr, chainmonitor, channel
3434
use lightning::chain::channelmonitor::{ChannelMonitor, MonitorEvent};
3535
use lightning::chain::transaction::OutPoint;
3636
use lightning::chain::chaininterface::{BroadcasterInterface, ConfirmationTarget, FeeEstimator};
37-
use lightning::chain::keysinterface::{KeyMaterial, KeysInterface, InMemorySigner};
37+
use lightning::chain::keysinterface::{KeyMaterial, KeysInterface, InMemorySigner, Recipient};
3838
use lightning::ln::{PaymentHash, PaymentPreimage, PaymentSecret};
3939
use lightning::ln::channelmanager::{ChainParameters, ChannelManager, PaymentSendFailure, ChannelManagerReadArgs};
4040
use lightning::ln::channel::FEE_SPIKE_BUFFER_FEE_INCREASE_MULTIPLE;
@@ -222,7 +222,7 @@ impl KeysInterface for KeyProvider {
222222
})
223223
}
224224

225-
fn sign_invoice(&self, _hrp_bytes: &[u8], _invoice_data: &[u5]) -> Result<RecoverableSignature, ()> {
225+
fn sign_invoice(&self, _hrp_bytes: &[u8], _invoice_data: &[u5], _recipient: Recipient) -> Result<RecoverableSignature, ()> {
226226
unreachable!()
227227
}
228228
}

fuzz/src/full_stack.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ use lightning::chain::{BestBlock, Confirm, Listen};
3131
use lightning::chain::chaininterface::{BroadcasterInterface, ConfirmationTarget, FeeEstimator};
3232
use lightning::chain::chainmonitor;
3333
use lightning::chain::transaction::OutPoint;
34-
use lightning::chain::keysinterface::{InMemorySigner, KeyMaterial, KeysInterface};
34+
use lightning::chain::keysinterface::{InMemorySigner, Recipient, KeyMaterial, KeysInterface};
3535
use lightning::ln::{PaymentHash, PaymentPreimage, PaymentSecret};
3636
use lightning::ln::channelmanager::{ChainParameters, ChannelManager};
3737
use lightning::ln::peer_handler::{MessageHandler,PeerManager,SocketDescriptor,IgnoringMessageHandler};
@@ -336,7 +336,7 @@ impl KeysInterface for KeyProvider {
336336
))
337337
}
338338

339-
fn sign_invoice(&self, _hrp_bytes: &[u8], _invoice_data: &[u5]) -> Result<RecoverableSignature, ()> {
339+
fn sign_invoice(&self, _hrp_bytes: &[u8], _invoice_data: &[u5], _recipient: Recipient) -> Result<RecoverableSignature, ()> {
340340
unreachable!()
341341
}
342342
}

lightning-invoice/src/utils.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ use bitcoin_hashes::Hash;
88
use crate::prelude::*;
99
use lightning::chain;
1010
use lightning::chain::chaininterface::{BroadcasterInterface, FeeEstimator};
11-
use lightning::chain::keysinterface::{Sign, KeysInterface};
11+
use lightning::chain::keysinterface::{Recipient, KeysInterface, Sign};
1212
use lightning::ln::{PaymentHash, PaymentPreimage, PaymentSecret};
1313
use lightning::ln::channelmanager::{ChannelDetails, ChannelManager, PaymentId, PaymentSendFailure, MIN_FINAL_CLTV_EXPIRY};
1414
use lightning::ln::msgs::LightningError;
@@ -118,7 +118,7 @@ where
118118
let hrp_str = raw_invoice.hrp.to_string();
119119
let hrp_bytes = hrp_str.as_bytes();
120120
let data_without_signature = raw_invoice.data.to_base32();
121-
let signed_raw_invoice = raw_invoice.sign(|_| keys_manager.sign_invoice(hrp_bytes, &data_without_signature));
121+
let signed_raw_invoice = raw_invoice.sign(|_| keys_manager.sign_invoice(hrp_bytes, &data_without_signature, Recipient::Node));
122122
match signed_raw_invoice {
123123
Ok(inv) => Ok(Invoice::from_signed(inv).unwrap()),
124124
Err(e) => Err(SignOrCreationError::SignError(e))

lightning/src/chain/keysinterface.rs

Lines changed: 27 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -380,6 +380,18 @@ pub trait BaseSign {
380380
pub trait Sign: BaseSign + Writeable + Clone {
381381
}
382382

383+
/// Specifies the recipient of an invoice, to indicate to [`KeysInterface::sign_invoice`] what node
384+
/// secret key should be used to sign the invoice.
385+
pub enum Recipient {
386+
/// The invoice should be signed with the local node secret key.
387+
Node,
388+
/// The invoice should be signed with the phantom node secret key. This secret key must be the
389+
/// same for all nodes participating in the [phantom node payment].
390+
///
391+
/// [phantom node payment]: PhantomKeysManager
392+
PhantomNode,
393+
}
394+
383395
/// A trait to describe an object which can get user secrets and key material.
384396
pub trait KeysInterface {
385397
/// A type which implements Sign which will be returned by get_channel_signer.
@@ -424,7 +436,9 @@ pub trait KeysInterface {
424436
/// this trait to parse the invoice and make sure they're signing what they expect, rather than
425437
/// blindly signing the hash.
426438
/// The hrp is ascii bytes, while the invoice data is base32.
427-
fn sign_invoice(&self, hrp_bytes: &[u8], invoice_data: &[u5]) -> Result<RecoverableSignature, ()>;
439+
///
440+
/// The secret key used to sign the invoice is dependent on the [`Recipient`].
441+
fn sign_invoice(&self, hrp_bytes: &[u8], invoice_data: &[u5], receipient: Recipient) -> Result<RecoverableSignature, ()>;
428442

429443
/// Get secret key material as bytes for use in encrypting and decrypting inbound payment data.
430444
///
@@ -1149,9 +1163,13 @@ impl KeysInterface for KeysManager {
11491163
InMemorySigner::read(&mut io::Cursor::new(reader), self.get_node_secret())
11501164
}
11511165

1152-
fn sign_invoice(&self, hrp_bytes: &[u8], invoice_data: &[u5]) -> Result<RecoverableSignature, ()> {
1166+
fn sign_invoice(&self, hrp_bytes: &[u8], invoice_data: &[u5], recipient: Recipient) -> Result<RecoverableSignature, ()> {
11531167
let preimage = construct_invoice_preimage(&hrp_bytes, &invoice_data);
1154-
Ok(self.secp_ctx.sign_recoverable(&hash_to_message!(&Sha256::hash(&preimage)), &self.get_node_secret()))
1168+
let secret = match recipient {
1169+
Recipient::Node => self.get_node_secret(),
1170+
Recipient::PhantomNode => return Err(()),
1171+
};
1172+
Ok(self.secp_ctx.sign_recoverable(&hash_to_message!(&Sha256::hash(&preimage)), &secret))
11551173
}
11561174
}
11571175

@@ -1213,9 +1231,13 @@ impl KeysInterface for PhantomKeysManager {
12131231
self.inner.read_chan_signer(reader)
12141232
}
12151233

1216-
fn sign_invoice(&self, hrp_bytes: &[u8], invoice_data: &[u5]) -> Result<RecoverableSignature, ()> {
1234+
fn sign_invoice(&self, hrp_bytes: &[u8], invoice_data: &[u5], recipient: Recipient) -> Result<RecoverableSignature, ()> {
12171235
let preimage = construct_invoice_preimage(&hrp_bytes, &invoice_data);
1218-
Ok(self.inner.secp_ctx.sign_recoverable(&hash_to_message!(&Sha256::hash(&preimage)), &self.get_node_secret()))
1236+
let secret = match recipient {
1237+
Recipient::Node => self.get_node_secret(),
1238+
Recipient::PhantomNode => self.phantom_secret.clone(),
1239+
};
1240+
Ok(self.inner.secp_ctx.sign_recoverable(&hash_to_message!(&Sha256::hash(&preimage)), &secret))
12191241
}
12201242
}
12211243

lightning/src/ln/channel.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6116,7 +6116,7 @@ mod tests {
61166116
use ln::chan_utils::{ChannelPublicKeys, HolderCommitmentTransaction, CounterpartyChannelTransactionParameters, htlc_success_tx_weight, htlc_timeout_tx_weight};
61176117
use chain::BestBlock;
61186118
use chain::chaininterface::{FeeEstimator,ConfirmationTarget};
6119-
use chain::keysinterface::{InMemorySigner, KeyMaterial, KeysInterface, BaseSign};
6119+
use chain::keysinterface::{InMemorySigner, Recipient, KeyMaterial, KeysInterface, BaseSign};
61206120
use chain::transaction::OutPoint;
61216121
use util::config::UserConfig;
61226122
use util::enforcing_trait_impls::EnforcingSigner;
@@ -6184,7 +6184,7 @@ mod tests {
61846184
}
61856185
fn get_secure_random_bytes(&self) -> [u8; 32] { [0; 32] }
61866186
fn read_chan_signer(&self, _data: &[u8]) -> Result<Self::Signer, DecodeError> { panic!(); }
6187-
fn sign_invoice(&self, _hrp_bytes: &[u8], _invoice_data: &[u5]) -> Result<RecoverableSignature, ()> { panic!(); }
6187+
fn sign_invoice(&self, _hrp_bytes: &[u8], _invoice_data: &[u5], _recipient: Recipient) -> Result<RecoverableSignature, ()> { panic!(); }
61886188
}
61896189

61906190
fn public_from_secret_hex(secp_ctx: &Secp256k1<All>, hex: &str) -> PublicKey {

lightning/src/util/test_utils.rs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ use sync::{Mutex, Arc};
4747
use core::sync::atomic::{AtomicBool, AtomicUsize, Ordering};
4848
use core::{cmp, mem};
4949
use bitcoin::bech32::u5;
50-
use chain::keysinterface::{InMemorySigner, KeyMaterial};
50+
use chain::keysinterface::{InMemorySigner, Recipient, KeyMaterial};
5151

5252
pub struct TestVecWriter(pub Vec<u8>);
5353
impl Writer for TestVecWriter {
@@ -88,7 +88,7 @@ impl keysinterface::KeysInterface for OnlyReadsKeysInterface {
8888
false
8989
))
9090
}
91-
fn sign_invoice(&self, _hrp_bytes: &[u8], _invoice_data: &[u5]) -> Result<RecoverableSignature, ()> { unreachable!(); }
91+
fn sign_invoice(&self, _hrp_bytes: &[u8], _invoice_data: &[u5], _recipient: Recipient) -> Result<RecoverableSignature, ()> { unreachable!(); }
9292
}
9393

9494
pub struct TestChainMonitor<'a> {
@@ -529,8 +529,8 @@ impl keysinterface::KeysInterface for TestKeysInterface {
529529
))
530530
}
531531

532-
fn sign_invoice(&self, hrp_bytes: &[u8], invoice_data: &[u5]) -> Result<RecoverableSignature, ()> {
533-
self.backing.sign_invoice(hrp_bytes, invoice_data)
532+
fn sign_invoice(&self, hrp_bytes: &[u8], invoice_data: &[u5], recipient: Recipient) -> Result<RecoverableSignature, ()> {
533+
self.backing.sign_invoice(hrp_bytes, invoice_data, recipient)
534534
}
535535
}
536536

0 commit comments

Comments
 (0)