+ fn respond_with_onion_message<T: CustomOnionMessageContents>(
+ &self, response: OnionMessageContents<T>, path_id: Option<[u8; 32]>,
+ reply_path: Option<BlindedPath>
+ ) {
+ let sender = match self.node_signer.get_node_id(Recipient::Node) {
+ Ok(node_id) => node_id,
+ Err(_) => {
+ log_warn!(
+ self.logger, "Unable to retrieve node id when responding to onion message with \
+ path_id {:02x?}", path_id
+ );
+ return;
+ }
+ };
+
+ let peers = self.pending_messages.lock().unwrap().keys().copied().collect();
+
+ let destination = match reply_path {
+ Some(reply_path) => Destination::BlindedPath(reply_path),
+ None => {
+ log_trace!(
+ self.logger, "Missing reply path when responding to onion message with path_id \
+ {:02x?}", path_id
+ );
+ return;
+ },
+ };
+
+ let path = match self.message_router.find_path(sender, peers, destination) {
+ Ok(path) => path,
+ Err(()) => {
+ log_trace!(
+ self.logger, "Failed to find path when responding to onion message with \
+ path_id {:02x?}", path_id
+ );
+ return;
+ },
+ };
+
+ log_trace!(self.logger, "Responding to onion message with path_id {:02x?}", path_id);
+
+ if let Err(e) = self.send_onion_message(path, response, None) {
+ log_trace!(
+ self.logger, "Failed responding to onion message with path_id {:02x?}: {:?}",
+ path_id, e
+ );
+ return;
+ }
+ }
+
+ #[cfg(test)]
+ pub(super) fn release_pending_msgs(&self) -> HashMap<PublicKey, VecDeque<msgs::OnionMessage>> {
+ let mut pending_msgs = self.pending_messages.lock().unwrap();
+ let mut msgs = HashMap::new();
+ // We don't want to disconnect the peers by removing them entirely from the original map, so we
+ // swap the pending message buffers individually.
+ for (peer_node_id, pending_messages) in &mut *pending_msgs {
+ msgs.insert(*peer_node_id, core::mem::take(pending_messages));
+ }
+ msgs
+ }
+}
+
+fn outbound_buffer_full(peer_node_id: &PublicKey, buffer: &HashMap<PublicKey, VecDeque<msgs::OnionMessage>>) -> bool {
+ const MAX_TOTAL_BUFFER_SIZE: usize = (1 << 20) * 128;
+ const MAX_PER_PEER_BUFFER_SIZE: usize = (1 << 10) * 256;
+ let mut total_buffered_bytes = 0;
+ let mut peer_buffered_bytes = 0;
+ for (pk, peer_buf) in buffer {
+ for om in peer_buf {
+ let om_len = om.serialized_length();
+ if pk == peer_node_id {
+ peer_buffered_bytes += om_len;
+ }
+ total_buffered_bytes += om_len;
+
+ if total_buffered_bytes >= MAX_TOTAL_BUFFER_SIZE ||
+ peer_buffered_bytes >= MAX_PER_PEER_BUFFER_SIZE
+ {
+ return true
+ }
+ }
+ }
+ false
+}
+
+impl<ES: Deref, NS: Deref, L: Deref, MR: Deref, OMH: Deref, CMH: Deref> OnionMessageHandler
+for OnionMessenger<ES, NS, L, MR, OMH, CMH>
+where
+ ES::Target: EntropySource,
+ NS::Target: NodeSigner,
+ L::Target: Logger,
+ MR::Target: MessageRouter,
+ OMH::Target: OffersMessageHandler,
+ CMH::Target: CustomOnionMessageHandler,
+{