virtio-devices: vhost_user: Consolidate reset() into VhostUserCommon

The four vhost-user device wrappers (blk, fs, generic_vhost_user, net)
each carried an identical reset() body that resumed the worker thread,
asked the backend to reset, signalled kill_evt and dropped interrupt_cb.
Move the shared body into VhostUserCommon::reset() so behaviour stays in
one place.

No behavioural change.

Signed-off-by: Rob Bradford <rbradford@meta.com>
Assisted-by: Claude:claude-opus-4-7
This commit is contained in:
Rob Bradford
2026-04-26 13:10:54 +01:00
parent 92229a60ed
commit 733d1fe553
5 changed files with 33 additions and 99 deletions

View File

@@ -6,7 +6,6 @@ use std::sync::{Arc, Barrier, Mutex};
use std::{mem, result};
use block::VirtioBlockConfig;
use event_monitor::event;
use log::{error, info};
use seccompiler::SeccompAction;
use vhost::vhost_user::message::{
@@ -309,30 +308,7 @@ impl VirtioDevice for Blk {
}
fn reset(&mut self) -> Option<Arc<dyn VirtioInterrupt>> {
// We first must resume the virtio thread if it was paused.
if self.vu_common.virtio_common.pause_evt.take().is_some() {
self.vu_common.virtio_common.resume().ok()?;
}
if let Some(vu) = &self.vu_common.vu
&& let Err(e) = vu.lock().unwrap().reset_vhost_user()
{
error!(
"Failed to reset vhost-user daemon for socket {}: {e:?}",
self.vu_common.socket_path
);
return None;
}
if let Some(kill_evt) = self.vu_common.virtio_common.kill_evt.take() {
// Ignore the result because there is nothing we can do about it.
let _ = kill_evt.write(1);
}
event!("virtio-device", "reset", "id", &self.id);
// Return the interrupt
Some(self.vu_common.virtio_common.interrupt_cb.take().unwrap())
self.vu_common.reset(&self.id)
}
fn shutdown(&mut self) {

View File

@@ -286,30 +286,7 @@ impl VirtioDevice for Fs {
}
fn reset(&mut self) -> Option<Arc<dyn VirtioInterrupt>> {
// We first must resume the virtio thread if it was paused.
if self.vu_common.virtio_common.pause_evt.take().is_some() {
self.vu_common.virtio_common.resume().ok()?;
}
if let Some(vu) = &self.vu_common.vu
&& let Err(e) = vu.lock().unwrap().reset_vhost_user()
{
error!(
"Failed to reset vhost-user daemon for socket {}: {e:?}",
self.vu_common.socket_path
);
return None;
}
if let Some(kill_evt) = self.vu_common.virtio_common.kill_evt.take() {
// Ignore the result because there is nothing we can do about it.
let _ = kill_evt.write(1);
}
event!("virtio-device", "reset", "id", &self.id);
// Return the interrupt
Some(self.vu_common.virtio_common.interrupt_cb.take().unwrap())
self.vu_common.reset(&self.id)
}
fn shutdown(&mut self) {

View File

@@ -309,30 +309,7 @@ impl VirtioDevice for GenericVhostUser {
}
fn reset(&mut self) -> Option<Arc<dyn VirtioInterrupt>> {
// We first must resume the virtio thread if it was paused.
if self.vu_common.virtio_common.pause_evt.take().is_some() {
self.vu_common.virtio_common.resume().ok()?;
}
if let Some(vu) = &self.vu_common.vu
&& let Err(e) = vu.lock().unwrap().reset_vhost_user()
{
error!(
"Failed to reset vhost-user daemon for socket {}: {e:?}",
self.vu_common.socket_path
);
return None;
}
if let Some(kill_evt) = self.vu_common.virtio_common.kill_evt.take() {
// Ignore the result because there is nothing we can do about it.
let _ = kill_evt.write(1);
}
event!("virtio-device", "reset", "id", &self.id);
// Return the interrupt
Some(self.vu_common.virtio_common.interrupt_cb.take().unwrap())
self.vu_common.reset(&self.id)
}
fn shutdown(&mut self) {

View File

@@ -8,6 +8,7 @@ use std::sync::{Arc, Barrier, Mutex};
use std::{io, thread};
use anyhow::anyhow;
use event_monitor::event;
use log::error;
use serde::{Deserialize, Serialize};
use thiserror::Error;
@@ -21,7 +22,7 @@ use vm_memory::guest_memory::Error as MmapError;
use vm_memory::mmap::MmapRegionError;
use vm_memory::{Address, GuestAddressSpace, GuestMemory, GuestMemoryAtomic};
use vm_migration::protocol::MemoryRangeTable;
use vm_migration::{MigratableError, Snapshot};
use vm_migration::{MigratableError, Pausable, Snapshot};
use vmm_sys_util::eventfd::EventFd;
use vu_common_ctrl::VhostUserHandle;
@@ -427,6 +428,33 @@ impl VhostUserCommon {
Ok(())
}
pub fn reset(&mut self, id: &str) -> Option<Arc<dyn VirtioInterrupt>> {
// We first must resume the virtio thread if it was paused.
if self.virtio_common.pause_evt.take().is_some() {
self.virtio_common.resume().ok()?;
}
if let Some(vu) = &self.vu
&& let Err(e) = vu.lock().unwrap().reset_vhost_user()
{
error!(
"Failed to reset vhost-user daemon for socket {}: {e:?}",
self.socket_path
);
return None;
}
if let Some(kill_evt) = self.virtio_common.kill_evt.take() {
// Ignore the result because there is nothing we can do about it.
let _ = kill_evt.write(1);
}
event!("virtio-device", "reset", "id", id);
// Return the interrupt
Some(self.virtio_common.interrupt_cb.take().unwrap())
}
pub fn shutdown(&mut self) {
// Signal the epoll thread to exit, unpause it (it may be parked
// if the VM was paused for migration), then wait for it to finish.

View File

@@ -5,7 +5,6 @@ use std::sync::atomic::AtomicBool;
use std::sync::{Arc, Barrier, Mutex};
use std::{result, thread};
use event_monitor::event;
use log::{error, info};
use net_util::{CtrlQueue, MacAddr, VirtioNetConfig, build_net_config_space};
use seccompiler::SeccompAction;
@@ -366,30 +365,7 @@ impl VirtioDevice for Net {
}
fn reset(&mut self) -> Option<Arc<dyn VirtioInterrupt>> {
// We first must resume the virtio thread if it was paused.
if self.vu_common.virtio_common.pause_evt.take().is_some() {
self.vu_common.virtio_common.resume().ok()?;
}
if let Some(vu) = &self.vu_common.vu
&& let Err(e) = vu.lock().unwrap().reset_vhost_user()
{
error!(
"Failed to reset vhost-user daemon for socket {}: {e:?}",
self.vu_common.socket_path
);
return None;
}
if let Some(kill_evt) = self.vu_common.virtio_common.kill_evt.take() {
// Ignore the result because there is nothing we can do about it.
let _ = kill_evt.write(1);
}
event!("virtio-device", "reset", "id", &self.id);
// Return the interrupt
Some(self.vu_common.virtio_common.interrupt_cb.take().unwrap())
self.vu_common.reset(&self.id)
}
fn shutdown(&mut self) {