Cleanup: Remove redundant (hmac, nonce) from codebase
What changed, and why it matters
This commit removes an older, now-redundant HMAC/nonce authentication mechanism from LDK's blinded payment paths. The code had already introduced a newer 'ReceiveAuthKey' way to authenticate the same data, so the old (hmac, nonce) fields are being stripped out to simplify the codebase. The change is described by the project as a cleanup, not a security fix, and the diff shows the old verification checks being replaced by reliance on the newer mechanism. There is no direct evidence in the commit of an exploitable vulnerability, but removing a redundant authentication layer is a normal hardening step.
Treat this as a code-cleanup refactor rather than an urgent vulnerability patch. Reviewers should confirm that ReceiveAuthKey-based authentication is actually enforced on all inbound BlindedPaymentPath/Trampoline receive contexts that previously relied on the removed HMAC, and that no code path still expects or silently ignores the old authentication TLV. Regression tests for authentication failure (e.g., fails_receive_tlvs_authentication) should continue to pass with the new mechanism.
Security signals we found
Removal of redundant HMAC/nonce authentication fields
Replacement of legacy authenticate()/verify_for_offer_payment() with ReceiveAuthKey-based authentication
Deletion of PAYMENT_TLVS_HMAC_INPUT and associated HMAC helpers
Serialization change dropping TLV 65539 (authentication) from receive TLVs
Comment indicating old receive contexts will fail new authentication checks
Evidence from the diff
The patch refactors ReceiveTlvs so it no longer wraps UnauthenticatedReceiveTlvs plus an (HMAC, Nonce) tuple. Instead, ReceiveTlvs now directly contains payment_secret, payment_constraints, and payment_context. The HMAC computation and verification helpers (hmac_for_payment_tlvs, verify_payment_tlvs, the Verification trait) are deleted, and callers no longer call authenticate() before creating a BlindedPaymentPath. The deserialization paths for BlindedPaymentTlvs and BlindedTrampolineTlvs drop the optional authentication TLV (65539). A code comment notes that the authentication TLV field is being reused because old contexts are no longer supported. The newer ReceiveAuthKey-based authentication remains in place.
Changed components
lightning/src/blinded_path/payment.rslightning/src/ln/msgs.rslightning/src/ln/channelmanager.rslightning/src/offers/flow.rslightning/src/offers/signer.rslightning/src/routing/router.rsfuzz targets invoice_request_deser.rs and refund_deser.rsInspect captured patch +76 / −268
diff --git a/fuzz/src/invoice_request_deser.rs b/fuzz/src/invoice_request_deser.rs
index 93618d1..a21303d 100644
--- a/fuzz/src/invoice_request_deser.rs
+++ b/fuzz/src/invoice_request_deser.rs
@@ -12,13 +12,12 @@ use bitcoin::secp256k1::{self, Keypair, Parity, PublicKey, Secp256k1, SecretKey}
use core::convert::TryFrom;
use lightning::blinded_path::payment::{
BlindedPaymentPath, Bolt12OfferContext, ForwardTlvs, PaymentConstraints, PaymentContext,
- PaymentForwardNode, PaymentRelay, UnauthenticatedReceiveTlvs,
+ PaymentForwardNode, PaymentRelay, ReceiveTlvs,
};
use lightning::ln::channelmanager::MIN_FINAL_CLTV_EXPIRY_DELTA;
use lightning::ln::inbound_payment::ExpandedKey;
use lightning::offers::invoice::UnsignedBolt12Invoice;
use lightning::offers::invoice_request::{InvoiceRequest, InvoiceRequestFields};
-use lightning::offers::nonce::Nonce;
use lightning::offers::offer::OfferId;
use lightning::offers::parse::Bolt12SemanticError;
use lightning::sign::{EntropySource, ReceiveAuthKey};
@@ -84,7 +83,6 @@ fn build_response<T: secp256k1::Signing + secp256k1::Verification>(
) -> Result<UnsignedBolt12Invoice, Bolt12SemanticError> {
let expanded_key = ExpandedKey::new([42; 32]);
let entropy_source = Randomness {};
- let nonce = Nonce::from_entropy_source(&entropy_source);
let receive_auth_key = ReceiveAuthKey([41; 32]);
let invoice_request_fields =
@@ -107,7 +105,7 @@ fn build_response<T: secp256k1::Signing + secp256k1::Verification>(
offer_id: OfferId([42; 32]),
invoice_request: invoice_request_fields,
});
- let payee_tlvs = UnauthenticatedReceiveTlvs {
+ let payee_tlvs = ReceiveTlvs {
payment_secret: PaymentSecret([42; 32]),
payment_constraints: PaymentConstraints {
max_cltv_expiry: 1_000_000,
@@ -115,7 +113,6 @@ fn build_response<T: secp256k1::Signing + secp256k1::Verification>(
},
payment_context,
};
- let payee_tlvs = payee_tlvs.authenticate(nonce, &expanded_key);
let intermediate_nodes = [PaymentForwardNode {
tlvs: ForwardTlvs {
short_channel_id: 43,
@@ -125,7 +122,7 @@ fn build_response<T: secp256k1::Signing + secp256k1::Verification>(
fee_base_msat: 1,
},
payment_constraints: PaymentConstraints {
- max_cltv_expiry: payee_tlvs.tlvs().payment_constraints.max_cltv_expiry + 40,
+ max_cltv_expiry: payee_tlvs.payment_constraints.max_cltv_expiry + 40,
htlc_minimum_msat: 100,
},
features: BlindedHopFeatures::empty(),
diff --git a/fuzz/src/refund_deser.rs b/fuzz/src/refund_deser.rs
index 2dea67c..446ac70 100644
--- a/fuzz/src/refund_deser.rs
+++ b/fuzz/src/refund_deser.rs
@@ -12,12 +12,10 @@ use bitcoin::secp256k1::{self, Keypair, PublicKey, Secp256k1, SecretKey};
use core::convert::TryFrom;
use lightning::blinded_path::payment::{
BlindedPaymentPath, Bolt12RefundContext, ForwardTlvs, PaymentConstraints, PaymentContext,
- PaymentForwardNode, PaymentRelay, UnauthenticatedReceiveTlvs,
+ PaymentForwardNode, PaymentRelay, ReceiveTlvs,
};
use lightning::ln::channelmanager::MIN_FINAL_CLTV_EXPIRY_DELTA;
-use lightning::ln::inbound_payment::ExpandedKey;
use lightning::offers::invoice::UnsignedBolt12Invoice;
-use lightning::offers::nonce::Nonce;
use lightning::offers::parse::Bolt12SemanticError;
use lightning::offers::refund::Refund;
use lightning::sign::{EntropySource, ReceiveAuthKey};
@@ -69,12 +67,10 @@ fn privkey(byte: u8) -> SecretKey {
fn build_response<T: secp256k1::Signing + secp256k1::Verification>(
refund: &Refund, signing_pubkey: PublicKey, secp_ctx: &Secp256k1<T>,
) -> Result<UnsignedBolt12Invoice, Bolt12SemanticError> {
- let expanded_key = ExpandedKey::new([42; 32]);
let entropy_source = Randomness {};
let receive_auth_key = ReceiveAuthKey([41; 32]);
- let nonce = Nonce::from_entropy_source(&entropy_source);
let payment_context = PaymentContext::Bolt12Refund(Bolt12RefundContext {});
- let payee_tlvs = UnauthenticatedReceiveTlvs {
+ let payee_tlvs = ReceiveTlvs {
payment_secret: PaymentSecret([42; 32]),
payment_constraints: PaymentConstraints {
max_cltv_expiry: 1_000_000,
@@ -82,7 +78,6 @@ fn build_response<T: secp256k1::Signing + secp256k1::Verification>(
},
payment_context,
};
- let payee_tlvs = payee_tlvs.authenticate(nonce, &expanded_key);
let intermediate_nodes = [PaymentForwardNode {
tlvs: ForwardTlvs {
short_channel_id: 43,
@@ -92,7 +87,7 @@ fn build_response<T: secp256k1::Signing + secp256k1::Verification>(
fee_base_msat: 1,
},
payment_constraints: PaymentConstraints {
- max_cltv_expiry: payee_tlvs.tlvs().payment_constraints.max_cltv_expiry + 40,
+ max_cltv_expiry: payee_tlvs.payment_constraints.max_cltv_expiry + 40,
htlc_minimum_msat: 100,
},
features: BlindedHopFeatures::empty(),
diff --git a/lightning/src/blinded_path/payment.rs b/lightning/src/blinded_path/payment.rs
index ae60aaa..13ade22 100644
--- a/lightning/src/blinded_path/payment.rs
+++ b/lightning/src/blinded_path/payment.rs
@@ -9,8 +9,6 @@
//! Data structures and methods for constructing [`BlindedPaymentPath`]s to send a payment over.
-use bitcoin::hashes::hmac::Hmac;
-use bitcoin::hashes::sha256::Hash as Sha256;
use bitcoin::secp256k1::ecdh::SharedSecret;
use bitcoin::secp256k1::{self, PublicKey, Secp256k1, SecretKey};
@@ -20,8 +18,6 @@ use crate::crypto::streams::ChaChaDualPolyReadAdapter;
use crate::io;
use crate::io::Cursor;
use crate::ln::channel_state::CounterpartyForwardingInfo;
-use crate::ln::channelmanager::Verification;
-use crate::ln::inbound_payment::ExpandedKey;
use crate::ln::msgs::DecodeError;
use crate::ln::onion_utils;
use crate::offers::invoice_request::InvoiceRequestFields;
@@ -137,7 +133,7 @@ impl BlindedPaymentPath {
let blinded_payinfo = compute_payinfo(
intermediate_nodes,
- &payee_tlvs.tlvs,
+ &payee_tlvs,
htlc_maximum_msat,
min_final_cltv_expiry_delta,
)?;
@@ -334,26 +330,8 @@ pub struct TrampolineForwardTlvs {
/// Data to construct a [`BlindedHop`] for receiving a payment. This payload is custom to LDK and
/// may not be valid if received by another lightning implementation.
-///
-/// Can only be constructed by calling [`UnauthenticatedReceiveTlvs::authenticate`].
#[derive(Clone, Debug)]
pub struct ReceiveTlvs {
- /// The TLVs for which the HMAC in `authentication` is derived.
- pub(crate) tlvs: UnauthenticatedReceiveTlvs,
- /// An HMAC of `tlvs` along with a nonce used to construct it.
- pub(crate) authentication: (Hmac<Sha256>, Nonce),
-}
-
-impl ReceiveTlvs {
- /// Returns the underlying TLVs.
- pub fn tlvs(&self) -> &UnauthenticatedReceiveTlvs {
- &self.tlvs
- }
-}
-
-/// An unauthenticated [`ReceiveTlvs`].
-#[derive(Clone, Debug)]
-pub struct UnauthenticatedReceiveTlvs {
/// Used to authenticate the sender of a payment to the receiver and tie MPP HTLCs together.
pub payment_secret: PaymentSecret,
/// Constraints for the receiver of this payment.
@@ -362,17 +340,6 @@ pub struct UnauthenticatedReceiveTlvs {
pub payment_context: PaymentContext,
}
-impl UnauthenticatedReceiveTlvs {
- /// Creates an authenticated [`ReceiveTlvs`], which includes an HMAC and the provide [`Nonce`]
- /// that can be use later to verify it authenticity.
- pub fn authenticate(self, nonce: Nonce, expanded_key: &ExpandedKey) -> ReceiveTlvs {
- ReceiveTlvs {
- authentication: (self.hmac_for_offer_payment(nonce, expanded_key), nonce),
- tlvs: self,
- }
- }
-}
-
/// Data to construct a [`BlindedHop`] for sending a payment over.
///
/// [`BlindedHop`]: crate::blinded_path::BlindedHop
@@ -545,19 +512,12 @@ impl Writeable for TrampolineForwardTlvs {
}
}
+// Note: The `authentication` TLV field was removed in LDK v0.3 following
+// the introduction of `ReceiveAuthKey`-based authentication for inbound
+// `BlindedPaymentPaths`s. Because we do not support receiving to those
+// contexts anymore (they will fail the `ReceiveAuthKey`-based
+// authentication checks), we can reuse that field here.
impl Writeable for ReceiveTlvs {
- fn write<W: Writer>(&self, w: &mut W) -> Result<(), io::Error> {
- encode_tlv_stream!(w, {
- (12, self.tlvs.payment_constraints, required),
- (65536, self.tlvs.payment_secret, required),
- (65537, self.tlvs.payment_context, required),
- (65539, self.authentication, required),
- });
- Ok(())
- }
-}
-
-impl Writeable for UnauthenticatedReceiveTlvs {
fn write<W: Writer>(&self, w: &mut W) -> Result<(), io::Error> {
encode_tlv_stream!(w, {
(12, self.payment_constraints, required),
@@ -592,7 +552,6 @@ impl Readable for BlindedPaymentTlvs {
(14, features, (option, encoding: (BlindedHopFeatures, WithoutLength))),
(65536, payment_secret, option),
(65537, payment_context, option),
- (65539, authentication, option),
});
if let Some(short_channel_id) = scid {
@@ -611,12 +570,9 @@ impl Readable for BlindedPaymentTlvs {
return Err(DecodeError::InvalidValue);
}
Ok(BlindedPaymentTlvs::Receive(ReceiveTlvs {
- tlvs: UnauthenticatedReceiveTlvs {
- payment_secret: payment_secret.ok_or(DecodeError::InvalidValue)?,
- payment_constraints: payment_constraints.0.unwrap(),
- payment_context: payment_context.ok_or(DecodeError::InvalidValue)?,
- },
- authentication: authentication.ok_or(DecodeError::InvalidValue)?,
+ payment_secret: payment_secret.ok_or(DecodeError::InvalidValue)?,
+ payment_constraints: payment_constraints.0.unwrap(),
+ payment_context: payment_context.ok_or(DecodeError::InvalidValue)?,
}))
}
}
@@ -632,7 +588,6 @@ impl Readable for BlindedTrampolineTlvs {
(14, features, (option, encoding: (BlindedHopFeatures, WithoutLength))),
(65536, payment_secret, option),
(65537, payment_context, option),
- (65539, authentication, option),
});
if let Some(next_trampoline) = next_trampoline {
@@ -651,19 +606,15 @@ impl Readable for BlindedTrampolineTlvs {
return Err(DecodeError::InvalidValue);
}
Ok(BlindedTrampolineTlvs::Receive(ReceiveTlvs {
- tlvs: UnauthenticatedReceiveTlvs {
- payment_secret: payment_secret.ok_or(DecodeError::InvalidValue)?,
- payment_constraints: payment_constraints.0.unwrap(),
- payment_context: payment_context.ok_or(DecodeError::InvalidValue)?,
- },
- authentication: authentication.ok_or(DecodeError::InvalidValue)?,
+ payment_secret: payment_secret.ok_or(DecodeError::InvalidValue)?,
+ payment_constraints: payment_constraints.0.unwrap(),
+ payment_context: payment_context.ok_or(DecodeError::InvalidValue)?,
}))
}
}
}
-/// Represents the padding round off size (in bytes) that
-/// is used to pad payment bilnded path's [`BlindedHop`]
+/// Represents the padding round-off size (in bytes) used to pad payment blinded path's [`BlindedHop`].
pub(crate) const PAYMENT_PADDING_ROUND_OFF: usize = 30;
/// Construct blinded payment hops for the given `intermediate_nodes` and payee info.
@@ -743,7 +694,7 @@ where
}
pub(super) fn compute_payinfo(
- intermediate_nodes: &[PaymentForwardNode], payee_tlvs: &UnauthenticatedReceiveTlvs,
+ intermediate_nodes: &[PaymentForwardNode], payee_tlvs: &ReceiveTlvs,
payee_htlc_maximum_msat: u64, min_final_cltv_expiry_delta: u16,
) -> Result<BlindedPayInfo, ()> {
let (aggregated_base_fee, aggregated_prop_fee) =
@@ -866,7 +817,7 @@ impl_writeable_tlv_based!(Bolt12RefundContext, {});
mod tests {
use crate::blinded_path::payment::{
Bolt12RefundContext, ForwardTlvs, PaymentConstraints, PaymentContext, PaymentForwardNode,
- PaymentRelay, UnauthenticatedReceiveTlvs,
+ PaymentRelay, ReceiveTlvs,
};
use crate::ln::functional_test_utils::TEST_FINAL_CLTV;
use crate::types::features::BlindedHopFeatures;
@@ -916,7 +867,7 @@ mod tests {
htlc_maximum_msat: u64::max_value(),
},
];
- let recv_tlvs = UnauthenticatedReceiveTlvs {
+ let recv_tlvs = ReceiveTlvs {
payment_secret: PaymentSecret([0; 32]),
payment_constraints: PaymentConstraints { max_cltv_expiry: 0, htlc_minimum_msat: 1 },
payment_context: PaymentContext::Bolt12Refund(Bolt12RefundContext {}),
@@ -934,7 +885,7 @@ mod tests {
#[test]
fn compute_payinfo_1_hop() {
- let recv_tlvs = UnauthenticatedReceiveTlvs {
+ let recv_tlvs = ReceiveTlvs {
payment_secret: PaymentSecret([0; 32]),
payment_constraints: PaymentConstraints { max_cltv_expiry: 0, htlc_minimum_msat: 1 },
payment_context: PaymentContext::Bolt12Refund(Bolt12RefundContext {}),
@@ -991,7 +942,7 @@ mod tests {
htlc_maximum_msat: u64::max_value(),
},
];
- let recv_tlvs = UnauthenticatedReceiveTlvs {
+ let recv_tlvs = ReceiveTlvs {
payment_secret: PaymentSecret([0; 32]),
payment_constraints: PaymentConstraints { max_cltv_expiry: 0, htlc_minimum_msat: 3 },
payment_context: PaymentContext::Bolt12Refund(Bolt12RefundContext {}),
@@ -1050,7 +1001,7 @@ mod tests {
htlc_maximum_msat: u64::max_value(),
},
];
- let recv_tlvs = UnauthenticatedReceiveTlvs {
+ let recv_tlvs = ReceiveTlvs {
payment_secret: PaymentSecret([0; 32]),
payment_constraints: PaymentConstraints { max_cltv_expiry: 0, htlc_minimum_msat: 1 },
payment_context: PaymentContext::Bolt12Refund(Bolt12RefundContext {}),
@@ -1119,7 +1070,7 @@ mod tests {
htlc_maximum_msat: 10_000,
},
];
- let recv_tlvs = UnauthenticatedReceiveTlvs {
+ let recv_tlvs = ReceiveTlvs {
payment_secret: PaymentSecret([0; 32]),
payment_constraints: PaymentConstraints { max_cltv_expiry: 0, htlc_minimum_msat: 1 },
payment_context: PaymentContext::Bolt12Refund(Bolt12RefundContext {}),
diff --git a/lightning/src/ln/async_payments_tests.rs b/lightning/src/ln/async_payments_tests.rs
index d56670f..78250e6 100644
--- a/lightning/src/ln/async_payments_tests.rs
+++ b/lightning/src/ln/async_payments_tests.rs
@@ -272,7 +272,6 @@ fn pass_async_payments_oms(
fn create_static_invoice_builder<'a>(
recipient: &Node, offer: &'a Offer, offer_nonce: Nonce, relative_expiry: Option<Duration>,
) -> StaticInvoiceBuilder<'a> {
- let entropy = recipient.keys_manager;
let amount_msat = offer.amount().and_then(|amount| match amount {
Amount::Bitcoin { amount_msats } => Some(amount_msats),
Amount::Currency { .. } => None,
@@ -296,7 +295,6 @@ fn create_static_invoice_builder<'a>(
.flow
.create_static_invoice_builder(
&recipient.router,
- entropy,
offer,
offer_nonce,
payment_secret,
@@ -1860,7 +1858,7 @@ fn expired_static_invoice_payment_path() {
.advance_path_by_one(&nodes[1].keys_manager, &nodes[1].node, &secp_ctx)
.unwrap();
match blinded_path.decrypt_intro_payload(&nodes[2].keys_manager).unwrap().0 {
- BlindedPaymentTlvs::Receive(tlvs) => tlvs.tlvs.payment_constraints.max_cltv_expiry,
+ BlindedPaymentTlvs::Receive(tlvs) => tlvs.payment_constraints.max_cltv_expiry,
_ => panic!(),
}
};
@@ -3106,7 +3104,6 @@ fn intercepted_hold_htlc() {
.flow
.test_create_blinded_payment_paths(
&recipient.router,
- recipient.keys_manager,
first_hops,
None,
payment_secret,
diff --git a/lightning/src/ln/blinded_payment_tests.rs b/lightning/src/ln/blinded_payment_tests.rs
index 85be279..3f65b89 100644
--- a/lightning/src/ln/blinded_payment_tests.rs
+++ b/lightning/src/ln/blinded_payment_tests.rs
@@ -15,7 +15,7 @@ use bitcoin::secp256k1::{PublicKey, Scalar, Secp256k1, SecretKey, schnorr};
use bitcoin::secp256k1::ecdh::SharedSecret;
use bitcoin::secp256k1::ecdsa::{RecoverableSignature, Signature};
use crate::blinded_path;
-use crate::blinded_path::payment::{BlindedPaymentPath, Bolt12RefundContext, ForwardTlvs, PaymentConstraints, PaymentContext, PaymentForwardNode, PaymentRelay, UnauthenticatedReceiveTlvs, PAYMENT_PADDING_ROUND_OFF};
+use crate::blinded_path::payment::{BlindedPaymentPath, Bolt12RefundContext, ForwardTlvs, PaymentConstraints, PaymentContext, PaymentForwardNode, PaymentRelay, ReceiveTlvs, PAYMENT_PADDING_ROUND_OFF};
use crate::blinded_path::utils::is_padded;
use crate::events::{Event, HTLCHandlingFailureType, PaymentFailureReason};
use crate::ln::types::ChannelId;
@@ -31,7 +31,6 @@ use crate::ln::onion_payment;
use crate::ln::onion_utils::{self, LocalHTLCFailureReason};
use crate::ln::outbound_payment::{Retry, IDEMPOTENCY_TIMEOUT_TICKS};
use crate::offers::invoice::UnsignedBolt12Invoice;
-use crate::offers::nonce::Nonce;
use crate::prelude::*;
use crate::routing::router::{BlindedTail, Path, Payee, PaymentParameters, RouteHop, RouteParameters, TrampolineHop};
use crate::sign::{NodeSigner, PeerStorageKey, ReceiveAuthKey, Recipient};
@@ -74,7 +73,7 @@ pub fn blinded_payment_path(
});
}
- let payee_tlvs = UnauthenticatedReceiveTlvs {
+ let payee_tlvs = ReceiveTlvs {
payment_secret,
payment_constraints: PaymentConstraints {
max_cltv_expiry: u32::max_value(),
@@ -84,10 +83,7 @@ pub fn blinded_payment_path(
payment_context: PaymentContext::Bolt12Refund(Bolt12RefundContext {}),
};
- let nonce = Nonce([42u8; 16]);
- let expanded_key = keys_manager.get_expanded_key();
let receive_auth_key = keys_manager.get_receive_auth_key();
- let payee_tlvs = payee_tlvs.authenticate(nonce, &expanded_key);
let mut secp_ctx = Secp256k1::new();
BlindedPaymentPath::new(
@@ -162,7 +158,7 @@ fn do_one_hop_blinded_path(success: bool) {
let amt_msat = 5000;
let (payment_preimage, payment_hash, payment_secret) = get_payment_preimage_hash(&nodes[1], Some(amt_msat), None);
- let payee_tlvs = UnauthenticatedReceiveTlvs {
+ let payee_tlvs = ReceiveTlvs {
payment_secret,
payment_constraints: PaymentConstraints {
max_cltv_expiry: u32::max_value(),
@@ -170,10 +166,7 @@ fn do_one_hop_blinded_path(success: bool) {
},
payment_context: PaymentContext::Bolt12Refund(Bolt12RefundContext {}),
};
- let nonce = Nonce([42u8; 16]);
- let expanded_key = chanmon_cfgs[1].keys_manager.get_expanded_key();
let receive_auth_key = chanmon_cfgs[1].keys_manager.get_receive_auth_key();
- let payee_tlvs = payee_tlvs.authenticate(nonce, &expanded_key);
let mut secp_ctx = Secp256k1::new();
let blinded_path = BlindedPaymentPath::new(
@@ -218,7 +211,7 @@ fn mpp_to_one_hop_blinded_path() {
let amt_msat = 15_000_000;
let (payment_preimage, payment_hash, payment_secret) = get_payment_preimage_hash(&nodes[3], Some(amt_msat), None);
- let payee_tlvs = UnauthenticatedReceiveTlvs {
+ let payee_tlvs = ReceiveTlvs {
payment_secret,
payment_constraints: PaymentConstraints {
max_cltv_expiry: u32::max_value(),
@@ -226,10 +219,7 @@ fn mpp_to_one_hop_blinded_path() {
},
payment_context: PaymentContext::Bolt12Refund(Bolt12RefundContext {}),
};
- let nonce = Nonce([42u8; 16]);
- let expanded_key = chanmon_cfgs[3].keys_manager.get_expanded_key();
let receive_auth_key = chanmon_cfgs[3].keys_manager.get_receive_auth_key();
- let payee_tlvs = payee_tlvs.authenticate(nonce, &expanded_key);
let blinded_path = BlindedPaymentPath::new(
&[], nodes[3].node.get_our_node_id(), receive_auth_key,
payee_tlvs, u64::MAX, TEST_FINAL_CLTV as u16,
@@ -1330,7 +1320,7 @@ fn custom_tlvs_to_blinded_path() {
let amt_msat = 5000;
let (payment_preimage, payment_hash, payment_secret) = get_payment_preimage_hash(&nodes[1], Some(amt_msat), None);
- let payee_tlvs = UnauthenticatedReceiveTlvs {
+ let payee_tlvs = ReceiveTlvs {
payment_secret,
payment_constraints: PaymentConstraints {
max_cltv_expiry: u32::max_value(),
@@ -1338,10 +1328,8 @@ fn custom_tlvs_to_blinded_path() {
},
payment_context: PaymentContext::Bolt12Refund(Bolt12RefundContext {}),
};
- let nonce = Nonce([42u8; 16]);
- let expanded_key = chanmon_cfgs[1].keys_manager.get_expanded_key();
let receive_auth_key = chanmon_cfgs[1].keys_manager.get_receive_auth_key();
- let payee_tlvs = payee_tlvs.authenticate(nonce, &expanded_key);
+
let mut secp_ctx = Secp256k1::new();
let blinded_path = BlindedPaymentPath::new(
&[], nodes[1].node.get_our_node_id(), receive_auth_key,
@@ -1386,7 +1374,7 @@ fn fails_receive_tlvs_authentication() {
let amt_msat = 5000;
let (payment_preimage, payment_hash, payment_secret) = get_payment_preimage_hash(&nodes[1], Some(amt_msat), None);
- let payee_tlvs = UnauthenticatedReceiveTlvs {
+ let payee_tlvs = ReceiveTlvs {
payment_secret,
payment_constraints: PaymentConstraints {
max_cltv_expiry: u32::max_value(),
@@ -1394,10 +1382,7 @@ fn fails_receive_tlvs_authentication() {
},
payment_context: PaymentContext::Bolt12Refund(Bolt12RefundContext {}),
};
- let nonce = Nonce([42u8; 16]);
- let expanded_key = chanmon_cfgs[1].keys_manager.get_expanded_key();
let receive_auth_key = chanmon_cfgs[1].keys_manager.get_receive_auth_key();
- let payee_tlvs = payee_tlvs.authenticate(nonce, &expanded_key);
let mut secp_ctx = Secp256k1::new();
let blinded_path = BlindedPaymentPath::new(
@@ -1419,7 +1404,7 @@ fn fails_receive_tlvs_authentication() {
// Swap in a different nonce to force authentication to fail.
let (_, payment_hash, payment_secret) = get_payment_preimage_hash(&nodes[1], Some(amt_msat), None);
- let payee_tlvs = UnauthenticatedReceiveTlvs {
+ let payee_tlvs = ReceiveTlvs {
payment_secret,
payment_constraints: PaymentConstraints {
max_cltv_expiry: u32::max_value(),
@@ -1427,13 +1412,12 @@ fn fails_receive_tlvs_authentication() {
},
payment_context: PaymentContext::Bolt12Refund(Bolt12RefundContext {}),
};
- let nonce = Nonce([43u8; 16]);
- let mut payee_tlvs = payee_tlvs.authenticate(nonce, &expanded_key);
- payee_tlvs.authentication.1 = Nonce([0u8; 16]);
+ // Use a mismatched ReceiveAuthKey to force auth failure:
+ let mismatched_receive_auth_key = ReceiveAuthKey([0u8; 32]);
let mut secp_ctx = Secp256k1::new();
let blinded_path = BlindedPaymentPath::new(
- &[], nodes[1].node.get_our_node_id(), receive_auth_key,
+ &[], nodes[1].node.get_our_node_id(), mismatched_receive_auth_key,
payee_tlvs, u64::MAX, TEST_FINAL_CLTV as u16,
&chanmon_cfgs[1].keys_manager, &secp_ctx
).unwrap();
@@ -2207,7 +2191,7 @@ fn do_test_trampoline_single_hop_receive(success: bool) {
let (payment_preimage, payment_hash, payment_secret) = get_payment_preimage_hash(&nodes[2], Some(amt_msat), None);
// Create a 1-hop blinded path for Carol.
- let payee_tlvs = UnauthenticatedReceiveTlvs {
+ let payee_tlvs = ReceiveTlvs {
payment_secret,
payment_constraints: PaymentConstraints {
max_cltv_expiry: u32::max_value(),
@@ -2215,10 +2199,7 @@ fn do_test_trampoline_single_hop_receive(success: bool) {
},
payment_context: PaymentContext::Bolt12Refund(Bolt12RefundContext {}),
};
- let nonce = Nonce([42u8; 16]);
- let expanded_key = nodes[2].keys_manager.get_expanded_key();
let receive_auth_key = nodes[2].keys_manager.get_receive_auth_key();
- let payee_tlvs = payee_tlvs.authenticate(nonce, &expanded_key);
let blinded_path = BlindedPaymentPath::new(&[], carol_node_id, receive_auth_key, payee_tlvs, u64::MAX, 0, nodes[2].keys_manager, &secp_ctx).unwrap();
let route = Route {
diff --git a/lightning/src/ln/channelmanager.rs b/lightning/src/ln/channelmanager.rs
index 6449205..271ecaa 100644
--- a/lightning/src/ln/channelmanager.rs
+++ b/lightning/src/ln/channelmanager.rs
@@ -35,9 +35,7 @@ use bitcoin::{secp256k1, Sequence, SignedAmount};
use crate::blinded_path::message::{
AsyncPaymentsContext, BlindedMessagePath, MessageForwardNode, OffersContext,
};
-use crate::blinded_path::payment::{
- AsyncBolt12OfferContext, Bolt12OfferContext, PaymentContext, UnauthenticatedReceiveTlvs,
-};
+use crate::blinded_path::payment::{AsyncBolt12OfferContext, Bolt12OfferContext, PaymentContext};
use crate::blinded_path::NodeIdLookUp;
use crate::chain;
use crate::chain::chaininterface::{
@@ -100,7 +98,6 @@ use crate::offers::nonce::Nonce;
use crate::offers::offer::{Offer, OfferFromHrn};
use crate::offers::parse::Bolt12SemanticError;
use crate::offers::refund::Refund;
-use crate::offers::signer;
use crate::offers::static_invoice::StaticInvoice;
use crate::onion_message::async_payments::{
AsyncPaymentsMessage, AsyncPaymentsMessageHandler, HeldHtlcAvailable, OfferPaths,
@@ -574,34 +571,6 @@ impl Ord for ClaimableHTLC {
}
}
-/// A trait defining behavior for creating and verifing the HMAC for authenticating a given data.
-pub trait Verification {
- /// Constructs an HMAC to include in [`OffersContext`] for the data along with the given
- /// [`Nonce`].
- fn hmac_for_offer_payment(
- &self, nonce: Nonce, expanded_key: &inbound_payment::ExpandedKey,
- ) -> Hmac<Sha256>;
-
- /// Authenticates the data using an HMAC and a [`Nonce`] taken from an [`OffersContext`].
- fn verify_for_offer_payment(
- &self, hmac: Hmac<Sha256>, nonce: Nonce, expanded_key: &inbound_payment::ExpandedKey,
- ) -> Result<(), ()>;
-}
-
-impl Verification for UnauthenticatedReceiveTlvs {
- fn hmac_for_offer_payment(
- &self, nonce: Nonce, expanded_key: &inbound_payment::ExpandedKey,
- ) -> Hmac<Sha256> {
- signer::hmac_for_payment_tlvs(self, nonce, expanded_key)
- }
-
- fn verify_for_offer_payment(
- &self, hmac: Hmac<Sha256>, nonce: Nonce, expanded_key: &inbound_payment::ExpandedKey,
- ) -> Result<(), ()> {
- signer::verify_payment_tlvs(self, hmac, nonce, expanded_key)
- }
-}
-
/// A user-provided identifier in [`ChannelManager::send_payment`] used to uniquely identify
/// a payment and ensure idempotency in LDK.
///
@@ -5642,12 +5611,10 @@ where
fn check_refresh_async_receive_offer_cache(&self, timer_tick_occurred: bool) {
let peers = self.get_peers_for_blinded_path();
let channels = self.list_usable_channels();
- let entropy = &*self.entropy_source;
let router = &*self.router;
let refresh_res = self.flow.check_refresh_async_receive_offer_cache(
peers,
channels,
- entropy,
router,
timer_tick_occurred,
);
@@ -13364,11 +13331,8 @@ where
&self, amount_msats: Option<u64>, payment_secret: PaymentSecret,
payment_context: PaymentContext, relative_expiry_seconds: u32,
) -> Result<Vec<BlindedPaymentPath>, ()> {
- let entropy = &*self.entropy_source;
-
self.flow.test_create_blinded_payment_paths(
&self.router,
- entropy,
self.list_usable_channels(),
amount_msats,
payment_secret,
@@ -15272,7 +15236,6 @@ where
InvoiceRequestVerifiedFromOffer::DerivedKeys(request) => {
let result = self.flow.create_invoice_builder_from_invoice_request_with_keys(
&self.router,
- &*self.entropy_source,
&request,
self.list_usable_channels(),
get_payment_info,
@@ -15297,7 +15260,6 @@ where
InvoiceRequestVerifiedFromOffer::ExplicitKeys(request) => {
let result = self.flow.create_invoice_builder_from_invoice_request_without_keys(
&self.router,
- &*self.entropy_source,
&request,
self.list_usable_channels(),
get_payment_info,
diff --git a/lightning/src/ln/max_payment_path_len_tests.rs b/lightning/src/ln/max_payment_path_len_tests.rs
index 366f54b..f67ad44 100644
--- a/lightning/src/ln/max_payment_path_len_tests.rs
+++ b/lightning/src/ln/max_payment_path_len_tests.rs
@@ -12,7 +12,7 @@
use crate::blinded_path::payment::{
BlindedPayInfo, BlindedPaymentPath, Bolt12RefundContext, PaymentConstraints, PaymentContext,
- UnauthenticatedReceiveTlvs,
+ ReceiveTlvs,
};
use crate::blinded_path::BlindedHop;
use crate::events::Event;
@@ -24,7 +24,6 @@ use crate::ln::msgs::{BaseMessageHandler, OnionMessageHandler};
use crate::ln::onion_utils;
use crate::ln::onion_utils::MIN_FINAL_VALUE_ESTIMATE_WITH_OVERPAY;
use crate::ln::outbound_payment::{RecipientOnionFields, Retry, RetryableSendFailure};
-use crate::offers::nonce::Nonce;
use crate::prelude::*;
use crate::routing::router::{
PaymentParameters, RouteParameters, DEFAULT_MAX_TOTAL_CLTV_EXPIRY_DELTA,
@@ -213,7 +212,7 @@ fn one_hop_blinded_path_with_custom_tlv() {
let amt_msat = 100_000;
let (payment_preimage, payment_hash, payment_secret) =
get_payment_preimage_hash(&nodes[2], Some(amt_msat), None);
- let payee_tlvs = UnauthenticatedReceiveTlvs {
+ let payee_tlvs = ReceiveTlvs {
payment_secret,
payment_constraints: PaymentConstraints {
max_cltv_expiry: u32::max_value(),
@@ -221,10 +220,7 @@ fn one_hop_blinded_path_with_custom_tlv() {
},
payment_context: PaymentContext::Bolt12Refund(Bolt12RefundContext {}),
};
- let nonce = Nonce([42u8; 16]);
- let expanded_key = chanmon_cfgs[2].keys_manager.get_expanded_key();
let receive_auth_key = chanmon_cfgs[2].keys_manager.get_receive_auth_key();
- let payee_tlvs = payee_tlvs.authenticate(nonce, &expanded_key);
let mut secp_ctx = Secp256k1::new();
let blinded_path = BlindedPaymentPath::new(
&[],
diff --git a/lightning/src/ln/msgs.rs b/lightning/src/ln/msgs.rs
index 4462f77..67bf764 100644
--- a/lightning/src/ln/msgs.rs
+++ b/lightning/src/ln/msgs.rs
@@ -32,11 +32,8 @@ use bitcoin::secp256k1::PublicKey;
use bitcoin::{secp256k1, Transaction, Witness};
use crate::blinded_path::message::BlindedMessagePath;
-use crate::blinded_path::payment::{
- BlindedPaymentTlvs, ForwardTlvs, ReceiveTlvs, UnauthenticatedReceiveTlvs,
-};
+use crate::blinded_path::payment::{BlindedPaymentTlvs, ForwardTlvs, ReceiveTlvs};
use crate::blinded_path::payment::{BlindedTrampolineTlvs, TrampolineForwardTlvs};
-use crate::ln::channelmanager::Verification;
use crate::ln::onion_utils;
use crate::ln::types::ChannelId;
use crate::offers::invoice_request::InvoiceRequest;
@@ -3695,17 +3692,9 @@ where
return Err(DecodeError::InvalidValue);
}
- let ReceiveTlvs { tlvs, authentication: (hmac, nonce) } = receive_tlvs;
- let expanded_key = node_signer.get_expanded_key();
- if tlvs.verify_for_offer_payment(hmac, nonce, &expanded_key).is_err() {
- return Err(DecodeError::InvalidValue);
- }
+ let ReceiveTlvs { payment_secret, payment_constraints, payment_context } =
+ receive_tlvs;
- let UnauthenticatedReceiveTlvs {
- payment_secret,
- payment_constraints,
- payment_context,
- } = tlvs;
if total_msat.unwrap_or(0) > MAX_VALUE_MSAT {
return Err(DecodeError::InvalidValue);
}
@@ -3855,17 +3844,9 @@ where
return Err(DecodeError::InvalidValue);
}
- let ReceiveTlvs { tlvs, authentication: (hmac, nonce) } = receive_tlvs;
- let expanded_key = node_signer.get_expanded_key();
- if tlvs.verify_for_offer_payment(hmac, nonce, &expanded_key).is_err() {
- return Err(DecodeError::InvalidValue);
- }
+ let ReceiveTlvs { payment_secret, payment_constraints, payment_context } =
+ receive_tlvs;
- let UnauthenticatedReceiveTlvs {
- payment_secret,
- payment_constraints,
- payment_context,
- } = tlvs;
if total_msat.unwrap_or(0) > MAX_VALUE_MSAT {
return Err(DecodeError::InvalidValue);
}
diff --git a/lightning/src/offers/flow.rs b/lightning/src/offers/flow.rs
index 6415d4b..94a4534 100644
--- a/lightning/src/offers/flow.rs
+++ b/lightning/src/offers/flow.rs
@@ -23,7 +23,7 @@ use crate::blinded_path::message::{
};
use crate::blinded_path::payment::{
AsyncBolt12OfferContext, BlindedPaymentPath, Bolt12OfferContext, Bolt12RefundContext,
- PaymentConstraints, PaymentContext, UnauthenticatedReceiveTlvs,
+ PaymentConstraints, PaymentContext, ReceiveTlvs,
};
use crate::chain::channelmonitor::LATENCY_GRACE_PERIOD_BLOCKS;
@@ -317,17 +317,14 @@ where
/// Creates multi-hop blinded payment paths for the given `amount_msats` by delegating to
/// [`Router::create_blinded_payment_paths`].
- fn create_blinded_payment_paths<ES: Deref, R: Deref>(
- &self, router: &R, entropy_source: ES, usable_channels: Vec<ChannelDetails>,
- amount_msats: Option<u64>, payment_secret: PaymentSecret, payment_context: PaymentContext,
+ fn create_blinded_payment_paths<R: Deref>(
+ &self, router: &R, usable_channels: Vec<ChannelDetails>, amount_msats: Option<u64>,
+ payment_secret: PaymentSecret, payment_context: PaymentContext,
relative_expiry_seconds: u32,
) -> Result<Vec<BlindedPaymentPath>, ()>
where
- ES::Target: EntropySource,
R::Target: Router,
{
- let expanded_key = &self.inbound_payment_key;
- let entropy = &*entropy_source;
let secp_ctx = &self.secp_ctx;
let receive_auth_key = self.receive_auth_key;
@@ -340,13 +337,11 @@ where
.saturating_add(LATENCY_GRACE_PERIOD_BLOCKS)
.saturating_add(self.best_block.read().unwrap().height);
- let payee_tlvs = UnauthenticatedReceiveTlvs {
+ let payee_tlvs = ReceiveTlvs {
payment_secret,
payment_constraints: PaymentConstraints { max_cltv_expiry, htlc_minimum_msat: 1 },
payment_context,
};
- let nonce = Nonce::from_entropy_source(entropy);
- let payee_tlvs = payee_tlvs.authenticate(nonce, expanded_key);
router.create_blinded_payment_paths(
payee_node_id,
@@ -361,18 +356,16 @@ where
#[cfg(test)]
/// Creates multi-hop blinded payment paths for the given `amount_msats` by delegating to
/// [`Router::create_blinded_payment_paths`].
- pub(crate) fn test_create_blinded_payment_paths<ES: Deref, R: Deref>(
- &self, router: &R, entropy_source: ES, usable_channels: Vec<ChannelDetails>,
- amount_msats: Option<u64>, payment_secret: PaymentSecret, payment_context: PaymentContext,
+ pub(crate) fn test_create_blinded_payment_paths<R: Deref>(
+ &self, router: &R, usable_channels: Vec<ChannelDetails>, amount_msats: Option<u64>,
+ payment_secret: PaymentSecret, payment_context: PaymentContext,
relative_expiry_seconds: u32,
) -> Result<Vec<BlindedPaymentPath>, ()>
where
- ES::Target: EntropySource,
R::Target: Router,
{
self.create_blinded_payment_paths(
router,
- entropy_source,
usable_channels,
amount_msats,
payment_secret,
@@ -828,17 +821,15 @@ where
/// created via [`Self::create_async_receive_offer_builder`].
///
/// This is not exported to bindings users as builder patterns don't map outside of move semantics.
- pub fn create_static_invoice_builder<'a, ES: Deref, R: Deref>(
- &self, router: &R, entropy_source: ES, offer: &'a Offer, offer_nonce: Nonce,
- payment_secret: PaymentSecret, relative_expiry_secs: u32,
- usable_channels: Vec<ChannelDetails>, peers: Vec<MessageForwardNode>,
+ pub fn create_static_invoice_builder<'a, R: Deref>(
+ &self, router: &R, offer: &'a Offer, offer_nonce: Nonce, payment_secret: PaymentSecret,
+ relative_expiry_secs: u32, usable_channels: Vec<ChannelDetails>,
+ peers: Vec<MessageForwardNode>,
) -> Result<StaticInvoiceBuilder<'a>, Bolt12SemanticError>
where
- ES::Target: EntropySource,
R::Target: Router,
{
let expanded_key = &self.inbound_payment_key;
- let entropy = &*entropy_source;
let secp_ctx = &self.secp_ctx;
let payment_context =
@@ -854,7 +845,6 @@ where
let payment_paths = self
.create_blinded_payment_paths(
router,
- entropy,
usable_channels,
amount_msat,
payment_secret,
@@ -927,7 +917,6 @@ where
let payment_paths = self
.create_blinded_payment_paths(
router,
- entropy,
usable_channels,
Some(amount_msats),
payment_secret,
@@ -972,18 +961,14 @@ where
/// Returns a [`Bolt12SemanticError`] if:
/// - Valid blinded payment paths could not be generated for the [`Bolt12Invoice`].
/// - The [`InvoiceBuilder`] could not be created from the [`InvoiceRequest`].
- pub fn create_invoice_builder_from_invoice_request_with_keys<'a, ES: Deref, R: Deref, F>(
- &self, router: &R, entropy_source: ES,
- invoice_request: &'a VerifiedInvoiceRequest<DerivedSigningPubkey>,
+ pub fn create_invoice_builder_from_invoice_request_with_keys<'a, R: Deref, F>(
+ &self, router: &R, invoice_request: &'a VerifiedInvoiceRequest<DerivedSigningPubkey>,
usable_channels: Vec<ChannelDetails>, get_payment_info: F,
) -> Result<(InvoiceBuilder<'a, DerivedSigningPubkey>, MessageContext), Bolt12SemanticError>
where
- ES::Target: EntropySource,
-
R::Target: Router,
F: Fn(u64, u32) -> Result<(PaymentHash, PaymentSecret), Bolt12SemanticError>,
{
- let entropy = &*entropy_source;
let relative_expiry = DEFAULT_RELATIVE_EXPIRY.as_secs() as u32;
let amount_msats =
@@ -999,7 +984,6 @@ where
let payment_paths = self
.create_blinded_payment_paths(
router,
- entropy,
usable_channels,
Some(amount_msats),
payment_secret,
@@ -1037,17 +1021,14 @@ where
/// Returns a [`Bolt12SemanticError`] if:
/// - Valid blinded payment paths could not be generated for the [`Bolt12Invoice`].
/// - The [`InvoiceBuilder`] could not be created from the [`InvoiceRequest`].
- pub fn create_invoice_builder_from_invoice_request_without_keys<'a, ES: Deref, R: Deref, F>(
- &self, router: &R, entropy_source: ES,
- invoice_request: &'a VerifiedInvoiceRequest<ExplicitSigningPubkey>,
+ pub fn create_invoice_builder_from_invoice_request_without_keys<'a, R: Deref, F>(
+ &self, router: &R, invoice_request: &'a VerifiedInvoiceRequest<ExplicitSigningPubkey>,
usable_channels: Vec<ChannelDetails>, get_payment_info: F,
) -> Result<(InvoiceBuilder<'a, ExplicitSigningPubkey>, MessageContext), Bolt12SemanticError>
where
- ES::Target: EntropySource,
R::Target: Router,
F: Fn(u64, u32) -> Result<(PaymentHash, PaymentSecret), Bolt12SemanticError>,
{
- let entropy = &*entropy_source;
let relative_expiry = DEFAULT_RELATIVE_EXPIRY.as_secs() as u32;
let amount_msats =
@@ -1063,7 +1044,6 @@ where
let payment_paths = self
.create_blinded_payment_paths(
router,
- entropy,
usable_channels,
Some(amount_msats),
payment_secret,
@@ -1394,12 +1374,11 @@ where
/// the cache can self-regulate the number of messages sent out.
///
/// Errors if we failed to create blinded reply paths when sending an [`OfferPathsRequest`] message.
- pub fn check_refresh_async_receive_offer_cache<ES: Deref, R: Deref>(
- &self, peers: Vec<MessageForwardNode>, usable_channels: Vec<ChannelDetails>, entropy: ES,
- router: R, timer_tick_occurred: bool,
+ pub fn check_refresh_async_receive_offer_cache<R: Deref>(
+ &self, peers: Vec<MessageForwardNode>, usable_channels: Vec<ChannelDetails>, router: R,
+ timer_tick_occurred: bool,
) -> Result<(), ()>
where
- ES::Target: EntropySource,
R::Target: Router,
{
// Terminate early if this node does not intend to receive async payments.
@@ -1413,7 +1392,7 @@ where
self.check_refresh_async_offers(peers.clone(), timer_tick_occurred)?;
if timer_tick_occurred {
- self.check_refresh_static_invoices(peers, usable_channels, entropy, router);
+ self.check_refresh_static_invoices(peers, usable_channels, router);
}
Ok(())
@@ -1470,11 +1449,9 @@ where
/// Enqueue onion messages that will used to request invoice refresh from the static invoice
/// server, based on the offers provided by the cache.
- fn check_refresh_static_invoices<ES: Deref, R: Deref>(
- &self, peers: Vec<MessageForwardNode>, usable_channels: Vec<ChannelDetails>, entropy: ES,
- router: R,
+ fn check_refresh_static_invoices<R: Deref>(
+ &self, peers: Vec<MessageForwardNode>, usable_channels: Vec<ChannelDetails>, router: R,
) where
- ES::Target: EntropySource,
R::Target: Router,
{
let mut serve_static_invoice_msgs = Vec::new();
@@ -1489,7 +1466,6 @@ where
offer_nonce,
peers.clone(),
usable_channels.clone(),
- &*entropy,
&*router,
) {
Ok((invoice, path)) => (invoice, path),
@@ -1655,7 +1631,6 @@ where
offer_nonce,
peers,
usable_channels,
- &*entropy,
router,
) {
Ok(res) => res,
@@ -1690,12 +1665,11 @@ where
/// Creates a [`StaticInvoice`] and a blinded path for the server to forward invoice requests from
/// payers to our node.
- fn create_static_invoice_for_server<ES: Deref, R: Deref>(
+ fn create_static_invoice_for_server<R: Deref>(
&self, offer: &Offer, offer_nonce: Nonce, peers: Vec<MessageForwardNode>,
- usable_channels: Vec<ChannelDetails>, entropy: ES, router: R,
+ usable_channels: Vec<ChannelDetails>, router: R,
) -> Result<(StaticInvoice, BlindedMessagePath), ()>
where
- ES::Target: EntropySource,
R::Target: Router,
{
let expanded_key = &self.inbound_payment_key;
@@ -1722,7 +1696,6 @@ where
let invoice = self
.create_static_invoice_builder(
&router,
- &*entropy,
&offer,
offer_nonce,
payment_secret,
diff --git a/lightning/src/offers/signer.rs b/lightning/src/offers/signer.rs
index 645949f..e51a120 100644
--- a/lightning/src/offers/signer.rs
+++ b/lightning/src/offers/signer.rs
@@ -9,7 +9,6 @@
//! Utilities for signing offer messages and verifying metadata.
-use crate::blinded_path::payment::UnauthenticatedReceiveTlvs;
use crate::ln::channelmanager::PaymentId;
use crate::ln::inbound_payment::{ExpandedKey, IV_LEN};
use crate::offers::merkle::TlvRecord;
@@ -41,16 +40,14 @@ const WITH_ENCRYPTED_PAYMENT_ID_HMAC_INPUT: &[u8; 16] = &[4; 16];
// The following `HMAC_INPUT` constants were previously used for authenticating fields in
// `OffersContext`, but were removed in LDK v0.2 with the introduction of `ReceiveAuthKey`-based
// authentication.
-// Their corresponding values (`[5; 16]` and `[7; 16]`) are now reserved and must not
+// Their corresponding values (`[5; 16]`, `[7; 16]` and `[8; 16]`) are now reserved and must not
// be reused to ensure type confusion attacks are impossible.
//
// Reserved HMAC_INPUT values — do not reuse:
//
// const OFFER_PAYMENT_ID_HMAC_INPUT: &[u8; 16] = &[5; 16];
// const PAYMENT_HASH_HMAC_INPUT: &[u8; 16] = &[7; 16];
-
-// HMAC input for `ReceiveTlvs`. The HMAC is used in `blinded_path::payment::PaymentContext`.
-const PAYMENT_TLVS_HMAC_INPUT: &[u8; 16] = &[8; 16];
+// const PAYMENT_TLVS_HMAC_INPUT: &[u8; 16] = &[8; 16];
/// Message metadata which possibly is derived from [`MetadataMaterial`] such that it can be
/// verified.
@@ -449,27 +446,3 @@ fn hmac_for_message<'a>(
Ok(hmac)
}
-
-pub(crate) fn hmac_for_payment_tlvs(
- receive_tlvs: &UnauthenticatedReceiveTlvs, nonce: Nonce, expanded_key: &ExpandedKey,
-) -> Hmac<Sha256> {
- const IV_BYTES: &[u8; IV_LEN] = b"LDK Payment TLVs";
- let mut hmac = expanded_key.hmac_for_offer();
- hmac.input(IV_BYTES);
- hmac.input(&nonce.0);
- hmac.input(PAYMENT_TLVS_HMAC_INPUT);
- receive_tlvs.write(&mut hmac).unwrap();
-
- Hmac::from_engine(hmac)
-}
-
-pub(crate) fn verify_payment_tlvs(
- receive_tlvs: &UnauthenticatedReceiveTlvs, hmac: Hmac<Sha256>, nonce: Nonce,
- expanded_key: &ExpandedKey,
-) -> Result<(), ()> {
- if hmac_for_payment_tlvs(receive_tlvs, nonce, expanded_key) == hmac {
- Ok(())
- } else {
- Err(())
- }
-}
diff --git a/lightning/src/routing/router.rs b/lightning/src/routing/router.rs
index c032868..e969237 100644
--- a/lightning/src/routing/router.rs
+++ b/lightning/src/routing/router.rs
@@ -180,7 +180,9 @@ where
let cltv_expiry_delta = payment_relay.cltv_expiry_delta as u32;
let payment_constraints = PaymentConstraints {
- max_cltv_expiry: tlvs.tlvs().payment_constraints.max_cltv_expiry + cltv_expiry_delta,
+ max_cltv_expiry: tlvs.payment_constraints
+ .max_cltv_expiry
+ .saturating_add(cltv_expiry_delta),
htlc_minimum_msat: details.inbound_htlc_minimum_msat.unwrap_or(0),
};
Some(PaymentForwardNode {
Why this scored 34/100
Community notes
Notes can correct, qualify, or add evidence to the AI analysis. Every note shown here has been validated by a human moderator.
The AI analysis stands alone for now. Submit a note if you can add evidence or important context.