@@ -108,7 +108,7 @@ use crate::onion_message::async_payments::{
108108 AsyncPaymentsMessage, AsyncPaymentsMessageHandler, HeldHtlcAvailable, OfferPaths,
109109 OfferPathsRequest, ReleaseHeldHtlc, ServeStaticInvoice, StaticInvoicePersisted,
110110};
111- use crate::onion_message::dns_resolution::HumanReadableName;
111+ use crate::onion_message::dns_resolution::{DNSSECProof, HumanReadableName} ;
112112use crate::onion_message::messenger::{
113113 MessageRouter, MessageSendInstructions, Responder, ResponseInstruction,
114114};
@@ -836,6 +836,10 @@ mod fuzzy_channelmanager {
836836 /// we can provide proof-of-payment details in payment claim events even after a restart
837837 /// with a stale ChannelManager state.
838838 bolt12_invoice: Option<PaidBolt12Invoice>,
839+ /// The DNSSEC proof for BIP 353 proof of payment, if this payment originated from
840+ /// a Human Readable Name resolution. Stored here to ensure we can provide it in
841+ /// payment claim events even after a restart with a stale ChannelManager state.
842+ dnssec_proof: Option<DNSSECProof>,
839843 },
840844 }
841845
@@ -909,13 +913,15 @@ impl core::hash::Hash for HTLCSource {
909913 payment_id,
910914 first_hop_htlc_msat,
911915 bolt12_invoice,
916+ dnssec_proof,
912917 } => {
913918 1u8.hash(hasher);
914919 path.hash(hasher);
915920 session_priv[..].hash(hasher);
916921 payment_id.hash(hasher);
917922 first_hop_htlc_msat.hash(hasher);
918923 bolt12_invoice.hash(hasher);
924+ dnssec_proof.hash(hasher);
919925 },
920926 HTLCSource::TrampolineForward {
921927 previous_hop_data,
@@ -943,6 +949,7 @@ impl HTLCSource {
943949 first_hop_htlc_msat: 0,
944950 payment_id: PaymentId([2; 32]),
945951 bolt12_invoice: None,
952+ dnssec_proof: None,
946953 }
947954 }
948955
@@ -5394,6 +5401,7 @@ impl<
53945401 keysend_preimage,
53955402 invoice_request: None,
53965403 bolt12_invoice: None,
5404+ dnssec_proof: None,
53975405 session_priv_bytes,
53985406 hold_htlc_at_next_hop: false,
53995407 })
@@ -5409,6 +5417,7 @@ impl<
54095417 keysend_preimage,
54105418 invoice_request,
54115419 bolt12_invoice,
5420+ dnssec_proof,
54125421 session_priv_bytes,
54135422 hold_htlc_at_next_hop,
54145423 } = args;
@@ -5485,6 +5494,7 @@ impl<
54855494 first_hop_htlc_msat: htlc_msat,
54865495 payment_id,
54875496 bolt12_invoice: bolt12_invoice.cloned(),
5497+ dnssec_proof: dnssec_proof.cloned(),
54885498 };
54895499 let send_res = chan.send_htlc_and_commit(
54905500 htlc_msat,
@@ -9952,7 +9962,7 @@ This indicates a bug inside LDK. Please report this error at https://github.com/
99529962 let htlc_id = SentHTLCId::from_source(&source);
99539963 match source {
99549964 HTLCSource::OutboundRoute {
9955- session_priv, payment_id, path, bolt12_invoice, ..
9965+ session_priv, payment_id, path, bolt12_invoice, dnssec_proof, ..
99569966 } => {
99579967 debug_assert!(!startup_replay,
99589968 "We don't support claim_htlc claims during startup - monitors may not be available yet");
@@ -9984,6 +9994,7 @@ This indicates a bug inside LDK. Please report this error at https://github.com/
99849994 payment_id,
99859995 payment_preimage,
99869996 bolt12_invoice,
9997+ dnssec_proof,
99879998 session_priv,
99889999 path,
998910000 from_onchain,
@@ -17386,6 +17397,7 @@ impl<
1738617397
1738717398 #[rustfmt::skip]
1738817399 fn handle_dnssec_proof(&self, message: DNSSECProof, context: DNSResolverContext) {
17400+ let proof = message.clone();
1738917401 let offer_opt = self.flow.hrn_resolver.handle_dnssec_proof_for_offer(message, context);
1739017402 #[cfg_attr(not(feature = "_test_utils"), allow(unused_mut))]
1739117403 if let Some((completed_requests, mut offer)) = offer_opt {
@@ -17404,7 +17416,12 @@ impl<
1740417416 .received_offer(payment_id, Some(retryable_invoice_request))
1740517417 .map_err(|_| Bolt12SemanticError::DuplicatePaymentId)
1740617418 });
17407- if offer_pay_res.is_err() {
17419+ if offer_pay_res.is_ok() {
17420+ // Store the DNSSEC proof for BIP 353 proof of payment. The proof is
17421+ // now attached to the AwaitingInvoice state and will be carried through
17422+ // to the PaymentSent event.
17423+ self.pending_outbound_payments.set_dnssec_proof(payment_id, proof.clone());
17424+ } else {
1740817425 // The offer we tried to pay is the canonical current offer for the name we
1740917426 // wanted to pay. If we can't pay it, there's no way to recover so fail the
1741017427 // payment.
@@ -17767,6 +17784,7 @@ impl Readable for HTLCSource {
1776717784 let mut payment_params: Option<PaymentParameters> = None;
1776817785 let mut blinded_tail: Option<BlindedTail> = None;
1776917786 let mut bolt12_invoice: Option<PaidBolt12Invoice> = None;
17787+ let mut dnssec_proof: Option<DNSSECProof> = None;
1777017788 read_tlv_fields!(reader, {
1777117789 (0, session_priv, required),
1777217790 (1, payment_id, option),
@@ -17775,6 +17793,7 @@ impl Readable for HTLCSource {
1777517793 (5, payment_params, (option: ReadableArgs, 0)),
1777617794 (6, blinded_tail, option),
1777717795 (7, bolt12_invoice, option),
17796+ (9, dnssec_proof, option),
1777817797 });
1777917798 if payment_id.is_none() {
1778017799 // For backwards compat, if there was no payment_id written, use the session_priv bytes
@@ -17798,6 +17817,7 @@ impl Readable for HTLCSource {
1779817817 path,
1779917818 payment_id: payment_id.unwrap(),
1780017819 bolt12_invoice,
17820+ dnssec_proof,
1780117821 })
1780217822 }
1780317823 1 => Ok(HTLCSource::PreviousHopData(Readable::read(reader)?)),
@@ -17817,6 +17837,7 @@ impl Writeable for HTLCSource {
1781717837 ref path,
1781817838 payment_id,
1781917839 bolt12_invoice,
17840+ dnssec_proof,
1782017841 } => {
1782117842 0u8.write(writer)?;
1782217843 let payment_id_opt = Some(payment_id);
@@ -17829,6 +17850,7 @@ impl Writeable for HTLCSource {
1782917850 (5, None::<PaymentParameters>, option), // payment_params in LDK versions prior to 0.0.115
1783017851 (6, path.blinded_tail, option),
1783117852 (7, bolt12_invoice, option),
17853+ (9, dnssec_proof, option),
1783217854 });
1783317855 },
1783417856 HTLCSource::PreviousHopData(ref field) => {
@@ -19687,6 +19709,7 @@ impl<
1968719709 session_priv,
1968819710 path,
1968919711 bolt12_invoice,
19712+ dnssec_proof,
1969019713 ..
1969119714 } => {
1969219715 if let Some(preimage) = preimage_opt {
@@ -19704,6 +19727,7 @@ impl<
1970419727 payment_id,
1970519728 preimage,
1970619729 bolt12_invoice,
19730+ dnssec_proof,
1970719731 session_priv,
1970819732 path,
1970919733 true,
0 commit comments