Skip to content

Commit db9c76a

Browse files
committed
2/3 Use MessageSendInstructions instead of PendingOnionMessage
Now that the `MessageRouter` can `create_blinded_paths` forcing callers of the `OnionMessenger` to provide it with a reply path up front is unnecessary complexity, doubly so in message handlers. Here we take the next step towards untangling that, moving from `PendingOnionMessage` to `MessageSendInstructions` for the outbound message queue in `OffersMessageHandler`. Better, we can also drop the `c_bindings`-specific message queue variant, unifying the APIs. Because `ChannelManager` needs to actually control the reply path set in individual messages, however, we have to halfway this patch, adding a new `MessageSendInstructions` variant that allows specifying the `reply_path` explicitly. Still, because other message handlers are moving this way, its nice to be consistent. By unifying the response type with the outbound message queue type, this also fixes #3178.
1 parent 3609207 commit db9c76a

File tree

4 files changed

+87
-106
lines changed

4 files changed

+87
-106
lines changed

lightning/src/ln/channelmanager.rs

Lines changed: 28 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,7 @@ use crate::offers::parse::Bolt12SemanticError;
7171
use crate::offers::refund::{Refund, RefundBuilder};
7272
use crate::offers::signer;
7373
use crate::onion_message::async_payments::{AsyncPaymentsMessage, HeldHtlcAvailable, ReleaseHeldHtlc, AsyncPaymentsMessageHandler};
74-
use crate::onion_message::messenger::{new_pending_onion_message, Destination, MessageRouter, PendingOnionMessage, Responder, MessageSendInstructions};
74+
use crate::onion_message::messenger::{Destination, MessageRouter, PendingOnionMessage, Responder, MessageSendInstructions};
7575
use crate::onion_message::offers::{OffersMessage, OffersMessageHandler};
7676
use crate::sign::{EntropySource, NodeSigner, Recipient, SignerProvider};
7777
use crate::sign::ecdsa::EcdsaChannelSigner;
@@ -2277,9 +2277,9 @@ where
22772277
needs_persist_flag: AtomicBool,
22782278

22792279
#[cfg(not(any(test, feature = "_test_utils")))]
2280-
pending_offers_messages: Mutex<Vec<PendingOnionMessage<OffersMessage>>>,
2280+
pending_offers_messages: Mutex<Vec<(OffersMessage, MessageSendInstructions)>>,
22812281
#[cfg(any(test, feature = "_test_utils"))]
2282-
pub(crate) pending_offers_messages: Mutex<Vec<PendingOnionMessage<OffersMessage>>>,
2282+
pub(crate) pending_offers_messages: Mutex<Vec<(OffersMessage, MessageSendInstructions)>>,
22832283

