Pass FinalOnionHopData to payment verify by reference, not clone
[rust-lightning] / lightning / src / ln / inbound_payment.rs
index f7fbb48985ef07492a5ce129e95aeec739643c92..f4f114d957193c8bf696f8cc12cacb49c005d0ed 100644 (file)
@@ -38,7 +38,7 @@ const METHOD_TYPE_OFFSET: usize = 5;
 /// [`KeysInterface::get_inbound_payment_key_material`].
 ///
 /// [`KeysInterface::get_inbound_payment_key_material`]: crate::chain::keysinterface::KeysInterface::get_inbound_payment_key_material
-pub(super) struct ExpandedKey {
+pub struct ExpandedKey {
        /// The key used to encrypt the bytes containing the payment metadata (i.e. the amount and
        /// expiry, included for payment verification on decryption).
        metadata_key: [u8; 32],
@@ -51,7 +51,10 @@ pub(super) struct ExpandedKey {
 }
 
 impl ExpandedKey {
-       pub(super) fn new(key_material: &KeyMaterial) -> ExpandedKey {
+       /// Create a  new [`ExpandedKey`] for generating an inbound payment hash and secret.
+       ///
+       /// It is recommended to cache this value and not regenerate it for each new inbound payment.
+       pub fn new(key_material: &KeyMaterial) -> ExpandedKey {
                let (metadata_key, ldk_pmt_hash_key, user_pmt_hash_key) =
                        hkdf_extract_expand_thrice(b"LDK Inbound Payment Key Expansion", &key_material.0);
                Self {
@@ -77,10 +80,21 @@ impl Method {
        }
 }
 
-pub(super) fn create<Signer: Sign, K: Deref>(keys: &ExpandedKey, min_value_msat: Option<u64>, invoice_expiry_delta_secs: u32, keys_manager: &K, highest_seen_timestamp: u64) -> Result<(PaymentHash, PaymentSecret), ()>
+/// Equivalent to [`crate::ln::channelmanager::ChannelManager::create_inbound_payment`], but no
+/// `ChannelManager` is required. Useful for generating invoices for [phantom node payments] without
+/// a `ChannelManager`.
+///
+/// `keys` is generated by calling [`KeysInterface::get_inbound_payment_key_material`] and then
+/// calling [`ExpandedKey::new`] with its result. It is recommended to cache this value and not
+/// regenerate it for each new inbound payment.
+///
+/// `current_time` is a Unix timestamp representing the current time.
+///
+/// [phantom node payments]: crate::chain::keysinterface::PhantomKeysManager
+pub fn create<Signer: Sign, K: Deref>(keys: &ExpandedKey, min_value_msat: Option<u64>, invoice_expiry_delta_secs: u32, keys_manager: &K, current_time: u64) -> Result<(PaymentHash, PaymentSecret), ()>
        where K::Target: KeysInterface<Signer = Signer>
 {
-       let metadata_bytes = construct_metadata_bytes(min_value_msat, Method::LdkPaymentHash, invoice_expiry_delta_secs, highest_seen_timestamp)?;
+       let metadata_bytes = construct_metadata_bytes(min_value_msat, Method::LdkPaymentHash, invoice_expiry_delta_secs, current_time)?;
 
        let mut iv_bytes = [0 as u8; IV_LEN];
        let rand_bytes = keys_manager.get_secure_random_bytes();
@@ -96,8 +110,15 @@ pub(super) fn create<Signer: Sign, K: Deref>(keys: &ExpandedKey, min_value_msat:
        Ok((ldk_pmt_hash, payment_secret))
 }
 
-pub(super) fn create_from_hash(keys: &ExpandedKey, min_value_msat: Option<u64>, payment_hash: PaymentHash, invoice_expiry_delta_secs: u32, highest_seen_timestamp: u64) -> Result<PaymentSecret, ()> {
-       let metadata_bytes = construct_metadata_bytes(min_value_msat, Method::UserPaymentHash, invoice_expiry_delta_secs, highest_seen_timestamp)?;
+/// Equivalent to [`crate::ln::channelmanager::ChannelManager::create_inbound_payment_for_hash`],
+/// but no `ChannelManager` is required. Useful for generating invoices for [phantom node payments]
+/// without a `ChannelManager`.
+///
+/// See [`create`] for information on the `keys` and `current_time` parameters.
+///
+/// [phantom node payments]: crate::chain::keysinterface::PhantomKeysManager
+pub fn create_from_hash(keys: &ExpandedKey, min_value_msat: Option<u64>, payment_hash: PaymentHash, invoice_expiry_delta_secs: u32, current_time: u64) -> Result<PaymentSecret, ()> {
+       let metadata_bytes = construct_metadata_bytes(min_value_msat, Method::UserPaymentHash, invoice_expiry_delta_secs, current_time)?;
 
        let mut hmac = HmacEngine::<Sha256>::new(&keys.user_pmt_hash_key);
        hmac.input(&metadata_bytes);
@@ -179,7 +200,7 @@ fn construct_payment_secret(iv_bytes: &[u8; IV_LEN], metadata_bytes: &[u8; METAD
 /// [`KeysInterface::get_inbound_payment_key_material`]: crate::chain::keysinterface::KeysInterface::get_inbound_payment_key_material
 /// [`create_inbound_payment`]: crate::ln::channelmanager::ChannelManager::create_inbound_payment
 /// [`create_inbound_payment_for_hash`]: crate::ln::channelmanager::ChannelManager::create_inbound_payment_for_hash
-pub(super) fn verify<L: Deref>(payment_hash: PaymentHash, payment_data: msgs::FinalOnionHopData, highest_seen_timestamp: u64, keys: &ExpandedKey, logger: &L) -> Result<Option<PaymentPreimage>, ()>
+pub(super) fn verify<L: Deref>(payment_hash: PaymentHash, payment_data: &msgs::FinalOnionHopData, highest_seen_timestamp: u64, keys: &ExpandedKey, logger: &L) -> Result<Option<PaymentPreimage>, ()>
        where L::Target: Logger
 {
        let (iv_bytes, metadata_bytes) = decrypt_metadata(payment_data.payment_secret, keys);