arcbox_virtio_net/
backend.rs1use std::collections::VecDeque;
4
5use crate::header::NetPacket;
6
7#[derive(Debug, Clone, Copy, Default)]
14pub struct NetOffloadFlags {
15 pub csum: bool,
18 pub tso4: bool,
20 pub tso6: bool,
22 pub tso_ecn: bool,
24 pub ufo: bool,
26}
27
28pub trait NetBackend: Send + Sync {
30 fn send(&mut self, packet: &NetPacket) -> std::io::Result<usize>;
32
33 fn send_tso(&mut self, packet: &NetPacket) -> std::io::Result<usize> {
43 self.send(packet)
44 }
45
46 fn recv(&mut self, buf: &mut [u8]) -> std::io::Result<usize>;
48
49 fn has_data(&self) -> bool;
51
52 fn supports_tso(&self) -> bool {
57 false
58 }
59
60 fn configure_offload(&mut self, flags: NetOffloadFlags) -> std::io::Result<()> {
67 let _ = flags;
68 Ok(())
69 }
70
71 fn set_vnet_hdr_sz(&mut self, size: u32) -> std::io::Result<()> {
78 let _ = size;
79 Ok(())
80 }
81}
82
83pub struct LoopbackBackend {
85 packets: VecDeque<Vec<u8>>,
87}
88
89impl LoopbackBackend {
90 #[must_use]
92 pub const fn new() -> Self {
93 Self {
94 packets: VecDeque::new(),
95 }
96 }
97}
98
99impl Default for LoopbackBackend {
100 fn default() -> Self {
101 Self::new()
102 }
103}
104
105impl NetBackend for LoopbackBackend {
106 fn send(&mut self, packet: &NetPacket) -> std::io::Result<usize> {
107 self.packets.push_back(packet.data.clone());
108 Ok(packet.data.len())
109 }
110
111 fn recv(&mut self, buf: &mut [u8]) -> std::io::Result<usize> {
112 if let Some(packet) = self.packets.pop_front() {
113 let len = packet.len().min(buf.len());
114 buf[..len].copy_from_slice(&packet[..len]);
115 Ok(len)
116 } else {
117 Ok(0)
118 }
119 }
120
121 fn has_data(&self) -> bool {
122 !self.packets.is_empty()
123 }
124}
125
126#[cfg(test)]
127mod tests {
128 use super::*;
129
130 #[test]
131 fn test_loopback_backend_new() {
132 let backend = LoopbackBackend::new();
133 assert!(!backend.has_data());
134 }
135
136 #[test]
137 fn test_loopback_backend_default() {
138 let backend = LoopbackBackend::default();
139 assert!(!backend.has_data());
140 }
141
142 #[test]
143 fn test_loopback_backend_send_recv() {
144 let mut backend = LoopbackBackend::new();
145
146 let packet = NetPacket::new(vec![1, 2, 3, 4, 5]);
147 let sent = backend.send(&packet).unwrap();
148 assert_eq!(sent, 5);
149
150 assert!(backend.has_data());
151
152 let mut buf = [0u8; 10];
153 let n = backend.recv(&mut buf).unwrap();
154 assert_eq!(n, 5);
155 assert_eq!(&buf[..n], &[1, 2, 3, 4, 5]);
156
157 assert!(!backend.has_data());
158 }
159
160 #[test]
161 fn test_loopback_backend_recv_empty() {
162 let mut backend = LoopbackBackend::new();
163
164 let mut buf = [0u8; 10];
165 let n = backend.recv(&mut buf).unwrap();
166 assert_eq!(n, 0);
167 }
168
169 #[test]
170 fn test_loopback_backend_multiple_packets() {
171 let mut backend = LoopbackBackend::new();
172
173 for i in 0..5 {
174 let packet = NetPacket::new(vec![i; 10]);
175 backend.send(&packet).unwrap();
176 }
177
178 for i in 0..5 {
179 assert!(backend.has_data());
180 let mut buf = [0u8; 20];
181 let n = backend.recv(&mut buf).unwrap();
182 assert_eq!(n, 10);
183 assert!(buf[..n].iter().all(|&b| b == i));
184 }
185
186 assert!(!backend.has_data());
187 }
188
189 #[test]
190 fn test_loopback_backend_small_buffer() {
191 let mut backend = LoopbackBackend::new();
192
193 let packet = NetPacket::new(vec![0xAA; 100]);
194 backend.send(&packet).unwrap();
195
196 let mut buf = [0u8; 10];
197 let n = backend.recv(&mut buf).unwrap();
198 assert_eq!(n, 10);
199 assert!(buf.iter().all(|&b| b == 0xAA));
200 }
201
202 #[test]
203 fn test_loopback_large_packet() {
204 let mut backend = LoopbackBackend::new();
205
206 let data = vec![0xAB; 65536];
207 let packet = NetPacket::new(data.clone());
208 let sent = backend.send(&packet).unwrap();
209 assert_eq!(sent, 65536);
210
211 let mut buf = vec![0u8; 65536];
212 let n = backend.recv(&mut buf).unwrap();
213 assert_eq!(n, 65536);
214 assert_eq!(buf, data);
215 }
216
217 #[test]
218 fn test_loopback_supports_tso_default_false() {
219 let backend = LoopbackBackend::new();
220 assert!(!backend.supports_tso());
221 }
222}