Skip to content

Unify blinding nomenclature to call them "paths" not "routes". #1918

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
// You may not use this file except in accordance with one or both of these
// licenses.

//! Creating blinded routes and related utilities live here.
//! Creating blinded paths and related utilities live here.

use bitcoin::hashes::{Hash, HashEngine};
use bitcoin::hashes::sha256::Hash as Sha256;
Expand All @@ -26,11 +26,11 @@ use core::ops::Deref;
use crate::io::{self, Cursor};
use crate::prelude::*;

/// Onion messages can be sent and received to blinded routes, which serve to hide the identity of
/// Onion messages can be sent and received to blinded paths, which serve to hide the identity of
/// the recipient.
#[derive(Clone, Debug, PartialEq)]
pub struct BlindedRoute {
/// To send to a blinded route, the sender first finds a route to the unblinded
pub struct BlindedPath {
/// To send to a blinded path, the sender first finds a route to the unblinded
/// `introduction_node_id`, which can unblind its [`encrypted_payload`] to find out the onion
/// message's next hop and forward it along.
///
Expand All @@ -41,24 +41,24 @@ pub struct BlindedRoute {
///
/// [`encrypted_payload`]: BlindedHop::encrypted_payload
pub(crate) blinding_point: PublicKey,
/// The hops composing the blinded route.
/// The hops composing the blinded path.
pub(crate) blinded_hops: Vec<BlindedHop>,
}

/// Used to construct the blinded hops portion of a blinded route. These hops cannot be identified
/// Used to construct the blinded hops portion of a blinded path. These hops cannot be identified
/// by outside observers and thus can be used to hide the identity of the recipient.
#[derive(Clone, Debug, PartialEq)]
pub struct BlindedHop {
/// The blinded node id of this hop in a blinded route.
/// The blinded node id of this hop in a blinded path.
pub(crate) blinded_node_id: PublicKey,
/// The encrypted payload intended for this hop in a blinded route.
// The node sending to this blinded route will later encode this payload into the onion packet for
/// The encrypted payload intended for this hop in a blinded path.
// The node sending to this blinded path will later encode this payload into the onion packet for
// this hop.
pub(crate) encrypted_payload: Vec<u8>,
}

impl BlindedRoute {
/// Create a blinded route to be forwarded along `node_pks`. The last node pubkey in `node_pks`
impl BlindedPath {
/// Create a blinded path to be forwarded along `node_pks`. The last node pubkey in `node_pks`
/// will be the destination node.
///
/// Errors if less than two hops are provided or if `node_pk`(s) are invalid.
Expand All @@ -71,14 +71,14 @@ impl BlindedRoute {
let blinding_secret = SecretKey::from_slice(&blinding_secret_bytes[..]).expect("RNG is busted");
let introduction_node_id = node_pks[0];

Ok(BlindedRoute {
Ok(BlindedPath {
introduction_node_id,
blinding_point: PublicKey::from_secret_key(secp_ctx, &blinding_secret),
blinded_hops: blinded_hops(secp_ctx, node_pks, &blinding_secret).map_err(|_| ())?,
})
}

// Advance the blinded route by one hop, so make the second hop into the new introduction node.
// Advance the blinded path by one hop, so make the second hop into the new introduction node.
pub(super) fn advance_by_one<K: Deref, T: secp256k1::Signing + secp256k1::Verification>
(&mut self, keys_manager: &K, secp_ctx: &Secp256k1<T>) -> Result<(), ()>
where K::Target: KeysInterface
Expand Down Expand Up @@ -156,7 +156,7 @@ fn encrypt_payload<P: Writeable>(payload: P, encrypted_tlvs_ss: [u8; 32]) -> Vec
writer.0
}

impl Writeable for BlindedRoute {
impl Writeable for BlindedPath {
fn write<W: Writer>(&self, w: &mut W) -> Result<(), io::Error> {
self.introduction_node_id.write(w)?;
self.blinding_point.write(w)?;
Expand All @@ -168,7 +168,7 @@ impl Writeable for BlindedRoute {
}
}

impl Readable for BlindedRoute {
impl Readable for BlindedPath {
fn read<R: io::Read>(r: &mut R) -> Result<Self, DecodeError> {
let introduction_node_id = Readable::read(r)?;
let blinding_point = Readable::read(r)?;
Expand All @@ -178,7 +178,7 @@ impl Readable for BlindedRoute {
for _ in 0..num_hops {
blinded_hops.push(Readable::read(r)?);
}
Ok(BlindedRoute {
Ok(BlindedPath {
introduction_node_id,
blinding_point,
blinded_hops,
Expand All @@ -196,15 +196,15 @@ impl_writeable!(BlindedHop, {
pub(crate) struct ForwardTlvs {
/// The node id of the next hop in the onion message's path.
pub(super) next_node_id: PublicKey,
/// Senders to a blinded route use this value to concatenate the route they find to the
/// introduction node with the blinded route.
/// Senders to a blinded path use this value to concatenate the route they find to the
/// introduction node with the blinded path.
pub(super) next_blinding_override: Option<PublicKey>,
}

/// Similar to [`ForwardTlvs`], but these TLVs are for the final node.
pub(crate) struct ReceiveTlvs {
/// If `path_id` is `Some`, it is used to identify the blinded route that this onion message is
/// sending to. This is useful for receivers to check that said blinded route is being used in
/// If `path_id` is `Some`, it is used to identify the blinded path that this onion message is
/// sending to. This is useful for receivers to check that said blinded path is being used in
/// the right context.
pub(super) path_id: Option<[u8; 32]>,
}
Expand Down
52 changes: 26 additions & 26 deletions lightning/src/onion_message/functional_tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
use crate::chain::keysinterface::{KeysInterface, Recipient};
use crate::ln::features::InitFeatures;
use crate::ln::msgs::{self, DecodeError, OnionMessageHandler};
use super::{BlindedRoute, CustomOnionMessageContents, CustomOnionMessageHandler, Destination, OnionMessageContents, OnionMessenger, SendError};
use super::{BlindedPath, CustomOnionMessageContents, CustomOnionMessageHandler, Destination, OnionMessageContents, OnionMessenger, SendError};
use crate::util::ser::{Writeable, Writer};
use crate::util::test_utils;

Expand Down Expand Up @@ -136,9 +136,9 @@ fn two_unblinded_two_blinded() {
let test_msg = OnionMessageContents::Custom(TestCustomMessage {});

let secp_ctx = Secp256k1::new();
let blinded_route = BlindedRoute::new(&[nodes[3].get_node_pk(), nodes[4].get_node_pk()], &*nodes[4].keys_manager, &secp_ctx).unwrap();
let blinded_path = BlindedPath::new(&[nodes[3].get_node_pk(), nodes[4].get_node_pk()], &*nodes[4].keys_manager, &secp_ctx).unwrap();

nodes[0].messenger.send_onion_message(&[nodes[1].get_node_pk(), nodes[2].get_node_pk()], Destination::BlindedRoute(blinded_route), test_msg, None).unwrap();
nodes[0].messenger.send_onion_message(&[nodes[1].get_node_pk(), nodes[2].get_node_pk()], Destination::BlindedPath(blinded_path), test_msg, None).unwrap();
pass_along_path(&nodes, None);
}

Expand All @@ -148,9 +148,9 @@ fn three_blinded_hops() {
let test_msg = OnionMessageContents::Custom(TestCustomMessage {});

let secp_ctx = Secp256k1::new();
let blinded_route = BlindedRoute::new(&[nodes[1].get_node_pk(), nodes[2].get_node_pk(), nodes[3].get_node_pk()], &*nodes[3].keys_manager, &secp_ctx).unwrap();
let blinded_path = BlindedPath::new(&[nodes[1].get_node_pk(), nodes[2].get_node_pk(), nodes[3].get_node_pk()], &*nodes[3].keys_manager, &secp_ctx).unwrap();

nodes[0].messenger.send_onion_message(&[], Destination::BlindedRoute(blinded_route), test_msg, None).unwrap();
nodes[0].messenger.send_onion_message(&[], Destination::BlindedPath(blinded_path), test_msg, None).unwrap();
pass_along_path(&nodes, None);
}

Expand All @@ -168,42 +168,42 @@ fn too_big_packet_error() {

#[test]
fn we_are_intro_node() {
// If we are sending straight to a blinded route and we are the introduction node, we need to
// advance the blinded route by 1 hop so the second hop is the new introduction node.
// If we are sending straight to a blinded path and we are the introduction node, we need to
// advance the blinded path by 1 hop so the second hop is the new introduction node.
let mut nodes = create_nodes(3);
let test_msg = TestCustomMessage {};

let secp_ctx = Secp256k1::new();
let blinded_route = BlindedRoute::new(&[nodes[0].get_node_pk(), nodes[1].get_node_pk(), nodes[2].get_node_pk()], &*nodes[2].keys_manager, &secp_ctx).unwrap();
let blinded_path = BlindedPath::new(&[nodes[0].get_node_pk(), nodes[1].get_node_pk(), nodes[2].get_node_pk()], &*nodes[2].keys_manager, &secp_ctx).unwrap();

nodes[0].messenger.send_onion_message(&[], Destination::BlindedRoute(blinded_route), OnionMessageContents::Custom(test_msg.clone()), None).unwrap();
nodes[0].messenger.send_onion_message(&[], Destination::BlindedPath(blinded_path), OnionMessageContents::Custom(test_msg.clone()), None).unwrap();
pass_along_path(&nodes, None);

// Try with a two-hop blinded route where we are the introduction node.
let blinded_route = BlindedRoute::new(&[nodes[0].get_node_pk(), nodes[1].get_node_pk()], &*nodes[1].keys_manager, &secp_ctx).unwrap();
nodes[0].messenger.send_onion_message(&[], Destination::BlindedRoute(blinded_route), OnionMessageContents::Custom(test_msg), None).unwrap();
// Try with a two-hop blinded path where we are the introduction node.
let blinded_path = BlindedPath::new(&[nodes[0].get_node_pk(), nodes[1].get_node_pk()], &*nodes[1].keys_manager, &secp_ctx).unwrap();
nodes[0].messenger.send_onion_message(&[], Destination::BlindedPath(blinded_path), OnionMessageContents::Custom(test_msg), None).unwrap();
nodes.remove(2);
pass_along_path(&nodes, None);
}

#[test]
fn invalid_blinded_route_error() {
// Make sure we error as expected if a provided blinded route has 0 or 1 hops.
fn invalid_blinded_path_error() {
// Make sure we error as expected if a provided blinded path has 0 or 1 hops.
let nodes = create_nodes(3);
let test_msg = TestCustomMessage {};

// 0 hops
let secp_ctx = Secp256k1::new();
let mut blinded_route = BlindedRoute::new(&[nodes[1].get_node_pk(), nodes[2].get_node_pk()], &*nodes[2].keys_manager, &secp_ctx).unwrap();
blinded_route.blinded_hops.clear();
let err = nodes[0].messenger.send_onion_message(&[], Destination::BlindedRoute(blinded_route), OnionMessageContents::Custom(test_msg.clone()), None).unwrap_err();
let mut blinded_path = BlindedPath::new(&[nodes[1].get_node_pk(), nodes[2].get_node_pk()], &*nodes[2].keys_manager, &secp_ctx).unwrap();
blinded_path.blinded_hops.clear();
let err = nodes[0].messenger.send_onion_message(&[], Destination::BlindedPath(blinded_path), OnionMessageContents::Custom(test_msg.clone()), None).unwrap_err();
assert_eq!(err, SendError::TooFewBlindedHops);

// 1 hop
let mut blinded_route = BlindedRoute::new(&[nodes[1].get_node_pk(), nodes[2].get_node_pk()], &*nodes[2].keys_manager, &secp_ctx).unwrap();
blinded_route.blinded_hops.remove(0);
assert_eq!(blinded_route.blinded_hops.len(), 1);
let err = nodes[0].messenger.send_onion_message(&[], Destination::BlindedRoute(blinded_route), OnionMessageContents::Custom(test_msg), None).unwrap_err();
let mut blinded_path = BlindedPath::new(&[nodes[1].get_node_pk(), nodes[2].get_node_pk()], &*nodes[2].keys_manager, &secp_ctx).unwrap();
blinded_path.blinded_hops.remove(0);
assert_eq!(blinded_path.blinded_hops.len(), 1);
let err = nodes[0].messenger.send_onion_message(&[], Destination::BlindedPath(blinded_path), OnionMessageContents::Custom(test_msg), None).unwrap_err();
assert_eq!(err, SendError::TooFewBlindedHops);
}

Expand All @@ -214,19 +214,19 @@ fn reply_path() {
let secp_ctx = Secp256k1::new();

// Destination::Node
let reply_path = BlindedRoute::new(&[nodes[2].get_node_pk(), nodes[1].get_node_pk(), nodes[0].get_node_pk()], &*nodes[0].keys_manager, &secp_ctx).unwrap();
let reply_path = BlindedPath::new(&[nodes[2].get_node_pk(), nodes[1].get_node_pk(), nodes[0].get_node_pk()], &*nodes[0].keys_manager, &secp_ctx).unwrap();
nodes[0].messenger.send_onion_message(&[nodes[1].get_node_pk(), nodes[2].get_node_pk()], Destination::Node(nodes[3].get_node_pk()), OnionMessageContents::Custom(test_msg.clone()), Some(reply_path)).unwrap();
pass_along_path(&nodes, None);
// Make sure the last node successfully decoded the reply path.
nodes[3].logger.assert_log_contains(
"lightning::onion_message::messenger".to_string(),
format!("Received an onion message with path_id None and a reply_path").to_string(), 1);

// Destination::BlindedRoute
let blinded_route = BlindedRoute::new(&[nodes[1].get_node_pk(), nodes[2].get_node_pk(), nodes[3].get_node_pk()], &*nodes[3].keys_manager, &secp_ctx).unwrap();
let reply_path = BlindedRoute::new(&[nodes[2].get_node_pk(), nodes[1].get_node_pk(), nodes[0].get_node_pk()], &*nodes[0].keys_manager, &secp_ctx).unwrap();
// Destination::BlindedPath
let blinded_path = BlindedPath::new(&[nodes[1].get_node_pk(), nodes[2].get_node_pk(), nodes[3].get_node_pk()], &*nodes[3].keys_manager, &secp_ctx).unwrap();
let reply_path = BlindedPath::new(&[nodes[2].get_node_pk(), nodes[1].get_node_pk(), nodes[0].get_node_pk()], &*nodes[0].keys_manager, &secp_ctx).unwrap();

nodes[0].messenger.send_onion_message(&[], Destination::BlindedRoute(blinded_route), OnionMessageContents::Custom(test_msg), Some(reply_path)).unwrap();
nodes[0].messenger.send_onion_message(&[], Destination::BlindedPath(blinded_path), OnionMessageContents::Custom(test_msg), Some(reply_path)).unwrap();
pass_along_path(&nodes, None);
nodes[3].logger.assert_log_contains(
"lightning::onion_message::messenger".to_string(),
Expand Down
Loading