22842284
/// Tracks the message events that are to be broadcasted when we are connected to some peer.
22852285
pending_broadcast_messages: Mutex<Vec<MessageSendEvent>>,
@@ -9068,21 +9068,21 @@ where
90689068
.flat_map(|reply_path| offer.paths().iter().map(move |path| (path, reply_path)))
90699069
.take(OFFERS_MESSAGE_REQUEST_LIMIT)
90709070
.for_each(|(path, reply_path)| {
9071-
let message = new_pending_onion_message(
9072-
OffersMessage::InvoiceRequest(invoice_request.clone()),
9073-
Destination::BlindedPath(path.clone()),
9074-
Some(reply_path.clone()),
9075-
);
9076-
pending_offers_messages.push(message);
9071+
let instructions = MessageSendInstructions::WithSpecifiedReplyPath {
9072+
destination: Destination::BlindedPath(path.clone()),
9073+
reply_path: reply_path.clone(),
9074+
};
9075+
let message = OffersMessage::InvoiceRequest(invoice_request.clone());
9076+
pending_offers_messages.push((message, instructions));
90779077
});
90789078
} else if let Some(signing_pubkey) = offer.signing_pubkey() {
90799079
for reply_path in reply_paths {
9080-
let message = new_pending_onion_message(
9081-
OffersMessage::InvoiceRequest(invoice_request.clone()),
9082-
Destination::Node(signing_pubkey),
9083-
Some(reply_path),
9084-
);
9085-
pending_offers_messages.push(message);
9080+
let instructions = MessageSendInstructions::WithSpecifiedReplyPath {
9081+
destination: Destination::Node(signing_pubkey),
9082+
reply_path,
9083+
};
9084+
let message = OffersMessage::InvoiceRequest(invoice_request.clone());
9085+
pending_offers_messages.push((message, instructions));
90869086
}
90879087
} else {
90889088
debug_assert!(false);
@@ -9162,25 +9162,25 @@ where
91629162
let mut pending_offers_messages = self.pending_offers_messages.lock().unwrap();
91639163
if refund.paths().is_empty() {
91649164
for reply_path in reply_paths {
9165-
let message = new_pending_onion_message(
9166-
OffersMessage::Invoice(invoice.clone()),
9167-
Destination::Node(refund.payer_id()),
9168-
Some(reply_path),
9169-
);
9170-
pending_offers_messages.push(message);
9165+
let instructions = MessageSendInstructions::WithSpecifiedReplyPath {
9166+
destination: Destination::Node(refund.payer_id()),
9167+
reply_path,
9168+
};
9169+
let message = OffersMessage::Invoice(invoice.clone());
9170+
pending_offers_messages.push((message, instructions));
91719171
}
91729172
} else {
91739173
reply_paths
91749174
.iter()
91759175
.flat_map(|reply_path| refund.paths().iter().map(move |path| (path, reply_path)))
91769176
.take(OFFERS_MESSAGE_REQUEST_LIMIT)
91779177
.for_each(|(path, reply_path)| {
9178-
let message = new_pending_onion_message(
9179-
OffersMessage::Invoice(invoice.clone()),
9180-
Destination::BlindedPath(path.clone()),
9181-
Some(reply_path.clone()),
9182-
);
9183-
pending_offers_messages.push(message);
9178+
let instructions = MessageSendInstructions::WithSpecifiedReplyPath {
9179+
destination: Destination::BlindedPath(path.clone()),
9180+
reply_path: reply_path.clone(),
9181+
};
9182+
let message = OffersMessage::Invoice(invoice.clone());
9183+
pending_offers_messages.push((message, instructions));
91849184
});
91859185
}
91869186

@@ -10937,7 +10937,7 @@ where
1093710937
}
1093810938
}
1093910939

10940-
fn release_pending_messages(&self) -> Vec<PendingOnionMessage<OffersMessage>> {
10940+
fn release_pending_messages(&self) -> Vec<(OffersMessage, MessageSendInstructions)> {
1094110941
core::mem::take(&mut self.pending_offers_messages.lock().unwrap())
1094210942
}
1094310943
}

lightning/src/ln/offers_tests.rs

Lines changed: 29 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -59,7 +59,7 @@ use crate::offers::invoice_error::InvoiceError;
5959
use crate::offers::invoice_request::{InvoiceRequest, InvoiceRequestFields};
6060
use crate::offers::nonce::Nonce;
6161
use crate::offers::parse::Bolt12SemanticError;
62-
use crate::onion_message::messenger::{Destination, PeeledOnion, new_pending_onion_message};
62+
use crate::onion_message::messenger::{Destination, PeeledOnion, MessageSendInstructions};
6363
use crate::onion_message::offers::OffersMessage;
6464
use crate::onion_message::packet::ParsedOnionMessageContents;
6565
use crate::routing::gossip::{NodeAlias, NodeId};
@@ -1313,13 +1313,10 @@ fn fails_authentication_when_handling_invoice_request() {
13131313
expect_recent_payment!(david, RecentPaymentDetails::AwaitingInvoice, payment_id);
13141314

13151315
connect_peers(david, alice);
1316-
#[cfg(not(c_bindings))] {
1317-
david.node.pending_offers_messages.lock().unwrap().first_mut().unwrap().destination =
1318-
Destination::Node(alice_id);
1319-
}
1320-
#[cfg(c_bindings)] {
1321-
david.node.pending_offers_messages.lock().unwrap().first_mut().unwrap().1 =
1322-
Destination::Node(alice_id);
1316+
match &mut david.node.pending_offers_messages.lock().unwrap().first_mut().unwrap().1 {
1317+
MessageSendInstructions::WithSpecifiedReplyPath { destination, .. } =>
1318+
*destination = Destination::Node(alice_id),
1319+
_ => panic!(),
13231320
}
13241321

