diff options
author | Alyssa Ross <hi@alyssa.is> | 2020-03-26 12:26:18 +0000 |
---|---|---|
committer | Alyssa Ross <hi@alyssa.is> | 2020-03-26 12:26:18 +0000 |
commit | dbd5f925b6b2f4cb1bf87563be4d24c8ed35689a (patch) | |
tree | 5a51c0af87b6a8bb3dfe43d599cabf96523a7f6f /devices/src/virtio/vhost/net.rs | |
parent | 88b7821302043b7ad871fcc0c7748573d0f140e2 (diff) | |
parent | 22964eab8874d41cf0eadf03dfeb1ffb653283e5 (diff) | |
download | crosvm-dbd5f925b6b2f4cb1bf87563be4d24c8ed35689a.tar crosvm-dbd5f925b6b2f4cb1bf87563be4d24c8ed35689a.tar.gz crosvm-dbd5f925b6b2f4cb1bf87563be4d24c8ed35689a.tar.bz2 crosvm-dbd5f925b6b2f4cb1bf87563be4d24c8ed35689a.tar.lz crosvm-dbd5f925b6b2f4cb1bf87563be4d24c8ed35689a.tar.xz crosvm-dbd5f925b6b2f4cb1bf87563be4d24c8ed35689a.tar.zst crosvm-dbd5f925b6b2f4cb1bf87563be4d24c8ed35689a.zip |
Merge remote-tracking branch 'origin/master'
Diffstat (limited to 'devices/src/virtio/vhost/net.rs')
-rw-r--r-- | devices/src/virtio/vhost/net.rs | 66 |
1 files changed, 66 insertions, 0 deletions
diff --git a/devices/src/virtio/vhost/net.rs b/devices/src/virtio/vhost/net.rs index ff72970..542423a 100644 --- a/devices/src/virtio/vhost/net.rs +++ b/devices/src/virtio/vhost/net.rs @@ -14,9 +14,12 @@ use sys_util::{error, warn, EventFd, GuestMemory}; use vhost::NetT as VhostNetT; use virtio_sys::virtio_net; +use super::control_socket::*; use super::worker::Worker; use super::{Error, Result}; +use crate::pci::MsixStatus; use crate::virtio::{Interrupt, Queue, VirtioDevice, TYPE_NET}; +use msg_socket::{MsgReceiver, MsgSender}; const QUEUE_SIZE: u16 = 256; const NUM_QUEUES: usize = 2; @@ -31,6 +34,8 @@ pub struct Net<T: TapT, U: VhostNetT<T>> { vhost_interrupt: Option<Vec<EventFd>>, avail_features: u64, acked_features: u64, + request_socket: Option<VhostDevRequestSocket>, + response_socket: Option<VhostDevResponseSocket>, } impl<T, U> Net<T, U> @@ -85,6 +90,8 @@ where vhost_interrupt.push(EventFd::new().map_err(Error::VhostIrqCreate)?); } + let (request_socket, response_socket) = create_control_sockets(); + Ok(Net { workers_kill_evt: Some(kill_evt.try_clone().map_err(Error::CloneKillEventFd)?), kill_evt, @@ -94,6 +101,8 @@ where vhost_interrupt: Some(vhost_interrupt), avail_features, acked_features: 0u64, + request_socket, + response_socket, }) } } @@ -143,6 +152,14 @@ where } keep_fds.push(self.kill_evt.as_raw_fd()); + if let Some(request_socket) = &self.request_socket { + keep_fds.push(request_socket.as_raw_fd()); + } + + if let Some(response_socket) = &self.response_socket { + keep_fds.push(response_socket.as_raw_fd()); + } + keep_fds } @@ -189,6 +206,11 @@ where if let Some(vhost_interrupt) = self.vhost_interrupt.take() { if let Some(kill_evt) = self.workers_kill_evt.take() { let acked_features = self.acked_features; + let socket = if self.response_socket.is_some() { + self.response_socket.take() + } else { + None + }; let worker_result = thread::Builder::new() .name("vhost_net".to_string()) .spawn(move || { @@ -199,6 +221,7 @@ where interrupt, acked_features, kill_evt, + socket, ); let activate_vqs = |handle: &U| -> Result<()> { for idx in 0..NUM_QUEUES { @@ -251,6 +274,48 @@ where } } + fn control_notify(&self, behavior: MsixStatus) { + if self.worker_thread.is_none() || self.request_socket.is_none() { + return; + } + if let Some(socket) = &self.request_socket { + match behavior { + MsixStatus::EntryChanged(index) => { + if let Err(e) = socket.send(&VhostDevRequest::MsixEntryChanged(index)) { + error!( + "{} failed to send VhostMsixEntryChanged request for entry {}: {:?}", + self.debug_label(), + index, + e + ); + return; + } + if let Err(e) = socket.recv() { + error!("{} failed to receive VhostMsixEntryChanged response for entry {}: {:?}", self.debug_label(), index, e); + } + } + MsixStatus::Changed => { + if let Err(e) = socket.send(&VhostDevRequest::MsixChanged) { + error!( + "{} failed to send VhostMsixChanged request: {:?}", + self.debug_label(), + e + ); + return; + } + if let Err(e) = socket.recv() { + error!( + "{} failed to receive VhostMsixChanged response {:?}", + self.debug_label(), + e + ); + } + } + _ => {} + } + } + } + fn reset(&mut self) -> bool { // Only kill the child if it claimed its eventfd. if self.workers_kill_evt.is_none() && self.kill_evt.write(1).is_err() { @@ -269,6 +334,7 @@ where self.tap = Some(tap); self.vhost_interrupt = Some(worker.vhost_interrupt); self.workers_kill_evt = Some(worker.kill_evt); + self.response_socket = worker.response_socket; return true; } } |