]> git.bitcoin.ninja Git - rust-lightning/commitdiff
Authenticate InvoiceRequest using OfferContext
authorJeffrey Czyz <jkczyz@gmail.com>
Tue, 2 Jul 2024 21:55:59 +0000 (16:55 -0500)
committerJeffrey Czyz <jkczyz@gmail.com>
Mon, 22 Jul 2024 16:34:03 +0000 (11:34 -0500)
When an InvoiceRequest is handled with an OfferContext, use the
containing nonce to verify that it is for a valid Offer. Otherwise, fall
back to using Offer::metadata, which also contains the nonce. The latter
is useful for supporting offers without blinded paths or those created
prior to including an OffersContext in their blinded paths.

lightning/src/ln/channelmanager.rs
lightning/src/offers/invoice_request.rs

index 9f05877b95129b422be39e34d0664ac94d2f9acc..80faffc0d7d41a3420224822b0707a98074014f8 100644 (file)
@@ -10703,19 +10703,35 @@ where
                                        Some(responder) => responder,
                                        None => return ResponseInstruction::NoResponse,
                                };
+
+                               let nonce = match context {
+                                       OffersContext::Unknown {} if invoice_request.metadata().is_some() => None,
+                                       OffersContext::InvoiceRequest { nonce } => Some(nonce),
+                                       _ => return ResponseInstruction::NoResponse,
+                               };
+
+                               let invoice_request = match nonce {
+                                       Some(nonce) => match invoice_request.verify_using_recipient_data(
+                                               nonce, expanded_key, secp_ctx,
+                                       ) {
+                                               Ok(invoice_request) => invoice_request,
+                                               Err(()) => return ResponseInstruction::NoResponse,
+                                       },
+                                       None => match invoice_request.verify(expanded_key, secp_ctx) {
+                                               Ok(invoice_request) => invoice_request,
+                                               Err(()) => {
+                                                       let error = Bolt12SemanticError::InvalidMetadata;
+                                                       return responder.respond(OffersMessage::InvoiceError(error.into()));
+                                               },
+                                       },
+                               };
+
                                let amount_msats = match InvoiceBuilder::<DerivedSigningPubkey>::amount_msats(
-                                       &invoice_request
+                                       &invoice_request.inner
                                ) {
                                        Ok(amount_msats) => amount_msats,
                                        Err(error) => return responder.respond(OffersMessage::InvoiceError(error.into())),
                                };
-                               let invoice_request = match invoice_request.verify(expanded_key, secp_ctx) {
-                                       Ok(invoice_request) => invoice_request,
-                                       Err(()) => {
-                                               let error = Bolt12SemanticError::InvalidMetadata;
-                                               return responder.respond(OffersMessage::InvoiceError(error.into()));
-                                       },
-                               };
 
                                let relative_expiry = DEFAULT_RELATIVE_EXPIRY.as_secs() as u32;
                                let (payment_hash, payment_secret) = match self.create_inbound_payment(
index 8c09721f28203793cf512f88c23a1541a718c5b4..6011ca79b22f4987c484076c2568317c557525ca 100644 (file)
@@ -613,7 +613,7 @@ pub struct VerifiedInvoiceRequest {
        pub offer_id: OfferId,
 
        /// The verified request.
-       inner: InvoiceRequest,
+       pub(crate) inner: InvoiceRequest,
 
        /// Keys used for signing a [`Bolt12Invoice`] if they can be derived.
        ///