13251322
let onion_message = david.onion_messenger.next_onion_message_for_peer(alice_id).unwrap();
@@ -1341,13 +1338,10 @@ fn fails_authentication_when_handling_invoice_request() {
13411338
.unwrap();
13421339
expect_recent_payment!(david, RecentPaymentDetails::AwaitingInvoice, payment_id);
13431340

1344-
#[cfg(not(c_bindings))] {
1345-
david.node.pending_offers_messages.lock().unwrap().first_mut().unwrap().destination =
1346-
Destination::BlindedPath(invalid_path);
1347-
}
1348-
#[cfg(c_bindings)] {
1349-
david.node.pending_offers_messages.lock().unwrap().first_mut().unwrap().1 =
1350-
Destination::BlindedPath(invalid_path);
1341+
match &mut david.node.pending_offers_messages.lock().unwrap().first_mut().unwrap().1 {
1342+
MessageSendInstructions::WithSpecifiedReplyPath { destination, .. } =>
1343+
*destination = Destination::BlindedPath(invalid_path),
1344+
_ => panic!(),
13511345
}
13521346

13531347
connect_peers(david, bob);
@@ -1427,11 +1421,9 @@ fn fails_authentication_when_handling_invoice_for_offer() {
14271421
let mut pending_offers_messages = david.node.pending_offers_messages.lock().unwrap();
14281422
let pending_invoice_request = pending_offers_messages.pop().unwrap();
14291423
pending_offers_messages.clear();
1430-
#[cfg(not(c_bindings))] {
1431-
pending_invoice_request.reply_path
1432-
}
1433-
#[cfg(c_bindings)] {
1434-
pending_invoice_request.2
1424+
match pending_invoice_request.1 {
1425+
MessageSendInstructions::WithSpecifiedReplyPath { reply_path, .. } => reply_path,
1426+
_ => panic!(),
14351427
}
14361428
};
14371429

@@ -1445,11 +1437,10 @@ fn fails_authentication_when_handling_invoice_for_offer() {
14451437
{
14461438
let mut pending_offers_messages = david.node.pending_offers_messages.lock().unwrap();
14471439
let mut pending_invoice_request = pending_offers_messages.first_mut().unwrap();
1448-
#[cfg(not(c_bindings))] {
1449-
pending_invoice_request.reply_path = invalid_reply_path;
1450-
}
1451-
#[cfg(c_bindings)] {
1452-
pending_invoice_request.2 = invalid_reply_path;
1440+
match &mut pending_invoice_request.1 {
1441+
MessageSendInstructions::WithSpecifiedReplyPath { reply_path, .. } =>
1442+
*reply_path = invalid_reply_path,
1443+
_ => panic!(),
14531444
}
14541445
}
14551446

