rns_core/transport/
outbound_engine.rs1use super::*;
2
3impl TransportEngine {
4 pub fn handle_outbound<B: crate::packet::PacketStorage>(
6 &mut self,
7 packet: &RawPacket<B>,
8 dest_type: u8,
9 attached_interface: Option<InterfaceId>,
10 now: f64,
11 ) -> Vec<TransportAction> {
12 let mut actions = Vec::new();
13 self.handle_outbound_into(packet, dest_type, attached_interface, now, &mut actions);
14 actions
15 }
16
17 pub fn handle_outbound_into<B: crate::packet::PacketStorage>(
20 &mut self,
21 packet: &RawPacket<B>,
22 dest_type: u8,
23 attached_interface: Option<InterfaceId>,
24 now: f64,
25 actions: &mut Vec<TransportAction>,
26 ) {
27 if packet.hops >= constants::PATHFINDER_M {
28 return;
29 }
30
31 let uses_path = packet.flags.packet_type != constants::PACKET_TYPE_ANNOUNCE
32 && dest_type != constants::DESTINATION_PLAIN
33 && dest_type != constants::DESTINATION_GROUP
34 && !(dest_type == constants::DESTINATION_LINK && attached_interface.is_some());
35 if uses_path {
36 if let Some(path_set) = self.path_table.get_mut(&packet.destination_hash) {
37 if let Some(entry) = path_set.primary_mut() {
38 entry.used = now;
39 }
40 }
41 }
42
43 let start = actions.len();
44 route_outbound_into(
45 &self.path_table,
46 &self.interfaces,
47 &self.local_destinations,
48 packet,
49 dest_type,
50 attached_interface,
51 OutboundRouteOptions {
52 identity_hash: self.config.identity_hash,
53 local_hops_delta: self.config.local_hops_delta,
54 },
55 actions,
56 );
57
58 if !packet.is_unhashed_link_resource() {
62 self.packet_hashlist.add(packet.packet_hash);
63 }
64
65 if packet.flags.packet_type == constants::PACKET_TYPE_ANNOUNCE && packet.hops > 0 {
67 let routed: Vec<TransportAction> = actions.drain(start..).collect();
68 let gated =
69 self.gate_announce_actions(routed, &packet.destination_hash, packet.hops, now);
70 actions.extend(gated);
71 }
72 }
73
74 fn gate_announce_actions(
76 &mut self,
77 actions: Vec<TransportAction>,
78 dest_hash: &[u8; 16],
79 hops: u8,
80 now: f64,
81 ) -> Vec<TransportAction> {
82 let mut result = Vec::new();
83 for action in actions {
84 match action {
85 TransportAction::SendOnInterface { interface, raw } => {
86 let (bitrate, airtime_profile, announce_cap) =
87 if let Some(info) = self.interfaces.get(&interface) {
88 (info.bitrate, info.airtime_profile, info.announce_cap)
89 } else {
90 (None, None, constants::ANNOUNCE_CAP)
91 };
92 if let Some(send_action) = self.announce_queues.gate_announce(
93 interface,
94 raw,
95 *dest_hash,
96 hops,
97 now,
98 now,
99 bitrate,
100 airtime_profile,
101 announce_cap,
102 ) {
103 result.push(send_action);
104 }
105 }
107 other => result.push(other),
108 }
109 }
110 result
111 }
112}