restoring nym-lp tests

This commit is contained in:
Jędrzej Stuczyński
2026-02-24 10:57:31 +00:00
parent 872ae85136
commit 595d034f64
26 changed files with 887 additions and 2203 deletions
+1 -1
View File
@@ -262,7 +262,7 @@ impl ForwardPacketData {
}
}
#[derive(Debug, Clone)]
#[derive(Debug, Clone, PartialEq, Eq)]
pub enum LpMessage {
/// The party is busy
Busy,
+1 -1
View File
@@ -53,7 +53,7 @@ impl EncryptedLpPacket {
}
}
#[derive(Clone)]
#[derive(Clone, PartialEq, Eq)]
pub struct LpPacket {
pub(crate) header: LpHeader,
pub(crate) message: LpMessage,
+5 -10
View File
@@ -1,9 +1,8 @@
use criterion::{BenchmarkId, Criterion, Throughput, black_box, criterion_group, criterion_main};
use nym_lp::replay::ReceivingKeyCounterValidator;
use nym_test_utils::helpers::deterministic_rng_09;
use parking_lot::Mutex;
use rand09::Rng;
use std::sync::Arc;
use std::sync::{Arc, Mutex};
fn bench_sequential_counters(c: &mut Criterion) {
let mut group = c.benchmark_group("replay_sequential");
@@ -75,19 +74,15 @@ fn bench_thread_safety(c: &mut Criterion) {
BenchmarkId::new("thread_safe_validator", size),
&size,
|b, &size| {
let validator = Arc::new(Mutex::new(ReceivingKeyCounterValidator::default()));
let mut validator = ReceivingKeyCounterValidator::default();
let counters: Vec<u64> = (0..size).collect();
b.iter(|| {
for &counter in &counters {
let result = {
let guard = validator.lock();
black_box(guard.will_accept_branchless(counter))
};
let result = { black_box(validator.will_accept_branchless(counter)) };
if result.is_ok() {
let mut guard = validator.lock();
let _ = black_box(guard.mark_did_receive_branchless(counter));
let _ = black_box(validator.mark_did_receive_branchless(counter));
}
}
});
@@ -202,7 +197,7 @@ fn bench_concurrency_scaling(c: &mut Criterion) {
let mut success_count = 0;
for i in 0..100 {
let counter = t * 1000 + i;
let mut guard = validator_clone.lock();
let mut guard = validator_clone.lock().unwrap();
if guard.mark_did_receive_branchless(counter as u64).is_ok() {
success_count += 1;
}
+210 -900
View File
File diff suppressed because it is too large Load Diff
+6
View File
@@ -27,6 +27,9 @@ pub enum LpError {
#[error("Attempted operation on closed session")]
SessionClosed,
#[error("There already exists an LP session with id {0:?}")]
DuplicateSessionId(SessionId),
#[error("Internal error: {0}")]
Internal(String),
@@ -112,6 +115,9 @@ pub enum LpError {
#[error("transport failure: {0}")]
TransportFailure(#[from] LpTransportError),
#[error("the current session is not in transport state")]
NotInTransport,
}
impl LpError {
-237
View File
@@ -135,240 +135,3 @@ pub fn sessions_for_tests() -> (LpSession, LpSession) {
pub fn mock_session_for_test() -> LpSession {
SessionsMock::mock_initiator()
}
#[cfg(test)]
mod tests {
use crate::session_manager::SessionManager;
use crate::{LpError, SessionsMock, mock_session_for_test};
use bytes::BytesMut;
use nym_kkt_ciphersuite::{Ciphersuite, HashFunction, IntoEnumIterator, KEM, SignatureScheme};
// Import the new standalone functions
use crate::codec::serialize_lp_packet;
#[test]
fn test_replay_protection_integration() {
todo!()
// for kem in kem_list() {
// // Create session
// let mut session = mock_session_for_test();
//
// // === Packet 1 (Counter 0 - Should succeed) ===
// let packet1 = LpPacket {
// header: LpHeader {
// protocol_version: 1,
// reserved: [0u8; 3],
// receiver_idx: 42, // Matches session's sending_index assumption for this test
// counter: 0,
// },
// message: LpMessage::Busy,
// trailer: [0u8; TRAILER_LEN],
// };
//
// // Serialize packet
// let mut buf1 = BytesMut::new();
// serialize_lp_packet(&packet1, &mut buf1, None).unwrap();
//
// // Parse packet
// let parsed_packet1 = parse_lp_packet(&buf1, None).unwrap();
//
// // Perform replay check (should pass)
// session
// .receiving_counter_quick_check(parsed_packet1.header.counter)
// .expect("Initial packet failed replay check");
//
// // Mark received (simulating successful processing)
// session
// .receiving_counter_mark(parsed_packet1.header.counter)
// .expect("Failed to mark initial packet received");
//
// // === Packet 2 (Counter 0 - Replay, should fail check) ===
// let packet2 = LpPacket {
// header: LpHeader {
// protocol_version: 1,
// reserved: [0u8; 3],
// receiver_idx: 42,
// counter: 0, // Same counter as before (replay)
// },
// message: LpMessage::Busy,
// trailer: [0u8; TRAILER_LEN],
// };
//
// // Serialize packet
// let mut buf2 = BytesMut::new();
// serialize_lp_packet(&packet2, &mut buf2, None).unwrap();
//
// // Parse packet
// let parsed_packet2 = parse_lp_packet(&buf2, None).unwrap();
//
// // Perform replay check (should fail)
// let replay_result =
// session.receiving_counter_quick_check(parsed_packet2.header.counter);
// assert!(replay_result.is_err());
// match replay_result.unwrap_err() {
// LpError::Replay(e) => {
// assert!(matches!(e, crate::replay::ReplayError::DuplicateCounter));
// }
// e => panic!("Expected replay error, got {:?}", e),
// }
// // Do not mark received as it failed validation
//
// // === Packet 3 (Counter 1 - Should succeed) ===
// let packet3 = LpPacket {
// header: LpHeader {
// protocol_version: 1,
// reserved: [0u8; 3],
// receiver_idx: 42,
// counter: 1, // Incremented counter
// },
// message: LpMessage::Busy,
// trailer: [0u8; TRAILER_LEN],
// };
//
// // Serialize packet
// let mut buf3 = BytesMut::new();
// serialize_lp_packet(&packet3, &mut buf3, None).unwrap();
//
// // Parse packet
// let parsed_packet3 = parse_lp_packet(&buf3, None).unwrap();
//
// // Perform replay check (should pass)
// session
// .receiving_counter_quick_check(parsed_packet3.header.counter)
// .expect("Packet 3 failed replay check");
//
// // Mark received
// session
// .receiving_counter_mark(parsed_packet3.header.counter)
// .expect("Failed to mark packet 3 received");
//
// // Verify validator state directly on the session
// let state = session.current_packet_cnt();
// assert_eq!(state.0, 2); // Next expected counter (correct - was 1, now expects 2)
// assert_eq!(state.1, 2); // Total marked received (correct - packets 1 and 3)
// }
}
#[test]
fn test_session_manager_integration() {
// Create session manager
let mut local_manager = SessionManager::new();
let mut remote_manager = SessionManager::new();
for kem in KEM::iter() {
todo!()
// // Generate Ed25519 keypairs for PSQ authentication
// let (init, resp) = mock_peers(kem);
//
// let mut ciphersuite = Ciphersuite::resolve_ciphersuite(
// kem,
// HashFunction::Blake3,
// SignatureScheme::Ed25519,
// None,
// );
//
// // Use fixed receiver_index for deterministic test
// let receiver_index: u32 = 54321;
//
// let sessions = SessionsMock::mock_post_handshake(receiver_index);
// let local_session = sessions.initiator;
// let remote_session = sessions.responder;
//
// // Create a session via manager
// let _ = local_manager.create_session_state_machine(local_session);
// let _ = remote_manager.create_session_state_machine(remote_session);
//
// // === Packet 1 (Counter 0 - Should succeed) ===
// let packet1 = LpPacket {
// header: LpHeader {
// protocol_version: 1,
// reserved: [0u8; 3],
// receiver_idx: receiver_index,
// counter: 0,
// },
// message: LpMessage::Busy,
// trailer: [0u8; TRAILER_LEN],
// };
//
// // Serialize
// let mut buf1 = BytesMut::new();
// serialize_lp_packet(&packet1, &mut buf1, None).unwrap();
//
// // Parse
// let parsed_packet1 = parse_lp_packet(&buf1, None).unwrap();
//
// // Process via SessionManager method (which should handle checks + marking)
// // NOTE: We might need a method on SessionManager/LpSession like `process_incoming_packet`
// // that encapsulates parse -> check -> process_noise -> mark.
// // For now, we simulate the steps using the retrieved session.
//
// // Perform replay check
// local_manager
// .receiving_counter_quick_check(receiver_index, parsed_packet1.header.counter)
// .expect("Packet 1 check failed");
// // Mark received
// local_manager
// .receiving_counter_mark(receiver_index, parsed_packet1.header.counter)
// .expect("Packet 1 mark failed");
//
// // === Packet 2 (Counter 1 - Should succeed on same session) ===
// let packet2 = LpPacket {
// header: LpHeader {
// protocol_version: 1,
// reserved: [0u8; 3],
// receiver_idx: receiver_index,
// counter: 1,
// },
// message: LpMessage::Busy,
// trailer: [0u8; TRAILER_LEN],
// };
//
// // Serialize
// let mut buf2 = BytesMut::new();
// serialize_lp_packet(&packet2, &mut buf2, None).unwrap();
//
// // Parse
// let parsed_packet2 = parse_lp_packet(&buf2, None).unwrap();
//
// // Perform replay check
// local_manager
// .receiving_counter_quick_check(receiver_index, parsed_packet2.header.counter)
// .expect("Packet 2 check failed");
// // Mark received
// local_manager
// .receiving_counter_mark(receiver_index, parsed_packet2.header.counter)
// .expect("Packet 2 mark failed");
//
// // === Packet 3 (Counter 0 - Replay, should fail check) ===
// let packet3 = LpPacket {
// header: LpHeader {
// protocol_version: 1,
// reserved: [0u8; 3],
// receiver_idx: receiver_index,
// counter: 0, // Replay of first packet
// },
// message: LpMessage::Busy,
// trailer: [0u8; TRAILER_LEN],
// };
//
// // Serialize
// let mut buf3 = BytesMut::new();
// serialize_lp_packet(&packet3, &mut buf3, None).unwrap();
//
// // Parse
// let parsed_packet3 = parse_lp_packet(&buf3, None).unwrap();
//
// // Perform replay check (should fail)
// let replay_result = local_manager
// .receiving_counter_quick_check(receiver_index, parsed_packet3.header.counter);
// assert!(replay_result.is_err());
// match replay_result.unwrap_err() {
// LpError::Replay(e) => {
// assert!(matches!(e, crate::replay::ReplayError::DuplicateCounter));
// }
// e => panic!("Expected replay error for packet 3, got {:?}", e),
// }
// // Do not mark received
}
}
}
+1 -1
View File
@@ -17,7 +17,7 @@ pub(crate) const UDP_PAYLOAD_SIZE: usize = MTU - UDP_OVERHEAD;
pub use nym_lp_packet::version;
pub(crate) trait LpPacketReplayExt {
pub trait LpPacketReplayExt {
/// Validate packet counter against a replay protection validator
///
/// This performs a quick check to see if the packet counter is valid before
+1 -1
View File
@@ -152,7 +152,7 @@ pub fn mock_peer() -> LpLocalPeer {
}
#[cfg(any(feature = "mock", test))]
pub fn random_peer<'a, R: rand09::CryptoRng + rand09::RngCore>(rng: &mut R) -> LpLocalPeer {
pub fn random_peer<R: rand09::CryptoRng + rand09::RngCore>(rng: &mut R) -> LpLocalPeer {
let x25519 = Arc::new(nym_kkt::key_utils::generate_keypair_x25519(rng));
LpLocalPeer {
+5 -11
View File
@@ -214,7 +214,6 @@ mod tests {
let conn_resp = conn_resp.leak();
let (mut init, mut resp) = mock_peers();
let init_remote = init.as_remote();
let resp_remote = resp.as_remote();
let ciphersuite = Ciphersuite::default().with_kem(kem);
@@ -246,8 +245,8 @@ mod tests {
let responder_x25519_keypair = resp.x25519();
let kkt_responder = KKTResponder::new(
&responder_x25519_keypair,
&resp_keys,
responder_x25519_keypair,
resp_keys,
&supported_hash,
&supported_sigs,
&[1],
@@ -282,11 +281,6 @@ mod tests {
.await??;
responder.read_message(&msg, &mut []).unwrap();
// Get the authenticator out here, so we can deserialize the session later.
let Some(initiator_authenticator) = responder.initiator_authenticator() else {
panic!("No initiator authenticator found")
};
// 4 send PSQ response
let mut buf = vec![0u8; PSQ_MSG2_SIZE];
let n = responder.write_message(&[], &mut buf).unwrap();
@@ -304,7 +298,7 @@ mod tests {
let mut r_transport = responder.into_session().unwrap();
// test serialization, deserialization
let mut channel_i = session_init.active_transport();
let channel_i = session_init.active_transport();
let mut channel_r = r_transport.transport_channel().unwrap();
assert_eq!(channel_i.identifier(), channel_r.identifier());
@@ -312,13 +306,13 @@ mod tests {
let app_data_i = b"Derived session hey".as_slice();
let app_data_r = b"Derived session ho".as_slice();
let ct_i = encrypt_data(app_data_i, &mut channel_i)?;
let ct_i = encrypt_data(app_data_i, channel_i)?;
let pt_r = decrypt_data(&ct_i, &mut channel_r)?;
assert_eq!(app_data_i, pt_r);
let ct_r = encrypt_data(app_data_r, &mut channel_r)?;
let pt_i = decrypt_data(&ct_r, &mut channel_i)?;
let pt_i = decrypt_data(&ct_r, channel_i)?;
assert_eq!(app_data_r, pt_i);
}
+8 -8
View File
@@ -172,21 +172,21 @@ mod tests {
);
// test serialization, deserialization
let mut channel_i = session_init.active_transport();
let mut channel_r = session_resp.active_transport();
let channel_i = session_init.active_transport();
let channel_r = session_resp.active_transport();
assert_eq!(channel_i.identifier(), channel_r.identifier());
let app_data_i = b"Derived session hey".as_slice();
let app_data_r = b"Derived session ho".as_slice();
let ct_i = encrypt_data(app_data_i, &mut channel_i)?;
let pt_r = decrypt_data(&ct_i, &mut channel_r)?;
let ct_i = encrypt_data(app_data_i, channel_i)?;
let pt_r = decrypt_data(&ct_i, channel_r)?;
assert_eq!(app_data_i, pt_r);
let ct_r = encrypt_data(app_data_r, &mut channel_r)?;
let pt_i = decrypt_data(&ct_r, &mut channel_i)?;
let ct_r = encrypt_data(app_data_r, channel_r)?;
let pt_i = decrypt_data(&ct_r, channel_i)?;
assert_eq!(app_data_r, pt_i);
}
@@ -218,8 +218,8 @@ mod tests {
HashFunction::SHA256,
];
let kkt_responder = KKTResponder::new(
&responder_x25519_keypair,
&resp_keys,
responder_x25519_keypair,
resp_keys,
&supported_hash,
&supported_sigs,
&[protocol_version],
+3 -4
View File
@@ -233,7 +233,6 @@ mod tests {
let conn_resp = conn_resp.leak();
let (mut init, mut resp) = mock_peers();
let init_remote = init.as_remote();
let resp_remote = resp.as_remote();
let ciphersuite = Ciphersuite::default().with_kem(kem);
@@ -314,7 +313,7 @@ mod tests {
// test serialization, deserialization
let mut channel_i = i_transport.transport_channel().unwrap();
let mut channel_r = session_resp.active_transport();
let channel_r = session_resp.active_transport();
assert_eq!(channel_i.identifier(), channel_r.identifier());
@@ -322,11 +321,11 @@ mod tests {
let app_data_r = b"Derived session ho".as_slice();
let ct_i = encrypt_data(app_data_i, &mut channel_i)?;
let pt_r = decrypt_data(&ct_i, &mut channel_r)?;
let pt_r = decrypt_data(&ct_i, channel_r)?;
assert_eq!(app_data_i, pt_r);
let ct_r = encrypt_data(app_data_r, &mut channel_r)?;
let ct_r = encrypt_data(app_data_r, channel_r)?;
let pt_i = decrypt_data(&ct_r, &mut channel_i)?;
assert_eq!(app_data_r, pt_i);
+36 -11
View File
@@ -38,6 +38,16 @@ const N_WORDS: usize = 16;
/// Total number of bits in the bitmap
const N_BITS: usize = WORD_SIZE * N_WORDS;
/// Current packet count statistics
#[derive(Copy, Clone, Debug, PartialEq)]
pub struct PacketCount {
/// the next expected counter value
pub next: u64,
/// the total number of received packets
pub received: u64,
}
/// Validator for receiving key counters to prevent replay attacks.
///
/// This structure maintains a bitmap of received packets and validates
@@ -205,11 +215,14 @@ impl ReceivingKeyCounterValidator {
/// Returns the current packet count statistics.
///
/// Returns a tuple of `(next, receive_cnt)` where:
/// Returns a struct consisting of `(next, receive_cnt)` where:
/// - `next` is the next expected counter value
/// - `receive_cnt` is the total number of received packets
pub fn current_packet_cnt(&self) -> (u64, u64) {
(self.next, self.receive_cnt)
pub fn current_packet_cnt(&self) -> PacketCount {
PacketCount {
next: self.next,
received: self.receive_cnt,
}
}
#[inline(always)]
@@ -481,7 +494,10 @@ mod tests {
let mut validator = ReceivingKeyCounterValidator::default();
// Initial state
let (next, count) = validator.current_packet_cnt();
let PacketCount {
next,
received: count,
} = validator.current_packet_cnt();
assert_eq!(next, 0);
assert_eq!(count, 0);
@@ -490,21 +506,30 @@ mod tests {
assert!(validator.mark_did_receive_branchless(1).is_ok());
assert!(validator.mark_did_receive_branchless(2).is_ok());
let (next, count) = validator.current_packet_cnt();
let PacketCount {
next,
received: count,
} = validator.current_packet_cnt();
assert_eq!(next, 3);
assert_eq!(count, 3);
// After an out of order packet
assert!(validator.mark_did_receive_branchless(10).is_ok());
let (next, count) = validator.current_packet_cnt();
let PacketCount {
next,
received: count,
} = validator.current_packet_cnt();
assert_eq!(next, 11);
assert_eq!(count, 4);
// After a packet from the past (within window)
assert!(validator.mark_did_receive_branchless(5).is_ok());
let (next, count) = validator.current_packet_cnt();
let PacketCount {
next,
received: count,
} = validator.current_packet_cnt();
assert_eq!(next, 11); // Next doesn't change
assert_eq!(count, 5); // Count increases
}
@@ -553,7 +578,7 @@ mod tests {
assert!(validator.mark_did_receive_branchless(first_jump).is_ok());
// Verify next counter is updated
let (next, _) = validator.current_packet_cnt();
let PacketCount { next, .. } = validator.current_packet_cnt();
assert_eq!(next, first_jump + 1);
// Second large jump, even further ahead
@@ -561,7 +586,7 @@ mod tests {
assert!(validator.mark_did_receive_branchless(second_jump).is_ok());
// Verify next counter is updated again
let (next, _) = validator.current_packet_cnt();
let PacketCount { next, .. } = validator.current_packet_cnt();
assert_eq!(next, second_jump + 1);
// Test packets within the new window
@@ -726,10 +751,10 @@ mod tests {
// Check final state of the validator
let final_state = validator.lock().unwrap();
let (_next, receive_cnt) = final_state.current_packet_cnt();
let count = final_state.current_packet_cnt();
// Verify that the received count matches our successful operations
assert_eq!(receive_cnt, total_successes as u64);
assert_eq!(count.received, total_successes as u64);
}
#[test]
+16 -10
View File
@@ -11,6 +11,7 @@ use crate::psq::{
InitiatorData, PSQHandshakeState, PSQHandshakeStateInitiator, PSQHandshakeStateResponder,
ResponderData,
};
use crate::replay::validator::PacketCount;
use crate::{LpError, LpMessage, LpPacket, ReceivingKeyCounterValidator};
use libcrux_psq::handshake::types::{Authenticator, DHPublicKey};
use libcrux_psq::session::{Session, SessionBinding};
@@ -162,7 +163,7 @@ impl LpSession {
self.psq_session.identifier()
}
pub fn id(&self) -> u32 {
pub fn receiver_index(&self) -> u32 {
let TODO = "this is temporary...";
let id = self.psq_session.identifier();
u32::from_le_bytes([id[0], id[1], id[2], id[3]])
@@ -177,7 +178,12 @@ impl LpSession {
pub fn next_packet(&mut self, message: LpMessage) -> Result<LpPacket, LpError> {
let counter = self.next_counter();
let header = LpHeader::new(self.id(), counter, self.protocol_version, message.typ());
let header = LpHeader::new(
self.receiver_index(),
counter,
self.protocol_version,
message.typ(),
);
let packet = LpPacket::new(header, message);
Ok(packet)
}
@@ -236,7 +242,7 @@ impl LpSession {
/// A tuple containing:
/// * The next expected counter value for incoming packets
/// * The total number of received packets
pub fn current_packet_cnt(&self) -> (u64, u64) {
pub fn current_packet_cnt(&self) -> PacketCount {
self.receiving_counter.current_packet_cnt()
}
@@ -280,7 +286,7 @@ impl LpSession {
#[cfg(test)]
mod tests {
use super::*;
use crate::{ReplayError, SessionsMock, sessions_for_tests};
use crate::{ReplayError, SessionsMock};
use nym_kkt_ciphersuite::{IntoEnumIterator, KEM};
#[test]
@@ -351,17 +357,17 @@ mod tests {
let mut session = SessionsMock::mock_post_handshake(kem).responder;
// Initial stats
let (next, received) = session.current_packet_cnt();
assert_eq!(next, 0);
assert_eq!(received, 0);
let packet_count = session.current_packet_cnt();
assert_eq!(packet_count.next, 0);
assert_eq!(packet_count.received, 0);
// After receiving packets
assert!(session.receiving_counter_mark(0).is_ok());
assert!(session.receiving_counter_mark(1).is_ok());
let (next, received) = session.current_packet_cnt();
assert_eq!(next, 2);
assert_eq!(received, 2);
let packet_count = session.current_packet_cnt();
assert_eq!(packet_count.next, 2);
assert_eq!(packet_count.received, 2);
}
}
}
File diff suppressed because it is too large Load Diff
+34 -34
View File
@@ -7,10 +7,13 @@
//! creation, retrieval, and storage of sessions.
use crate::session::SessionId;
use crate::state_machine::{LpAction, LpInput, LpStateBare};
use crate::state_machine::{LpAction, LpData, LpInput, LpStateBare};
use crate::{LpError, LpSession, LpStateMachine};
use nym_lp_packet::EncryptedLpPacket;
use std::collections::HashMap;
pub use crate::replay::validator::PacketCount;
/// Manages the lifecycle of Lewes Protocol sessions.
///
/// The SessionManager is responsible for creating, storing, and retrieving sessions
@@ -41,6 +44,19 @@ impl SessionManager {
self.with_state_machine_mut(lp_id, |sm| sm.process_input(input).transpose())?
}
pub fn send_data(&mut self, lp_id: SessionId, data: LpData) -> Result<LpAction, LpError> {
self.process_input(lp_id, LpInput::SendData(data))?
.ok_or(LpError::NotInTransport)
}
pub fn receive_packet(
&mut self,
lp_id: SessionId,
packet: EncryptedLpPacket,
) -> Result<Option<LpAction>, LpError> {
self.process_input(lp_id, LpInput::ReceivePacket(packet))
}
pub fn closed(&self, lp_id: SessionId) -> Result<bool, LpError> {
Ok(self.get_state(lp_id)? == LpStateBare::Closed)
}
@@ -58,31 +74,7 @@ impl SessionManager {
self.with_state_machine(lp_id, |sm| Ok(sm.bare_state()))?
}
pub fn receiving_counter_quick_check(
&self,
lp_id: SessionId,
counter: u64,
) -> Result<(), LpError> {
self.with_state_machine(lp_id, |sm| {
sm.session()?.receiving_counter_quick_check(counter)
})?
}
pub fn receiving_counter_mark(
&mut self,
lp_id: SessionId,
counter: u64,
) -> Result<(), LpError> {
self.with_state_machine_mut(lp_id, |sm| {
sm.session_mut()?.receiving_counter_mark(counter)
})?
}
pub fn next_counter(&mut self, lp_id: SessionId) -> Result<u64, LpError> {
self.with_state_machine_mut(lp_id, |sm| Ok(sm.session_mut()?.next_counter()))?
}
pub fn current_packet_cnt(&self, lp_id: SessionId) -> Result<(u64, u64), LpError> {
pub fn current_packet_cnt(&self, lp_id: SessionId) -> Result<PacketCount, LpError> {
self.with_state_machine(lp_id, |sm| Ok(sm.session()?.current_packet_cnt()))?
}
@@ -117,11 +109,19 @@ impl SessionManager {
}
}
pub fn create_session_state_machine(&mut self, lp_session: LpSession) -> SessionId {
pub fn create_session_state_machine(
&mut self,
lp_session: LpSession,
) -> Result<SessionId, LpError> {
let session_id = *lp_session.session_identifier();
if self.state_machines.contains_key(&session_id) {
return Err(LpError::DuplicateSessionId(session_id));
}
let sm = LpStateMachine::new(lp_session);
self.state_machines.insert(session_id, sm);
session_id
Ok(session_id)
}
/// Method to remove a state machine
@@ -144,7 +144,7 @@ mod tests {
let local_session = mock_session_for_test();
let id = *local_session.session_identifier();
let sm_1_id = manager.create_session_state_machine(local_session);
let sm_1_id = manager.create_session_state_machine(local_session).unwrap();
assert_eq!(sm_1_id, id);
let retrieved = manager.state_machine_exists(&id);
@@ -158,7 +158,7 @@ mod tests {
fn test_session_manager_remove() {
let mut manager = SessionManager::new();
let local_session = mock_session_for_test();
let sm_1_id = manager.create_session_state_machine(local_session);
let sm_1_id = manager.create_session_state_machine(local_session).unwrap();
let removed = manager.remove_state_machine(sm_1_id);
assert!(removed);
@@ -176,9 +176,9 @@ mod tests {
let session2 = SessionsMock::mock_seeded_post_handshake(124, kem).initiator;
let session3 = SessionsMock::mock_seeded_post_handshake(125, kem).initiator;
let sm_1 = manager.create_session_state_machine(session1);
let sm_2 = manager.create_session_state_machine(session2);
let sm_3 = manager.create_session_state_machine(session3);
let sm_1 = manager.create_session_state_machine(session1).unwrap();
let sm_2 = manager.create_session_state_machine(session2).unwrap();
let sm_3 = manager.create_session_state_machine(session3).unwrap();
assert_eq!(manager.session_count(), 3);
@@ -198,7 +198,7 @@ mod tests {
let sesion = mock_session_for_test();
let sm = manager.create_session_state_machine(sesion);
let sm = manager.create_session_state_machine(sesion).unwrap();
assert_eq!(manager.session_count(), 1);
let retrieved = manager.get_state_machine_id(sm);
+76 -87
View File
@@ -2,14 +2,6 @@
// SPDX-License-Identifier: Apache-2.0
//! Lewes Protocol State Machine for managing connection lifecycle.
//!
//! LP protocol flow (KKT → PSQ → Noise):
//! 1. KKTExchange: Client requests gateway's KEM public key (signed for MITM protection)
//! 2. Handshaking: Noise XKpsk3 with PSQ-derived PSK embedded in handshake messages
//! - PSQ ciphertext piggybacked on ClientHello (no extra round-trip)
//! - PSK = Blake3(ECDH || PSQ_secret || salt) provides hybrid classical+PQ security
//! 3. Transport: ChaCha20-Poly1305 authenticated encryption with derived keys
//!
//! State machine ensures protocol steps execute in correct order. Invalid transitions
//! return LpError, preventing protocol violations.
@@ -190,11 +182,6 @@ impl LpStateMachine {
}
}
pub fn id(&self) -> Result<u32, LpError> {
todo!()
// Ok(self.session()?.id())
}
pub fn session_identifier(&self) -> Result<SessionId, LpError> {
Ok(*self.session()?.session_identifier())
}
@@ -217,7 +204,7 @@ impl LpStateMachine {
match input {
LpInput::ReceivePacket(packet) => {
// Check if packet lp_id matches our session
if packet.outer_header().receiver_idx != session.id() {
if packet.outer_header().receiver_idx != session.receiver_index() {
let result_action = Some(Err(LpError::UnknownSessionId(
packet.outer_header().receiver_idx,
)));
@@ -231,17 +218,17 @@ impl LpStateMachine {
return (LpState::Transport(state), Some(Err(e)));
}
// 2. Mark counter as received
if let Err(e) = session.receiving_counter_mark(ctr) {
return (LpState::Transport(state), Some(Err(e)));
}
// 3. decrypt the packet and attempt to deliver data
// 2. decrypt the packet and attempt to deliver data
let packet = match session.decrypt_packet(packet) {
Ok(packet) => packet,
Err(e) => return (LpState::Transport(state), Some(Err(e))),
};
// 3. Mark counter as received
if let Err(e) = session.receiving_counter_mark(ctr) {
return (LpState::Transport(state), Some(Err(e)));
}
// Check message type
match packet.into_message() {
// Normal encrypted data
@@ -373,77 +360,79 @@ mod tests {
let resp_session = responder_sm.session().unwrap();
// Check both state machines use the same receiver_index
assert_eq!(init_session.id(), resp_session.id());
assert_eq!(init_session.receiver_index(), resp_session.receiver_index());
}
}
#[test]
fn test_state_machine_simplified_flow() {
todo!()
// for kem in KEM::iter() {
// let receiver_index: u32 = 123;
// let mock_sessions = SessionsMock::mock_post_handshake(kem);
//
// // Create state machines (already in Transport)
// let mut initiator = LpStateMachine::new(mock_sessions.initiator);
// let mut responder = LpStateMachine::new(mock_sessions.responder);
//
// assert_eq!(initiator.id().unwrap(), responder.id().unwrap());
//
// // --- Transport Phase ---
// println!("--- Step 1: Initiator sends data ---");
// let data_to_send_1 = LpData::new_opaque(b"hello responder".to_vec());
// let init_actions_4 = initiator.process_input(LpInput::SendData(data_to_send_1.clone()));
// let data_packet_1 = if let Some(Ok(LpAction::SendPacket(packet))) = init_actions_4 {
// packet.clone()
// } else {
// panic!("Initiator should send data packet");
// };
// assert_eq!(data_packet_1.header.receiver_idx(), receiver_index);
//
// println!("--- Step 2: Responder receives data ---");
// let resp_actions_5 = responder.process_input(LpInput::ReceivePacket(data_packet_1));
// let resp_data_1 = if let Some(Ok(LpAction::DeliverData(data))) = resp_actions_5 {
// data
// } else {
// panic!("Responder should deliver data");
// };
// assert_eq!(resp_data_1, data_to_send_1);
//
// println!("--- Step 3: Responder sends data ---");
// let data_to_send_2 = LpData::new_opaque(b"hello initiator".to_vec());
// let resp_actions_6 = responder.process_input(LpInput::SendData(data_to_send_2.clone()));
// let data_packet_2 = if let Some(Ok(LpAction::SendPacket(packet))) = resp_actions_6 {
// packet.clone()
// } else {
// panic!("Responder should send data packet");
// };
// assert_eq!(data_packet_2.header.receiver_idx(), receiver_index);
//
// println!("--- Step 4: Initiator receives data ---");
// let init_actions_5 = initiator.process_input(LpInput::ReceivePacket(data_packet_2));
// if let Some(Ok(LpAction::DeliverData(data))) = init_actions_5 {
// assert_eq!(data, data_to_send_2);
// } else {
// panic!("Initiator should deliver data");
// }
//
// // --- Close ---
// println!("--- Step 5: Initiator closes ---");
// let init_actions_6 = initiator.process_input(LpInput::Close);
// assert!(matches!(
// init_actions_6,
// Some(Ok(LpAction::ConnectionClosed))
// ));
// assert!(matches!(initiator.state, LpState::Closed { .. }));
//
// println!("--- Step 6: Responder closes ---");
// let resp_actions_7 = responder.process_input(LpInput::Close);
// assert!(matches!(
// resp_actions_7,
// Some(Ok(LpAction::ConnectionClosed))
// ));
// assert!(matches!(responder.state, LpState::Closed { .. }));
// }
for kem in KEM::iter() {
let mock_sessions = SessionsMock::mock_post_handshake(kem);
let receiver_index = mock_sessions.responder.receiver_index();
// Create state machines (already in Transport)
let mut initiator = LpStateMachine::new(mock_sessions.initiator);
let mut responder = LpStateMachine::new(mock_sessions.responder);
assert_eq!(
initiator.session_identifier().unwrap(),
responder.session_identifier().unwrap()
);
// --- Transport Phase ---
println!("--- Step 1: Initiator sends data ---");
let data_to_send_1 = LpData::new_opaque(b"hello responder".to_vec());
let init_actions_4 = initiator.process_input(LpInput::SendData(data_to_send_1.clone()));
let data_packet_1 = if let Some(Ok(LpAction::SendPacket(packet))) = init_actions_4 {
packet.clone()
} else {
panic!("Initiator should send data packet");
};
assert_eq!(data_packet_1.outer_header().receiver_idx, receiver_index);
println!("--- Step 2: Responder receives data ---");
let resp_actions_5 = responder.process_input(LpInput::ReceivePacket(data_packet_1));
let resp_data_1 = if let Some(Ok(LpAction::DeliverData(data))) = resp_actions_5 {
data
} else {
panic!("Responder should deliver data");
};
assert_eq!(resp_data_1, data_to_send_1);
println!("--- Step 3: Responder sends data ---");
let data_to_send_2 = LpData::new_opaque(b"hello initiator".to_vec());
let resp_actions_6 = responder.process_input(LpInput::SendData(data_to_send_2.clone()));
let data_packet_2 = if let Some(Ok(LpAction::SendPacket(packet))) = resp_actions_6 {
packet.clone()
} else {
panic!("Responder should send data packet");
};
assert_eq!(data_packet_2.outer_header().receiver_idx, receiver_index);
println!("--- Step 4: Initiator receives data ---");
let init_actions_5 = initiator.process_input(LpInput::ReceivePacket(data_packet_2));
if let Some(Ok(LpAction::DeliverData(data))) = init_actions_5 {
assert_eq!(data, data_to_send_2);
} else {
panic!("Initiator should deliver data");
}
// --- Close ---
println!("--- Step 5: Initiator closes ---");
let init_actions_6 = initiator.process_input(LpInput::Close);
assert!(matches!(
init_actions_6,
Some(Ok(LpAction::ConnectionClosed))
));
assert!(matches!(initiator.state, LpState::Closed { .. }));
println!("--- Step 6: Responder closes ---");
let resp_actions_7 = responder.process_input(LpInput::Close);
assert!(matches!(
resp_actions_7,
Some(Ok(LpAction::ConnectionClosed))
));
assert!(matches!(responder.state, LpState::Closed { .. }));
}
}
}
+1 -1
View File
@@ -5,7 +5,7 @@ use nym_authenticator_requests::AuthenticatorVersion;
use nym_crypto::asymmetric::x25519::serde_helpers::bs58_x25519_pubkey;
use nym_crypto::asymmetric::{ed25519, x25519};
use nym_ip_packet_requests::IpPair;
use nym_kkt_ciphersuite::{Ciphersuite, KEM, KEMKeyDigests, SignatureScheme};
use nym_kkt_ciphersuite::{Ciphersuite, KEM, KEMKeyDigests};
use nym_sphinx::addressing::Recipient;
use serde::{Deserialize, Serialize};
use std::collections::HashMap;
+2 -2
View File
@@ -162,7 +162,7 @@ where
}
Ok(Ok(session)) => session,
};
let receiver_idx = session.id();
let receiver_idx = session.receiver_index();
// 2. insert the state machine into the shared state
let state_machine = LpStateMachine::new(session);
@@ -742,7 +742,7 @@ mod tests {
}
fn add_dummy_lp_state(handler: &mut LpConnectionHandler, session: LpSession) {
let id = session.id();
let id = session.receiver_index();
let state_machine = LpStateMachine::new(session);
handler.bound_receiver_idx = Some(id);
+89 -87
View File
@@ -398,112 +398,115 @@ mod tests {
#[cfg(test)]
mod using_lp_registration_client {
use super::*;
use nym_kkt_ciphersuite::{IntoEnumIterator, KEM};
use nym_registration_client::NestedLpSession;
use nym_test_utils::helpers::u64_seeded_rng_09;
use nym_wireguard::DefguardPeer;
#[tokio::test]
async fn test_basic_lp_entry_registration() -> anyhow::Result<()> {
let TODO = "test with different kems";
let ciphersuite = Ciphersuite::default();
for kem in KEM::iter() {
let ciphersuite = Ciphersuite::default().with_kem(kem);
// nym_test_utils::helpers::setup_test_logger();
// initialise random, but deterministic, keys, addresses, etc. for the parties
let mut client_rng = u64_seeded_rng_09(0);
let mut gateway_rng = u64_seeded_rng_09(1);
// nym_test_utils::helpers::setup_test_logger();
// initialise random, but deterministic, keys, addresses, etc. for the parties
let mut client_rng = u64_seeded_rng_09(0);
let mut gateway_rng = u64_seeded_rng_09(1);
let client_data = Client::mock(&mut client_rng);
let client_key = *client_data.base.x25519_wg_keys.public_key();
let mut entry = Gateway::mock(&mut gateway_rng).await?;
let client_data = Client::mock(&mut client_rng);
let client_key = *client_data.base.x25519_wg_keys.public_key();
let mut entry = Gateway::mock(&mut gateway_rng).await?;
let mut client = LpRegistrationClient::<MockIOStream>::new_with_default_config(
client_data.base.peer.x25519().clone(),
entry.base.peer.as_remote(),
entry.base.socket_addr,
ciphersuite,
entry.base.lp_version,
);
let mut client = LpRegistrationClient::<MockIOStream>::new_with_default_config(
client_data.base.peer.x25519().clone(),
entry.base.peer.as_remote(),
entry.base.socket_addr,
ciphersuite,
entry.base.lp_version,
);
// 1. establish mock connection between client and gateway and retrieve gateway's handle
client.ensure_connected().await?;
let gateway_conn = client
.connection()
.as_ref()
.context("mock connection has failed!")?
.try_get_remote_handle();
// 1. establish mock connection between client and gateway and retrieve gateway's handle
client.ensure_connected().await?;
let gateway_conn = client
.connection()
.as_ref()
.context("mock connection has failed!")?
.try_get_remote_handle();
// 2. create and spawn gateway handler for the client connection
entry.create_lp_handler(gateway_conn, client_data.base.socket_addr);
entry.spawn_lp_handler();
// 2. create and spawn gateway handler for the client connection
entry.create_lp_handler(gateway_conn, client_data.base.socket_addr);
entry.spawn_lp_handler();
// 3. register all needed responses for the dvpn registration that will reach the peer controller
// 1) peer registration - ip pair allocation
let ip_pair = entry.pre_allocate_ip_pair();
let reg_res = Ok::<_, nym_wireguard::Error>(ip_pair);
// 3. register all needed responses for the dvpn registration that will reach the peer controller
// 1) peer registration - ip pair allocation
let ip_pair = entry.pre_allocate_ip_pair();
let reg_res = Ok::<_, nym_wireguard::Error>(ip_pair);
entry
.register_peer_controller_response(
PeerControlRequestType::AllocatePeerIpPair {},
reg_res,
)
.await;
entry
.register_peer_controller_response(
PeerControlRequestType::AllocatePeerIpPair {},
reg_res,
)
.await;
// 2) new peer inclusion - in non-mock system it would spawn handlers,
// here we'll just set a flag and say it's all fine
let public_key = client_key.to_wg_key();
let add_res = Ok::<_, nym_wireguard::Error>(());
entry
.register_peer_controller_response(
PeerControlRequestType::AddPeer { public_key },
add_res,
)
.await;
// 2) new peer inclusion - in non-mock system it would spawn handlers,
// here we'll just set a flag and say it's all fine
let public_key = client_key.to_wg_key();
let add_res = Ok::<_, nym_wireguard::Error>(());
entry
.register_peer_controller_response(
PeerControlRequestType::AddPeer { public_key },
add_res,
)
.await;
// 3) peer query - check for prior registrations
let query_res = Ok::<_, nym_wireguard::Error>(Option::<DefguardPeer>::None);
let key = client_key.to_wg_key();
entry
.register_peer_controller_response(
PeerControlRequestType::QueryPeer { key },
query_res,
)
.await;
// 3) peer query - check for prior registrations
let query_res = Ok::<_, nym_wireguard::Error>(Option::<DefguardPeer>::None);
let key = client_key.to_wg_key();
entry
.register_peer_controller_response(
PeerControlRequestType::QueryPeer { key },
query_res,
)
.await;
// 4. spawn peer controller to be able to handle dvpn registration requests
entry.spawn_peer_controller();
// 4. spawn peer controller to be able to handle dvpn registration requests
entry.spawn_peer_controller();
// 5. perform client handshake
client.perform_handshake().timeboxed().await??;
// 5. perform client handshake
client.perform_handshake().timeboxed().await??;
// 6. perform registration with entry only
let wg_keypair = client_data.base.x25519_wg_keys;
let gateway_identity = entry.base.identity.public_key();
let registration_result = client
.register_dvpn(
&mut client_rng,
&wg_keypair,
gateway_identity,
&client_data.ticket_provider,
TicketType::V1WireguardEntry,
)
.timeboxed()
.await??;
// 6. perform registration with entry only
let wg_keypair = client_data.base.x25519_wg_keys;
let gateway_identity = entry.base.identity.public_key();
let registration_result = client
.register_dvpn(
&mut client_rng,
&wg_keypair,
gateway_identity,
&client_data.ticket_provider,
TicketType::V1WireguardEntry,
)
.timeboxed()
.await??;
// 7. verify registration result
let peers_guard = entry.mock_peer_controller_state.peers.read().await;
let peer = peers_guard.get_by_x25519_key(&client_key).unwrap().clone();
drop(peers_guard);
assert!(peer.add_success);
// 7. verify registration result
let peers_guard = entry.mock_peer_controller_state.peers.read().await;
let peer = peers_guard.get_by_x25519_key(&client_key).unwrap().clone();
drop(peers_guard);
assert!(peer.add_success);
assert_eq!(registration_result.private_ipv4, ip_pair.ipv4);
assert_eq!(registration_result.private_ipv6, ip_pair.ipv6);
assert_eq!(
registration_result.public_key,
*entry.base.x25519_wg_keys.public_key()
);
assert_eq!(registration_result.private_ipv4, ip_pair.ipv4);
assert_eq!(registration_result.private_ipv6, ip_pair.ipv6);
assert_eq!(
registration_result.public_key,
*entry.base.x25519_wg_keys.public_key()
);
// 8. stop the gateway task and finish the test
entry.stop_tasks().await?;
}
// 8. stop the gateway task and finish the test
entry.stop_tasks().await?;
Ok(())
}
@@ -570,7 +573,7 @@ mod tests {
#[tokio::test]
async fn test_basic_lp_exit_registration() -> anyhow::Result<()> {
nym_test_utils::helpers::setup_test_logger();
// nym_test_utils::helpers::setup_test_logger();
let TODO = "test with different kems";
let ciphersuite = Ciphersuite::default();
@@ -705,7 +708,6 @@ mod tests {
let mut nested_session = NestedLpSession::new(
exit.base.socket_addr,
client_data.base.peer.x25519().clone(),
*exit.base.identity.public_key(),
exit.base.peer.as_remote(),
ciphersuite,
exit.base.lp_version,
@@ -60,8 +60,6 @@ impl LpBasedRegistrationClient {
let entry_address = entry_lp_data.address;
let exit_address = exit_lp_data.address;
let exit_identity = self.config.exit.node.identity;
tracing::debug!("Entry gateway LP address: {entry_address}");
tracing::debug!("Exit gateway LP address: {exit_address}");
@@ -103,7 +101,6 @@ impl LpBasedRegistrationClient {
let mut nested_session = NestedLpSession::new(
exit_address,
exit_lp_keypair,
exit_identity,
exit_peer,
exit_ciphersuite,
exit_lp_protocol,
@@ -5,20 +5,16 @@
use super::config::LpRegistrationConfig;
use super::error::{LpClientError, Result};
use crate::lp_client::helpers::{
LpDataDeliverExt, LpDataSendExt, convert_forward_data, try_convert_forward_response,
};
use crate::lp_client::helpers::{LpDataDeliverExt, LpDataSendExt};
use crate::lp_client::nested_session::connection::NestedConnection;
use crate::lp_client::state_machine_helpers::{extract_forwarded_response, prepare_send_packet};
use bytes::BytesMut;
use futures::SinkExt;
use nym_bandwidth_controller::{BandwidthTicketProvider, DEFAULT_TICKETS_TO_SPEND};
use nym_credentials_interface::TicketType;
use nym_crypto::asymmetric::{ed25519, x25519};
use nym_lp::LpSession;
use nym_lp::peer::{DHKeyPair, LpLocalPeer, LpRemotePeer};
use nym_lp::state_machine::{LpAction, LpData, LpInput, LpStateMachine};
use nym_lp::{Ciphersuite, EncryptedLpPacket, ForwardPacketData, packet::version};
use nym_lp::{LpPacket, LpSession};
use nym_lp::state_machine::LpStateMachine;
use nym_lp::{Ciphersuite, EncryptedLpPacket, packet::version};
use nym_lp_transport::traits::LpTransportChannel;
use nym_lp_transport::{LpHandshakeChannel, LpTransportError};
use nym_registration_common::dvpn::LpDvpnRegistrationResponseMessageContent;
@@ -120,13 +116,8 @@ where
}
/// Attempt to use this `LpRegistrationClient` as transport for `NestedSession`
pub fn as_nested_connection(
&mut self,
exit_identity: ed25519::PublicKey,
exit_address: SocketAddr,
) -> NestedConnection<'_, S> {
pub fn as_nested_connection(&mut self, exit_address: SocketAddr) -> NestedConnection<'_, S> {
NestedConnection {
exit_identity,
exit_address,
outer_client: self,
}
@@ -723,7 +714,7 @@ where
pub fn session_id(&self) -> Result<u32> {
self.state_machine()?
.session()
.map(|s| s.id())
.map(|s| s.receiver_index())
.map_err(Into::into)
}
}
@@ -6,8 +6,6 @@
use nym_lp::state_machine::{LpAction, LpDataKind};
use nym_lp::{LpError, MalformedLpPacketError};
use nym_lp_transport::LpTransportError;
use nym_registration_common::BincodeError;
use std::time::Duration;
use thiserror::Error;
/// Errors that can occur during LP client operations.
@@ -74,49 +72,6 @@ pub enum LpClientError {
#[error("{0}")]
Other(String),
// /// Failed to send registration request
// #[error("Failed to send registration request: {0}")]
// SendRegistrationRequest(String),
//
// /// Failed to receive registration response
// #[error("Failed to receive registration response: {0}")]
// ReceiveRegistrationResponse(String),
//
// /// Registration was rejected by gateway
// #[error("Gateway rejected registration: {reason}")]
// RegistrationRejected { reason: String },
//
// /// Failed to receive response within specified deadline
// #[error("Failed to receive response within the set timeout: {timeout:?}")]
// ResponseReceiveTimeout { timeout: Duration },
//
// /// LP transport error
// #[error("LP transport error: {0}")]
// Transport(String),
//
// #[error(transparent)]
// LpTransportError(#[from] LpTransportError),
//
// /// Invalid LP address format
// #[error("Invalid LP address '{address}': {reason}")]
// InvalidAddress { address: String, reason: String },
//
// /// Serialization/deserialization error
// #[error("Serialization error: {0}")]
// Serialization(#[from] BincodeError),
//
// /// Connection closed unexpectedly
// #[error("Connection closed unexpectedly")]
// ConnectionClosed,
//
// /// Timeout waiting for response
// #[error("Timeout waiting for {operation}")]
// Timeout { operation: String },
//
// /// Another uncategorized error
// #[error("{0}")]
// Other(String),
}
impl LpClientError {
@@ -4,7 +4,6 @@
#![allow(dead_code)]
use crate::LpClientError;
use nym_crypto::asymmetric::ed25519;
use nym_lp::ForwardPacketData;
use nym_lp::peer::LpRemotePeer;
use nym_lp::state_machine::{LpAction, LpData, LpDataKind, LpInput};
@@ -4,7 +4,6 @@
use crate::lp_client::helpers::{convert_forward_data, try_convert_forward_response};
use crate::{LpClientError, LpRegistrationClient};
use bytes::{BufMut, BytesMut};
use nym_crypto::asymmetric::ed25519;
use nym_lp::state_machine::{LpAction, LpInput};
use nym_lp::{EncryptedLpPacket, ExpectedResponseSize, ForwardPacketData, KEM};
use nym_lp_transport::traits::{HandshakeMessage, LpTransportChannel};
@@ -14,9 +13,6 @@ use std::net::SocketAddr;
/// Attempt to treat the inner client as a LP connection
pub struct NestedConnection<'a, S> {
/// Remote Ed25519 public key
pub(crate) exit_identity: ed25519::PublicKey,
/// Exit gateway's LP address (e.g., "2.2.2.2:41264")
pub(crate) exit_address: SocketAddr,
@@ -28,7 +28,7 @@ use nym_crypto::asymmetric::{ed25519, x25519};
use nym_lp::packet::version;
use nym_lp::peer::{DHKeyPair, LpLocalPeer, LpRemotePeer};
use nym_lp::state_machine::{LpData, LpStateMachine};
use nym_lp::{Ciphersuite, EncryptedLpPacket, ForwardPacketData, LpPacket, LpSession};
use nym_lp::{Ciphersuite, EncryptedLpPacket, LpSession};
use nym_lp_transport::LpHandshakeChannel;
use nym_lp_transport::traits::LpTransportChannel;
use nym_registration_common::dvpn::LpDvpnRegistrationResponseMessageContent;
@@ -71,9 +71,6 @@ pub struct NestedLpSession {
/// Encapsulates all the client keys needed for the Lewes Protocol.
lp_local_peer: LpLocalPeer,
/// Identity of the exit gateway
gateway_identity: ed25519::PublicKey,
/// Encapsulates all the exit gateway keys needed for the Lewes Protocol.
gateway_lp_peer: LpRemotePeer,
@@ -97,7 +94,6 @@ impl NestedLpSession {
pub fn new(
exit_address: SocketAddr,
client_keypair: Arc<DHKeyPair>,
gateway_identity: ed25519::PublicKey,
gateway_lp_peer: LpRemotePeer,
ciphersuite: Ciphersuite,
gateway_supported_lp_protocol_version: u8,
@@ -117,19 +113,12 @@ impl NestedLpSession {
Self {
exit_address,
lp_local_peer,
gateway_identity,
gateway_lp_peer,
gateway_supported_lp_protocol_version: lp_protocol,
state_machine: None,
}
}
fn state_machine(&self) -> Result<&LpStateMachine> {
self.state_machine
.as_ref()
.ok_or(LpClientError::IncompleteHandshake)
}
fn state_machine_mut(&mut self) -> Result<&mut LpStateMachine> {
self.state_machine
.as_mut()
@@ -178,8 +167,7 @@ impl NestedLpSession {
self.exit_address
);
let mut nested_connection =
outer_client.as_nested_connection(self.gateway_identity, self.exit_address);
let mut nested_connection = outer_client.as_nested_connection(self.exit_address);
let local_peer = self.lp_local_peer.clone();
let remote_peer = self.gateway_lp_peer.clone();
@@ -233,8 +221,7 @@ impl NestedLpSession {
S: LpTransportChannel + LpHandshakeChannel + Unpin,
{
tracing::debug!("Acquiring bandwidth credential for registration");
let mut nested_connection =
outer_client.as_nested_connection(self.gateway_identity, self.exit_address);
let mut nested_connection = outer_client.as_nested_connection(self.exit_address);
// Step 1: Get bandwidth credential from controller
let credential_spending = bandwidth_controller
@@ -341,8 +328,7 @@ impl NestedLpSession {
S: LpTransportChannel + LpHandshakeChannel + Unpin,
R: RngCore + CryptoRng,
{
let mut nested_connection =
outer_client.as_nested_connection(self.gateway_identity, self.exit_address);
let mut nested_connection = outer_client.as_nested_connection(self.exit_address);
tracing::debug!("Building registration request for exit gateway");
@@ -441,8 +427,7 @@ impl NestedLpSession {
/// - Forwarding through entry gateway fails
/// - Response decryption/deserialization fails
/// - Gateway rejects the registration
#[deprecated(note = "use explicit handshake and register methods")]
pub async fn handshake_and_register_dvpn<S, R>(
pub(crate) async fn handshake_and_register_dvpn<S, R>(
&mut self,
outer_client: &mut LpRegistrationClient<S>,
rng: &mut R,
@@ -3,7 +3,7 @@
use crate::LpClientError;
use nym_lp::state_machine::{LpAction, LpData, LpInput};
use nym_lp::{EncryptedLpPacket, LpPacket, LpStateMachine};
use nym_lp::{EncryptedLpPacket, LpStateMachine};
/// Attempt to prepare the provided data for sending by wrapping it in appropriate `LpAction`,
/// and attempting to extract `EncryptedLpPacket` from the provided state machine.