@@ -1531,13 +1522,10 @@ fn fails_authentication_when_handling_invoice_for_refund() {
15311522
let expected_invoice = alice.node.request_refund_payment(&refund).unwrap();
15321523

15331524
connect_peers(david, alice);
1534-
#[cfg(not(c_bindings))] {
1535-
alice.node.pending_offers_messages.lock().unwrap().first_mut().unwrap().destination =
1536-
Destination::Node(david_id);
1537-
}
1538-
#[cfg(c_bindings)] {
1539-
alice.node.pending_offers_messages.lock().unwrap().first_mut().unwrap().1 =
1540-
Destination::Node(david_id);
1525+
match &mut alice.node.pending_offers_messages.lock().unwrap().first_mut().unwrap().1 {
1526+
MessageSendInstructions::WithSpecifiedReplyPath { destination, .. } =>
1527+
*destination = Destination::Node(david_id),
1528+
_ => panic!(),
15411529
}
15421530

15431531
let onion_message = alice.onion_messenger.next_onion_message_for_peer(david_id).unwrap();
@@ -1565,13 +1553,10 @@ fn fails_authentication_when_handling_invoice_for_refund() {
15651553

15661554
let expected_invoice = alice.node.request_refund_payment(&refund).unwrap();
15671555

1568-
#[cfg(not(c_bindings))] {
1569-
alice.node.pending_offers_messages.lock().unwrap().first_mut().unwrap().destination =
1570-
Destination::BlindedPath(invalid_path);
1571-
}
1572-
#[cfg(c_bindings)] {
1573-
alice.node.pending_offers_messages.lock().unwrap().first_mut().unwrap().1 =
1574-
Destination::BlindedPath(invalid_path);
1556+
match &mut alice.node.pending_offers_messages.lock().unwrap().first_mut().unwrap().1 {
1557+
MessageSendInstructions::WithSpecifiedReplyPath { destination, .. } =>
1558+
*destination = Destination::BlindedPath(invalid_path),
1559+
_ => panic!(),
15751560
}
15761561

