diff --git a/examples/loopback.rs b/examples/loopback.rs index 047f429f..2b637fd1 100644 --- a/examples/loopback.rs +++ b/examples/loopback.rs @@ -77,7 +77,7 @@ fn main() { } let mut device = Loopback::new(); - let mut device = EthernetTracer::new(device, |printer| trace!("{}", printer)); + let mut device = EthernetTracer::new(device, |printer, _timestamp| trace!("{}", printer)); let mut arp_cache_entries: [_; 8] = Default::default(); let mut arp_cache = SliceArpCache::new(&mut arp_cache_entries[..]); diff --git a/examples/tcpdump.rs b/examples/tcpdump.rs index f58ed066..393df75e 100644 --- a/examples/tcpdump.rs +++ b/examples/tcpdump.rs @@ -8,7 +8,7 @@ fn main() { let ifname = env::args().nth(1).unwrap(); let mut socket = RawSocket::new(ifname.as_ref()).unwrap(); loop { - let buffer = socket.receive().unwrap(); + let buffer = socket.receive(/*timestamp=*/0).unwrap(); print!("{}", PrettyPrinter::>::new("", &buffer)) } } diff --git a/examples/utils.rs b/examples/utils.rs index 5aa8f53d..9fe96c55 100644 --- a/examples/utils.rs +++ b/examples/utils.rs @@ -78,7 +78,7 @@ pub fn setup_device(more_args: &[&str]) let seed = SystemTime::now().duration_since(UNIX_EPOCH).unwrap().subsec_nanos(); let device = TapInterface::new(&matches.free[0]).unwrap(); - let device = EthernetTracer::new(device, |printer| trace!("{}", printer)); + let device = EthernetTracer::new(device, |printer, _timestamp| trace!("{}", printer)); let mut device = FaultInjector::new(device, seed); device.set_drop_chance(drop_chance); device.set_corrupt_chance(corrupt_chance); diff --git a/src/iface/ethernet.rs b/src/iface/ethernet.rs index 61cb5f9b..6a2755a4 100644 --- a/src/iface/ethernet.rs +++ b/src/iface/ethernet.rs @@ -116,7 +116,7 @@ impl<'a, 'b, 'c, DeviceT: Device + 'a> Interface<'a, 'b, 'c, DeviceT> { } // Now, receive any incoming packets. - let rx_buffer = self.device.receive()?; + let rx_buffer = self.device.receive(timestamp)?; let eth_frame = EthernetFrame::new_checked(&rx_buffer)?; // Ignore any packets not directed to our hardware address. @@ -134,7 +134,7 @@ impl<'a, 'b, 'c, DeviceT: Device + 'a> Interface<'a, 'b, 'c, DeviceT> { _ => return Err(Error::Unrecognized), }; - self.send_response(response) + self.send_response(timestamp, response) } // Snoop all ARP traffic, and respond to ARP packets directed at us. @@ -360,7 +360,7 @@ impl<'a, 'b, 'c, DeviceT: Device + 'a> Interface<'a, 'b, 'c, DeviceT> { Ok(Response::Icmpv4(ipv4_reply_repr, icmp_reply_repr)) } - fn send_response(&mut self, response: Response) -> Result<(), Error> { + fn send_response(&mut self, timestamp: u64, response: Response) -> Result<(), Error> { macro_rules! ip_response { ($tx_buffer:ident, $frame:ident, $ip_repr:ident) => ({ let dst_hardware_addr = @@ -371,7 +371,7 @@ impl<'a, 'b, 'c, DeviceT: Device + 'a> Interface<'a, 'b, 'c, DeviceT> { let frame_len = EthernetFrame::<&[u8]>::buffer_len($ip_repr.buffer_len() + $ip_repr.payload_len); - $tx_buffer = self.device.transmit(frame_len)?; + $tx_buffer = self.device.transmit(timestamp, frame_len)?; $frame = EthernetFrame::new_checked(&mut $tx_buffer) .expect("transmit frame too small"); $frame.set_src_addr(self.hardware_addr); @@ -387,7 +387,7 @@ impl<'a, 'b, 'c, DeviceT: Device + 'a> Interface<'a, 'b, 'c, DeviceT> { match response { Response::Arp(repr) => { let tx_len = EthernetFrame::<&[u8]>::buffer_len(repr.buffer_len()); - let mut tx_buffer = self.device.transmit(tx_len)?; + let mut tx_buffer = self.device.transmit(timestamp, tx_len)?; let mut frame = EthernetFrame::new_checked(&mut tx_buffer) .expect("transmit frame too small"); frame.set_src_addr(self.hardware_addr); @@ -449,7 +449,7 @@ impl<'a, 'b, 'c, DeviceT: Device + 'a> Interface<'a, 'b, 'c, DeviceT> { Some(dst_hardware_addr) => { let tx_len = EthernetFrame::<&[u8]>::buffer_len(repr.buffer_len() + payload.buffer_len()); - let mut tx_buffer = device.transmit(tx_len)?; + let mut tx_buffer = device.transmit(timestamp, tx_len)?; let mut frame = EthernetFrame::new_checked(&mut tx_buffer) .expect("transmit frame too small"); frame.set_src_addr(src_hardware_addr); @@ -480,7 +480,7 @@ impl<'a, 'b, 'c, DeviceT: Device + 'a> Interface<'a, 'b, 'c, DeviceT> { }; let tx_len = EthernetFrame::<&[u8]>::buffer_len(payload.buffer_len()); - let mut tx_buffer = device.transmit(tx_len)?; + let mut tx_buffer = device.transmit(timestamp, tx_len)?; let mut frame = EthernetFrame::new_checked(&mut tx_buffer) .expect("transmit frame too small"); frame.set_src_addr(src_hardware_addr); diff --git a/src/phy/fault_injector.rs b/src/phy/fault_injector.rs index b0852777..a984d313 100644 --- a/src/phy/fault_injector.rs +++ b/src/phy/fault_injector.rs @@ -229,8 +229,8 @@ impl Device for FaultInjector limits } - fn receive(&mut self) -> Result { - let mut buffer = self.lower.receive()?; + fn receive(&mut self, timestamp: u64) -> Result { + let mut buffer = self.lower.receive(timestamp)?; if self.state.maybe(self.config.drop_pct) { net_trace!("rx: randomly dropping a packet"); return Err(Error::Exhausted) @@ -250,7 +250,7 @@ impl Device for FaultInjector Ok(buffer) } - fn transmit(&mut self, length: usize) -> Result { + fn transmit(&mut self, timestamp: u64, length: usize) -> Result { let buffer; if self.state.maybe(self.config.drop_pct) { net_trace!("tx: randomly dropping a packet"); @@ -262,7 +262,7 @@ impl Device for FaultInjector net_trace!("tx: dropping a packet because of rate limiting"); buffer = None; } else { - buffer = Some(self.lower.transmit(length)?); + buffer = Some(self.lower.transmit(timestamp, length)?); } Ok(TxBuffer { buffer: buffer, diff --git a/src/phy/loopback.rs b/src/phy/loopback.rs index 273d6f1b..62e45fb5 100644 --- a/src/phy/loopback.rs +++ b/src/phy/loopback.rs @@ -39,14 +39,14 @@ impl Device for Loopback { } } - fn receive(&mut self) -> Result { + fn receive(&mut self, _timestamp: u64) -> Result { match self.0.borrow_mut().pop_front() { Some(packet) => Ok(packet), None => Err(Error::Exhausted) } } - fn transmit(&mut self, length: usize) -> Result { + fn transmit(&mut self, _timestamp: u64, length: usize) -> Result { let mut buffer = Vec::new(); buffer.resize(length, 0); Ok(TxBuffer { diff --git a/src/phy/mod.rs b/src/phy/mod.rs index 5e176ffd..f78be886 100644 --- a/src/phy/mod.rs +++ b/src/phy/mod.rs @@ -61,7 +61,7 @@ impl Device for EthernetDevice { limits } - fn receive(&mut self) -> Result { + fn receive(&mut self, _timestamp: u64) -> Result { if rx_full() { let index = self.rx_next; self.rx_next = (self.rx_next + 1) % RX_BUFFERS.len(); @@ -75,7 +75,7 @@ impl Device for EthernetDevice { } } - fn transmit(&mut self, length: usize) -> Result { + fn transmit(&mut self, _timestamp: u64, length: usize) -> Result { if tx_empty() { let index = self.tx_next; self.tx_next = (self.tx_next + 1) % TX_BUFFERS.len(); @@ -175,12 +175,12 @@ pub trait Device { /// It is expected that a `receive` implementation, once a packet is written to memory /// through DMA, would gain ownership of the underlying buffer, provide it for parsing, /// and return it to the network device once it is dropped. - fn receive(&mut self) -> Result; + fn receive(&mut self, timestamp: u64) -> Result; /// Transmit a frame. /// /// It is expected that a `transmit` implementation would gain ownership of a buffer with /// the requested length, provide it for emission, and schedule it to be read from /// memory by the network device once it is dropped. - fn transmit(&mut self, length: usize) -> Result; + fn transmit(&mut self, timestamp: u64, length: usize) -> Result; } diff --git a/src/phy/raw_socket.rs b/src/phy/raw_socket.rs index 8f3f6d5a..599d9704 100644 --- a/src/phy/raw_socket.rs +++ b/src/phy/raw_socket.rs @@ -40,7 +40,7 @@ impl Device for RawSocket { } } - fn receive(&mut self) -> Result { + fn receive(&mut self, _timestamp: u64) -> Result { let mut lower = self.lower.borrow_mut(); let mut buffer = vec![0; self.mtu]; let size = lower.recv(&mut buffer[..]).unwrap(); @@ -48,7 +48,7 @@ impl Device for RawSocket { Ok(buffer) } - fn transmit(&mut self, length: usize) -> Result { + fn transmit(&mut self, _timestamp: u64, length: usize) -> Result { Ok(TxBuffer { lower: self.lower.clone(), buffer: vec![0; length] diff --git a/src/phy/tap_interface.rs b/src/phy/tap_interface.rs index 1680751a..f5e248e4 100644 --- a/src/phy/tap_interface.rs +++ b/src/phy/tap_interface.rs @@ -41,7 +41,7 @@ impl Device for TapInterface { } } - fn receive(&mut self) -> Result { + fn receive(&mut self, _timestamp: u64) -> Result { let mut lower = self.lower.borrow_mut(); let mut buffer = vec![0; self.mtu]; match lower.recv(&mut buffer[..]) { @@ -56,7 +56,7 @@ impl Device for TapInterface { } } - fn transmit(&mut self, length: usize) -> Result { + fn transmit(&mut self, _timestamp: u64, length: usize) -> Result { Ok(TxBuffer { lower: self.lower.clone(), buffer: vec![0; length] diff --git a/src/phy/tracer.rs b/src/phy/tracer.rs index 321f5472..4bb97df3 100644 --- a/src/phy/tracer.rs +++ b/src/phy/tracer.rs @@ -8,26 +8,13 @@ use super::{DeviceLimits, Device}; /// using the provided writer function, and then passes them to another /// device. pub struct Tracer { - lower: T, - writer: fn(PrettyPrinter) + lower: T, + writer: fn(u64, PrettyPrinter) } impl Tracer { /// Create a tracer device. - pub fn new(lower: T, writer: fn(PrettyPrinter)) -> Tracer { - Tracer { - lower: lower, - writer: writer - } - } - - /// Create a tracer device, printing to standard output. - #[cfg(feature = "std")] - pub fn new_stdout(lower: T) -> Tracer { - fn writer(printer: PrettyPrinter) { - print!("{}", printer) - } - + pub fn new(lower: T, writer: fn(timestamp: u64, printer: PrettyPrinter)) -> Tracer { Tracer { lower: lower, writer: writer @@ -46,25 +33,23 @@ impl Device for Tracer { fn limits(&self) -> DeviceLimits { self.lower.limits() } - fn receive(&mut self) -> Result { - let buffer = self.lower.receive()?; - (self.writer)(PrettyPrinter::::new("<- ", &buffer)); + fn receive(&mut self, timestamp: u64) -> Result { + let buffer = self.lower.receive(timestamp)?; + (self.writer)(timestamp, PrettyPrinter::::new("<- ", &buffer)); Ok(buffer) } - fn transmit(&mut self, length: usize) -> Result { - let buffer = self.lower.transmit(length)?; - Ok(TxBuffer { - buffer: buffer, - writer: self.writer - }) + fn transmit(&mut self, timestamp: u64, length: usize) -> Result { + let buffer = self.lower.transmit(timestamp, length)?; + Ok(TxBuffer { buffer, timestamp, writer: self.writer }) } } #[doc(hidden)] pub struct TxBuffer, U: PrettyPrint> { - buffer: T, - writer: fn(PrettyPrinter) + buffer: T, + timestamp: u64, + writer: fn(u64, PrettyPrinter) } impl, U: PrettyPrint> AsRef<[u8]> @@ -79,6 +64,6 @@ impl + AsMut<[u8]>, U: PrettyPrint> AsMut<[u8]> impl, U: PrettyPrint> Drop for TxBuffer { fn drop(&mut self) { - (self.writer)(PrettyPrinter::::new("-> ", &self.buffer)); + (self.writer)(self.timestamp, PrettyPrinter::::new("-> ", &self.buffer)); } }