#![deny(warnings)] #![allow(dead_code)] //! [TSM.ID].[11031972] -- Platform X Ecosystem //! xcu-labyrinth -- Multi-hop Obfuscated Routing //! Traffic path randomization so no single node knows full route use std::collections::HashMap; #[derive(Debug)] pub enum LabyrinthError { NoRoute(String), NodeFailed(String), EncryptionFailed(String), } impl std::fmt::Display for LabyrinthError { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { match self { Self::NoRoute(e) => write!(f, "No route: {e}"), Self::NodeFailed(e) => write!(f, "Node: {e}"), Self::EncryptionFailed(e) => write!(f, "Encrypt: {e}"), } } } impl std::error::Error for LabyrinthError {} #[derive(Debug, Clone)] pub struct LabyrinthNode { pub id: String, pub latency_ms: u32, pub bandwidth_mbps: u32, pub trust_score: f64, pub country: String, pub is_alive: bool, } /// Onion-layered routing envelope #[derive(Debug, Clone)] pub struct OnionEnvelope { pub layers: Vec, pub total_hops: usize, } #[derive(Debug, Clone)] pub struct EncryptedLayer { pub next_hop: String, pub encrypted_payload: Vec, pub layer_key_hash: u64, } pub struct Labyrinth { nodes: HashMap, min_hops: usize, max_hops: usize, avoid_countries: Vec, entropy_state: u64, } impl Labyrinth { pub fn new(min_hops: usize, max_hops: usize, avoid: Vec) -> Self { Self { nodes: HashMap::new(), min_hops, max_hops, avoid_countries: avoid, entropy_state: 0xa5a5a5a5deadbeef, } } pub fn add_node(&mut self, node: LabyrinthNode) { self.nodes.insert(node.id.clone(), node); } fn next_random(&mut self) -> u64 { self.entropy_state ^= self.entropy_state << 13; self.entropy_state ^= self.entropy_state >> 7; self.entropy_state ^= self.entropy_state << 17; self.entropy_state } /// Select route through the labyrinth pub fn build_route(&mut self, source: &str, destination: &str) -> Result, LabyrinthError> { // Pre-compute random values before borrowing self.nodes let hop_rand = self.next_random(); let node_count = self.nodes.len(); let rand_scores: Vec = (0..node_count) .map(|_| (self.next_random() % 100) as f64 * 0.3) .collect(); let eligible: Vec<&LabyrinthNode> = self.nodes.values() .filter(|n| n.is_alive) .filter(|n| !self.avoid_countries.contains(&n.country)) .filter(|n| n.id != source && n.id != destination) .collect(); if eligible.len() < self.min_hops { return Err(LabyrinthError::NoRoute(format!("Need {} hops, only {} nodes", self.min_hops, eligible.len()))); } let hop_count = self.min_hops + (hop_rand as usize % (self.max_hops - self.min_hops + 1)); let hop_count = hop_count.min(eligible.len()); // Score nodes: prefer high trust, low latency, diverse countries let mut scored: Vec<(&LabyrinthNode, f64)> = eligible.iter().enumerate().map(|(i, n)| { let rand_component = rand_scores.get(i).copied().unwrap_or(0.0); let score = n.trust_score * 50.0 + (1000.0 / (n.latency_ms as f64 + 1.0)) + n.bandwidth_mbps as f64 * 0.1 + rand_component; (*n, score) }).collect(); scored.sort_by(|a, b| b.1.partial_cmp(&a.1).unwrap_or(std::cmp::Ordering::Equal)); // Pick top nodes but ensure country diversity let mut route = vec![source.to_string()]; let mut used_countries = std::collections::HashSet::new(); for (node, _) in &scored { if route.len() - 1 >= hop_count { break; } if !used_countries.contains(&node.country) || route.len() > 3 { route.push(node.id.clone()); used_countries.insert(node.country.clone()); } } route.push(destination.to_string()); Ok(route) } /// Build onion-encrypted envelope for the route pub fn build_onion(&mut self, route: &[String], payload: &[u8]) -> Result { let mut layers = Vec::new(); let mut current_payload = payload.to_vec(); // Build layers from destination back to source (onion wrapping) for i in (1..route.len()).rev() { let next_hop = &route[i]; let layer_key = self.next_random(); // XOR encrypt each layer let encrypted: Vec = current_payload.iter().enumerate() .map(|(j, &b)| b ^ ((layer_key >> ((j % 8) * 8)) & 0xFF) as u8) .collect(); layers.push(EncryptedLayer { next_hop: next_hop.clone(), encrypted_payload: encrypted.clone(), layer_key_hash: layer_key & 0xFFFFFFFF, }); current_payload = encrypted; } layers.reverse(); Ok(OnionEnvelope { layers, total_hops: route.len() - 2 }) } /// Peel one layer of the onion (at each relay node) pub fn peel_layer(&self, layer: &EncryptedLayer, key: u64) -> Vec { layer.encrypted_payload.iter().enumerate() .map(|(j, &b)| b ^ ((key >> ((j % 8) * 8)) & 0xFF) as u8) .collect() } pub fn node_count(&self) -> usize { self.nodes.len() } } #[cfg(test)] mod tests { use super::*; fn make_nodes(lab: &mut Labyrinth) { for (id, country) in [("node-de","DE"),("node-jp","JP"),("node-br","BR"),("node-sg","SG"),("node-ch","CH")] { lab.add_node(LabyrinthNode { id: id.into(), latency_ms: 50, bandwidth_mbps: 100, trust_score: 0.9, country: country.into(), is_alive: true }); } } #[test] fn test_route_building() { let mut lab = Labyrinth::new(2, 4, vec!["CN".into()]); make_nodes(&mut lab); let route = lab.build_route("source", "dest").unwrap(); assert!(route.len() >= 4); assert_eq!(route[0], "source"); assert_eq!(route.last().unwrap(), "dest"); } #[test] fn test_onion_wrap() { let mut lab = Labyrinth::new(2, 3, vec![]); make_nodes(&mut lab); let route = lab.build_route("src", "dst").unwrap(); let envelope = lab.build_onion(&route, b"secret").unwrap(); assert!(envelope.total_hops >= 2); assert!(!envelope.layers.is_empty()); } }