15771562
connect_peers(alice, charlie);
@@ -2155,10 +2140,11 @@ fn fails_paying_invoice_with_unknown_required_features() {
21552140
.build_and_sign(&secp_ctx).unwrap();
21562141

21572142
// Enqueue an onion message containing the new invoice.
2158-
let pending_message = new_pending_onion_message(
2159-
OffersMessage::Invoice(invoice), Destination::BlindedPath(reply_path), None
2160-
);
2161-
alice.node.pending_offers_messages.lock().unwrap().push(pending_message);
2143+
let instructions = MessageSendInstructions::WithoutReplyPath {
2144+
destination: Destination::BlindedPath(reply_path),
2145+
};
2146+
let message = OffersMessage::Invoice(invoice);
2147+
alice.node.pending_offers_messages.lock().unwrap().push((message, instructions));
21622148

21632149
let onion_message = alice.onion_messenger.next_onion_message_for_peer(charlie_id).unwrap();
21642150
charlie.onion_messenger.handle_onion_message(&alice_id, &onion_message);

lightning/src/onion_message/messenger.rs

Lines changed: 29 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -385,6 +385,14 @@ impl Responder {
385385
/// Instructions for how and where to send a message.
386386
#[derive(Clone)]
387387
pub enum MessageSendInstructions {
388+
/// Indicates that a message should be sent including the provided reply path for the recipient
389+
/// to respond.
390+
WithSpecifiedReplyPath {
391+
/// The desination where we need to send our message.
392+
destination: Destination,
393+
/// The reply path which should be included in the message.
394+
reply_path: BlindedMessagePath,
395+
},
388396
/// Indicates that a message should be sent including a reply path for the recipient to
389397
/// respond.
390398
WithReplyPath {
@@ -1165,24 +1173,25 @@ where
11651173
fn handle_onion_message_send<T: OnionMessageContents>(
11661174
&self, response_message: T, response: MessageSendInstructions, log_suffix: fmt::Arguments,
11671175
) -> Result<Option<SendSuccess>, SendError> {
1168-
let (destination, context) = match response {
1169-
MessageSendInstructions::WithReplyPath { destination, context } => (destination, Some(context)),
1170-
MessageSendInstructions::WithoutReplyPath { destination } => (destination, None),
1171-
};
1172-
1173-
let reply_path = if let Some(context) = context {
1174-
match self.create_blinded_path(context) {
1175-
Ok(reply_path) => Some(reply_path),
1176-
Err(err) => {
1177-
log_trace!(
1178-
self.logger,
1179-
"Failed to create reply path {}: {:?}",
1180-
log_suffix, err
1181-
);
1182-
return Err(err);
1176+
let (destination, reply_path) = match response {
1177+
MessageSendInstructions::WithSpecifiedReplyPath { destination, reply_path } =>
1178+
(destination, Some(reply_path)),
1179+
MessageSendInstructions::WithReplyPath { destination, context } => {
1180+
match self.create_blinded_path(context) {
1181+
Ok(reply_path) => (destination, Some(reply_path)),
1182+
Err(err) => {
1183+
log_trace!(
1184+
self.logger,
1185+
"Failed to create reply path {}: {:?}",
1186+
log_suffix, err
1187+
);
1188+
return Err(err);
1189+
}
11831190
}
1184-
}
1185-
} else { None };
1191+
},
1192+
MessageSendInstructions::WithoutReplyPath { destination } =>
1193+
(destination, None),
1194+
};
11861195

11871196
self.find_path_and_enqueue_onion_message(
11881197
response_message, destination, reply_path, log_suffix,
@@ -1719,13 +1728,9 @@ where
17191728
// node, and then enqueue the message for sending to the first peer in the full path.
17201729
fn next_onion_message_for_peer(&self, peer_node_id: PublicKey) -> Option<OnionMessage> {
17211730
// Enqueue any initiating `OffersMessage`s to send.
1722-
for message in self.offers_handler.release_pending_messages() {
1723-
#[cfg(not(c_bindings))]
1724-
let PendingOnionMessage { contents, destination, reply_path } = message;
1725-
#[cfg(c_bindings)]
1726-
let (contents, destination, reply_path) = message;
1727-
let _ = self.find_path_and_enqueue_onion_message(
1728-
contents, destination, reply_path, format_args!("when sending OffersMessage")
1731+
for (message, instructions) in self.offers_handler.release_pending_messages() {
1732+
let _ = self.handle_onion_message_send(
1733+
message, instructions, format_args!("when sending OffersMessage")
17291734
);
17301735
}
17311736

lightning/src/onion_message/offers.rs

Lines changed: 1 addition & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -23,8 +23,6 @@ use crate::onion_message::packet::OnionMessageContents;
2323
use crate::util::logger::Logger;
2424
use crate::util::ser::{Readable, ReadableArgs, Writeable, Writer};
2525
use crate::onion_message::messenger::{MessageSendInstructions, Responder};
26-
#[cfg(not(c_bindings))]
27-
use crate::onion_message::messenger::PendingOnionMessage;
2826

2927
use crate::prelude::*;
3028

@@ -53,15 +51,7 @@ pub trait OffersMessageHandler {
5351
///
5452
/// Typically, this is used for messages initiating a payment flow rather than in response to
5553
/// another message. The latter should use the return value of [`Self::handle_message`].
56-
#[cfg(not(c_bindings))]
57-
fn release_pending_messages(&self) -> Vec<PendingOnionMessage<OffersMessage>> { vec![] }
58-
59-
/// Releases any [`OffersMessage`]s that need to be sent.
60-
///
61-
/// Typically, this is used for messages initiating a payment flow rather than in response to
62-
/// another message. The latter should use the return value of [`Self::handle_message`].
63-
#[cfg(c_bindings)]
64-
fn release_pending_messages(&self) -> Vec<(OffersMessage, crate::onion_message::messenger::Destination, Option<crate::blinded_path::message::BlindedMessagePath>)> { vec![] }
54+
fn release_pending_messages(&self) -> Vec<(OffersMessage, MessageSendInstructions)> { vec![] }
6555
}
6656

6757
/// Possible BOLT 12 Offers messages sent and received via an [`OnionMessage`].

0 commit comments

Comments
 (0)