xref: /cloud-hypervisor/vmm/src/lib.rs (revision 5e52729453cb62edbe4fb3a4aa24f8cca31e667e)
1 // Copyright © 2019 Intel Corporation
2 //
3 // SPDX-License-Identifier: Apache-2.0
4 //
5 
6 #[macro_use]
7 extern crate event_monitor;
8 #[macro_use]
9 extern crate log;
10 
11 use crate::api::{
12     ApiError, ApiRequest, ApiResponse, ApiResponsePayload, VmInfo, VmReceiveMigrationData,
13     VmSendMigrationData, VmmPingResponse,
14 };
15 use crate::config::{
16     add_to_config, DeviceConfig, DiskConfig, FsConfig, NetConfig, PmemConfig, RestoreConfig,
17     UserDeviceConfig, VdpaConfig, VmConfig, VsockConfig,
18 };
19 #[cfg(all(target_arch = "x86_64", feature = "guest_debug"))]
20 use crate::coredump::GuestDebuggable;
21 use crate::memory_manager::MemoryManager;
22 #[cfg(all(feature = "kvm", target_arch = "x86_64"))]
23 use crate::migration::get_vm_snapshot;
24 use crate::migration::{recv_vm_config, recv_vm_state};
25 use crate::seccomp_filters::{get_seccomp_filter, Thread};
26 use crate::vm::{Error as VmError, Vm, VmState};
27 use anyhow::anyhow;
28 use libc::{EFD_NONBLOCK, SIGINT, SIGTERM};
29 use memory_manager::MemoryManagerSnapshotData;
30 use pci::PciBdf;
31 use seccompiler::{apply_filter, SeccompAction};
32 use serde::ser::{SerializeStruct, Serializer};
33 use serde::{Deserialize, Serialize};
34 use signal_hook::iterator::{Handle, Signals};
35 use std::collections::HashMap;
36 use std::fs::File;
37 use std::io;
38 use std::io::{Read, Write};
39 use std::os::unix::io::{AsRawFd, FromRawFd, RawFd};
40 use std::os::unix::net::UnixListener;
41 use std::os::unix::net::UnixStream;
42 use std::panic::AssertUnwindSafe;
43 use std::path::PathBuf;
44 use std::sync::mpsc::{Receiver, RecvError, SendError, Sender};
45 use std::sync::{Arc, Mutex};
46 use std::time::Instant;
47 use std::{result, thread};
48 use thiserror::Error;
49 use tracer::trace_scoped;
50 use vm_memory::bitmap::AtomicBitmap;
51 use vm_migration::{protocol::*, Migratable};
52 use vm_migration::{MigratableError, Pausable, Snapshot, Snapshottable, Transportable};
53 use vmm_sys_util::eventfd::EventFd;
54 use vmm_sys_util::signal::unblock_signal;
55 use vmm_sys_util::sock_ctrl_msg::ScmSocket;
56 use vmm_sys_util::terminal::Terminal;
57 
58 mod acpi;
59 pub mod api;
60 mod clone3;
61 pub mod config;
62 #[cfg(all(target_arch = "x86_64", feature = "guest_debug"))]
63 mod coredump;
64 pub mod cpu;
65 pub mod device_manager;
66 pub mod device_tree;
67 #[cfg(feature = "guest_debug")]
68 mod gdb;
69 pub mod interrupt;
70 pub mod memory_manager;
71 pub mod migration;
72 mod pci_segment;
73 pub mod seccomp_filters;
74 mod serial_manager;
75 mod sigwinch_listener;
76 pub mod vm;
77 pub mod vm_config;
78 
79 type GuestMemoryMmap = vm_memory::GuestMemoryMmap<AtomicBitmap>;
80 type GuestRegionMmap = vm_memory::GuestRegionMmap<AtomicBitmap>;
81 
82 /// Errors associated with VMM management
83 #[derive(Debug, Error)]
84 #[allow(clippy::large_enum_variant)]
85 pub enum Error {
86     /// API request receive error
87     #[error("Error receiving API request: {0}")]
88     ApiRequestRecv(#[source] RecvError),
89 
90     /// API response send error
91     #[error("Error sending API request: {0}")]
92     ApiResponseSend(#[source] SendError<ApiResponse>),
93 
94     /// Cannot bind to the UNIX domain socket path
95     #[error("Error binding to UNIX domain socket: {0}")]
96     Bind(#[source] io::Error),
97 
98     /// Cannot clone EventFd.
99     #[error("Error cloning EventFd: {0}")]
100     EventFdClone(#[source] io::Error),
101 
102     /// Cannot create EventFd.
103     #[error("Error creating EventFd: {0}")]
104     EventFdCreate(#[source] io::Error),
105 
106     /// Cannot read from EventFd.
107     #[error("Error reading from EventFd: {0}")]
108     EventFdRead(#[source] io::Error),
109 
110     /// Cannot create epoll context.
111     #[error("Error creating epoll context: {0}")]
112     Epoll(#[source] io::Error),
113 
114     /// Cannot create HTTP thread
115     #[error("Error spawning HTTP thread: {0}")]
116     HttpThreadSpawn(#[source] io::Error),
117 
118     /// Cannot handle the VM STDIN stream
119     #[error("Error handling VM stdin: {0:?}")]
120     Stdin(VmError),
121 
122     /// Cannot handle the VM pty stream
123     #[error("Error handling VM pty: {0:?}")]
124     Pty(VmError),
125 
126     /// Cannot reboot the VM
127     #[error("Error rebooting VM: {0:?}")]
128     VmReboot(VmError),
129 
130     /// Cannot create VMM thread
131     #[error("Error spawning VMM thread {0:?}")]
132     VmmThreadSpawn(#[source] io::Error),
133 
134     /// Cannot shut the VMM down
135     #[error("Error shutting down VMM: {0:?}")]
136     VmmShutdown(VmError),
137 
138     /// Cannot create seccomp filter
139     #[error("Error creating seccomp filter: {0}")]
140     CreateSeccompFilter(seccompiler::Error),
141 
142     /// Cannot apply seccomp filter
143     #[error("Error applying seccomp filter: {0}")]
144     ApplySeccompFilter(seccompiler::Error),
145 
146     /// Error activating virtio devices
147     #[error("Error activating virtio devices: {0:?}")]
148     ActivateVirtioDevices(VmError),
149 
150     /// Error creating API server
151     #[error("Error creating API server {0:?}")]
152     CreateApiServer(micro_http::ServerError),
153 
154     /// Error binding API server socket
155     #[error("Error creation API server's socket {0:?}")]
156     CreateApiServerSocket(#[source] io::Error),
157 
158     #[cfg(feature = "guest_debug")]
159     #[error("Failed to start the GDB thread: {0}")]
160     GdbThreadSpawn(io::Error),
161 
162     /// GDB request receive error
163     #[cfg(feature = "guest_debug")]
164     #[error("Error receiving GDB request: {0}")]
165     GdbRequestRecv(#[source] RecvError),
166 
167     /// GDB response send error
168     #[cfg(feature = "guest_debug")]
169     #[error("Error sending GDB request: {0}")]
170     GdbResponseSend(#[source] SendError<gdb::GdbResponse>),
171 
172     #[error("Cannot spawn a signal handler thread: {0}")]
173     SignalHandlerSpawn(#[source] io::Error),
174 
175     #[error("Failed to join on threads: {0:?}")]
176     ThreadCleanup(std::boxed::Box<dyn std::any::Any + std::marker::Send>),
177 }
178 pub type Result<T> = result::Result<T, Error>;
179 
180 #[derive(Debug, Clone, Copy, PartialEq, Eq)]
181 #[repr(u64)]
182 pub enum EpollDispatch {
183     Exit = 0,
184     Reset = 1,
185     Api = 2,
186     ActivateVirtioDevices = 3,
187     Debug = 4,
188     Unknown,
189 }
190 
191 impl From<u64> for EpollDispatch {
192     fn from(v: u64) -> Self {
193         use EpollDispatch::*;
194         match v {
195             0 => Exit,
196             1 => Reset,
197             2 => Api,
198             3 => ActivateVirtioDevices,
199             4 => Debug,
200             _ => Unknown,
201         }
202     }
203 }
204 
205 pub struct EpollContext {
206     epoll_file: File,
207 }
208 
209 impl EpollContext {
210     pub fn new() -> result::Result<EpollContext, io::Error> {
211         let epoll_fd = epoll::create(true)?;
212         // Use 'File' to enforce closing on 'epoll_fd'
213         // SAFETY: the epoll_fd returned by epoll::create is valid and owned by us.
214         let epoll_file = unsafe { File::from_raw_fd(epoll_fd) };
215 
216         Ok(EpollContext { epoll_file })
217     }
218 
219     pub fn add_event<T>(&mut self, fd: &T, token: EpollDispatch) -> result::Result<(), io::Error>
220     where
221         T: AsRawFd,
222     {
223         let dispatch_index = token as u64;
224         epoll::ctl(
225             self.epoll_file.as_raw_fd(),
226             epoll::ControlOptions::EPOLL_CTL_ADD,
227             fd.as_raw_fd(),
228             epoll::Event::new(epoll::Events::EPOLLIN, dispatch_index),
229         )?;
230 
231         Ok(())
232     }
233 
234     #[cfg(fuzzing)]
235     pub fn add_event_custom<T>(
236         &mut self,
237         fd: &T,
238         id: u64,
239         evts: epoll::Events,
240     ) -> result::Result<(), io::Error>
241     where
242         T: AsRawFd,
243     {
244         epoll::ctl(
245             self.epoll_file.as_raw_fd(),
246             epoll::ControlOptions::EPOLL_CTL_ADD,
247             fd.as_raw_fd(),
248             epoll::Event::new(evts, id),
249         )?;
250 
251         Ok(())
252     }
253 }
254 
255 impl AsRawFd for EpollContext {
256     fn as_raw_fd(&self) -> RawFd {
257         self.epoll_file.as_raw_fd()
258     }
259 }
260 
261 pub struct PciDeviceInfo {
262     pub id: String,
263     pub bdf: PciBdf,
264 }
265 
266 impl Serialize for PciDeviceInfo {
267     fn serialize<S>(&self, serializer: S) -> std::result::Result<S::Ok, S::Error>
268     where
269         S: Serializer,
270     {
271         let bdf_str = self.bdf.to_string();
272 
273         // Serialize the structure.
274         let mut state = serializer.serialize_struct("PciDeviceInfo", 2)?;
275         state.serialize_field("id", &self.id)?;
276         state.serialize_field("bdf", &bdf_str)?;
277         state.end()
278     }
279 }
280 
281 #[allow(unused_variables)]
282 #[allow(clippy::too_many_arguments)]
283 pub fn start_vmm_thread(
284     vmm_version: String,
285     http_path: &Option<String>,
286     http_fd: Option<RawFd>,
287     api_event: EventFd,
288     api_sender: Sender<ApiRequest>,
289     api_receiver: Receiver<ApiRequest>,
290     #[cfg(feature = "guest_debug")] debug_path: Option<PathBuf>,
291     #[cfg(feature = "guest_debug")] debug_event: EventFd,
292     #[cfg(feature = "guest_debug")] vm_debug_event: EventFd,
293     seccomp_action: &SeccompAction,
294     hypervisor: Arc<dyn hypervisor::Hypervisor>,
295 ) -> Result<thread::JoinHandle<Result<()>>> {
296     #[cfg(feature = "guest_debug")]
297     let gdb_hw_breakpoints = hypervisor.get_guest_debug_hw_bps();
298     #[cfg(feature = "guest_debug")]
299     let (gdb_sender, gdb_receiver) = std::sync::mpsc::channel();
300     #[cfg(feature = "guest_debug")]
301     let gdb_debug_event = debug_event.try_clone().map_err(Error::EventFdClone)?;
302     #[cfg(feature = "guest_debug")]
303     let gdb_vm_debug_event = vm_debug_event.try_clone().map_err(Error::EventFdClone)?;
304 
305     let http_api_event = api_event.try_clone().map_err(Error::EventFdClone)?;
306     let hypervisor_type = hypervisor.hypervisor_type();
307 
308     // Retrieve seccomp filter
309     let vmm_seccomp_filter = get_seccomp_filter(seccomp_action, Thread::Vmm, hypervisor_type)
310         .map_err(Error::CreateSeccompFilter)?;
311 
312     let vmm_seccomp_action = seccomp_action.clone();
313     let exit_evt = EventFd::new(EFD_NONBLOCK).map_err(Error::EventFdCreate)?;
314     let thread = {
315         let exit_evt = exit_evt.try_clone().map_err(Error::EventFdClone)?;
316         thread::Builder::new()
317             .name("vmm".to_string())
318             .spawn(move || {
319                 // Apply seccomp filter for VMM thread.
320                 if !vmm_seccomp_filter.is_empty() {
321                     apply_filter(&vmm_seccomp_filter).map_err(Error::ApplySeccompFilter)?;
322                 }
323 
324                 let mut vmm = Vmm::new(
325                     vmm_version.to_string(),
326                     api_event,
327                     #[cfg(feature = "guest_debug")]
328                     debug_event,
329                     #[cfg(feature = "guest_debug")]
330                     vm_debug_event,
331                     vmm_seccomp_action,
332                     hypervisor,
333                     exit_evt,
334                 )?;
335 
336                 vmm.setup_signal_handler()?;
337 
338                 vmm.control_loop(
339                     Arc::new(api_receiver),
340                     #[cfg(feature = "guest_debug")]
341                     Arc::new(gdb_receiver),
342                 )
343             })
344             .map_err(Error::VmmThreadSpawn)?
345     };
346 
347     // The VMM thread is started, we can start serving HTTP requests
348     if let Some(http_path) = http_path {
349         api::start_http_path_thread(
350             http_path,
351             http_api_event,
352             api_sender,
353             seccomp_action,
354             exit_evt,
355             hypervisor_type,
356         )?;
357     } else if let Some(http_fd) = http_fd {
358         api::start_http_fd_thread(
359             http_fd,
360             http_api_event,
361             api_sender,
362             seccomp_action,
363             exit_evt,
364             hypervisor_type,
365         )?;
366     }
367 
368     #[cfg(feature = "guest_debug")]
369     if let Some(debug_path) = debug_path {
370         let target = gdb::GdbStub::new(
371             gdb_sender,
372             gdb_debug_event,
373             gdb_vm_debug_event,
374             gdb_hw_breakpoints,
375         );
376         thread::Builder::new()
377             .name("gdb".to_owned())
378             .spawn(move || gdb::gdb_thread(target, &debug_path))
379             .map_err(Error::GdbThreadSpawn)?;
380     }
381 
382     Ok(thread)
383 }
384 
385 #[derive(Clone, Deserialize, Serialize)]
386 struct VmMigrationConfig {
387     vm_config: Arc<Mutex<VmConfig>>,
388     #[cfg(all(feature = "kvm", target_arch = "x86_64"))]
389     common_cpuid: Vec<hypervisor::arch::x86::CpuIdEntry>,
390     memory_manager_data: MemoryManagerSnapshotData,
391 }
392 
393 pub struct Vmm {
394     epoll: EpollContext,
395     exit_evt: EventFd,
396     reset_evt: EventFd,
397     api_evt: EventFd,
398     #[cfg(feature = "guest_debug")]
399     debug_evt: EventFd,
400     #[cfg(feature = "guest_debug")]
401     vm_debug_evt: EventFd,
402     version: String,
403     vm: Option<Vm>,
404     vm_config: Option<Arc<Mutex<VmConfig>>>,
405     seccomp_action: SeccompAction,
406     hypervisor: Arc<dyn hypervisor::Hypervisor>,
407     activate_evt: EventFd,
408     signals: Option<Handle>,
409     threads: Vec<thread::JoinHandle<()>>,
410 }
411 
412 impl Vmm {
413     pub const HANDLED_SIGNALS: [i32; 2] = [SIGTERM, SIGINT];
414 
415     fn signal_handler(mut signals: Signals, on_tty: bool, exit_evt: &EventFd) {
416         for sig in &Self::HANDLED_SIGNALS {
417             unblock_signal(*sig).unwrap();
418         }
419 
420         for signal in signals.forever() {
421             match signal {
422                 SIGTERM | SIGINT => {
423                     if exit_evt.write(1).is_err() {
424                         // Resetting the terminal is usually done as the VMM exits
425                         if on_tty {
426                             io::stdin()
427                                 .lock()
428                                 .set_canon_mode()
429                                 .expect("failed to restore terminal mode");
430                         }
431                         std::process::exit(1);
432                     }
433                 }
434                 _ => (),
435             }
436         }
437     }
438 
439     fn setup_signal_handler(&mut self) -> Result<()> {
440         let signals = Signals::new(Self::HANDLED_SIGNALS);
441         match signals {
442             Ok(signals) => {
443                 self.signals = Some(signals.handle());
444                 let exit_evt = self.exit_evt.try_clone().map_err(Error::EventFdClone)?;
445                 // SAFETY: trivially safe
446                 let on_tty = unsafe { libc::isatty(libc::STDIN_FILENO) } != 0;
447 
448                 let signal_handler_seccomp_filter = get_seccomp_filter(
449                     &self.seccomp_action,
450                     Thread::SignalHandler,
451                     self.hypervisor.hypervisor_type(),
452                 )
453                 .map_err(Error::CreateSeccompFilter)?;
454                 self.threads.push(
455                     thread::Builder::new()
456                         .name("vmm_signal_handler".to_string())
457                         .spawn(move || {
458                             if !signal_handler_seccomp_filter.is_empty() {
459                                 if let Err(e) = apply_filter(&signal_handler_seccomp_filter)
460                                     .map_err(Error::ApplySeccompFilter)
461                                 {
462                                     error!("Error applying seccomp filter: {:?}", e);
463                                     exit_evt.write(1).ok();
464                                     return;
465                                 }
466                             }
467                             std::panic::catch_unwind(AssertUnwindSafe(|| {
468                                 Vmm::signal_handler(signals, on_tty, &exit_evt);
469                             }))
470                             .map_err(|_| {
471                                 error!("signal_handler thead panicked");
472                                 exit_evt.write(1).ok()
473                             })
474                             .ok();
475                         })
476                         .map_err(Error::SignalHandlerSpawn)?,
477                 );
478             }
479             Err(e) => error!("Signal not found {}", e),
480         }
481         Ok(())
482     }
483 
484     fn new(
485         vmm_version: String,
486         api_evt: EventFd,
487         #[cfg(feature = "guest_debug")] debug_evt: EventFd,
488         #[cfg(feature = "guest_debug")] vm_debug_evt: EventFd,
489         seccomp_action: SeccompAction,
490         hypervisor: Arc<dyn hypervisor::Hypervisor>,
491         exit_evt: EventFd,
492     ) -> Result<Self> {
493         let mut epoll = EpollContext::new().map_err(Error::Epoll)?;
494         let reset_evt = EventFd::new(EFD_NONBLOCK).map_err(Error::EventFdCreate)?;
495         let activate_evt = EventFd::new(EFD_NONBLOCK).map_err(Error::EventFdCreate)?;
496 
497         epoll
498             .add_event(&exit_evt, EpollDispatch::Exit)
499             .map_err(Error::Epoll)?;
500 
501         epoll
502             .add_event(&reset_evt, EpollDispatch::Reset)
503             .map_err(Error::Epoll)?;
504 
505         epoll
506             .add_event(&activate_evt, EpollDispatch::ActivateVirtioDevices)
507             .map_err(Error::Epoll)?;
508 
509         epoll
510             .add_event(&api_evt, EpollDispatch::Api)
511             .map_err(Error::Epoll)?;
512 
513         #[cfg(feature = "guest_debug")]
514         epoll
515             .add_event(&debug_evt, EpollDispatch::Debug)
516             .map_err(Error::Epoll)?;
517 
518         Ok(Vmm {
519             epoll,
520             exit_evt,
521             reset_evt,
522             api_evt,
523             #[cfg(feature = "guest_debug")]
524             debug_evt,
525             #[cfg(feature = "guest_debug")]
526             vm_debug_evt,
527             version: vmm_version,
528             vm: None,
529             vm_config: None,
530             seccomp_action,
531             hypervisor,
532             activate_evt,
533             signals: None,
534             threads: vec![],
535         })
536     }
537 
538     fn vm_create(&mut self, config: Arc<Mutex<VmConfig>>) -> result::Result<(), VmError> {
539         // We only store the passed VM config.
540         // The VM will be created when being asked to boot it.
541         if self.vm_config.is_none() {
542             self.vm_config = Some(config);
543             Ok(())
544         } else {
545             Err(VmError::VmAlreadyCreated)
546         }
547     }
548 
549     fn vm_boot(&mut self) -> result::Result<(), VmError> {
550         tracer::start();
551         let r = {
552             trace_scoped!("vm_boot");
553             // If we don't have a config, we can not boot a VM.
554             if self.vm_config.is_none() {
555                 return Err(VmError::VmMissingConfig);
556             };
557 
558             // Create a new VM if we don't have one yet.
559             if self.vm.is_none() {
560                 let exit_evt = self.exit_evt.try_clone().map_err(VmError::EventFdClone)?;
561                 let reset_evt = self.reset_evt.try_clone().map_err(VmError::EventFdClone)?;
562                 #[cfg(feature = "guest_debug")]
563                 let vm_debug_evt = self
564                     .vm_debug_evt
565                     .try_clone()
566                     .map_err(VmError::EventFdClone)?;
567                 let activate_evt = self
568                     .activate_evt
569                     .try_clone()
570                     .map_err(VmError::EventFdClone)?;
571 
572                 if let Some(ref vm_config) = self.vm_config {
573                     let vm = Vm::new(
574                         Arc::clone(vm_config),
575                         exit_evt,
576                         reset_evt,
577                         #[cfg(feature = "guest_debug")]
578                         vm_debug_evt,
579                         &self.seccomp_action,
580                         self.hypervisor.clone(),
581                         activate_evt,
582                         None,
583                         None,
584                         None,
585                         None,
586                         None,
587                         None,
588                     )?;
589 
590                     self.vm = Some(vm);
591                 }
592             }
593 
594             // Now we can boot the VM.
595             if let Some(ref mut vm) = self.vm {
596                 vm.boot()
597             } else {
598                 Err(VmError::VmNotCreated)
599             }
600         };
601         tracer::end();
602         r
603     }
604 
605     fn vm_pause(&mut self) -> result::Result<(), VmError> {
606         if let Some(ref mut vm) = self.vm {
607             vm.pause().map_err(VmError::Pause)
608         } else {
609             Err(VmError::VmNotRunning)
610         }
611     }
612 
613     fn vm_resume(&mut self) -> result::Result<(), VmError> {
614         if let Some(ref mut vm) = self.vm {
615             vm.resume().map_err(VmError::Resume)
616         } else {
617             Err(VmError::VmNotRunning)
618         }
619     }
620 
621     fn vm_snapshot(&mut self, destination_url: &str) -> result::Result<(), VmError> {
622         if let Some(ref mut vm) = self.vm {
623             vm.snapshot()
624                 .map_err(VmError::Snapshot)
625                 .and_then(|snapshot| {
626                     vm.send(&snapshot, destination_url)
627                         .map_err(VmError::SnapshotSend)
628                 })
629         } else {
630             Err(VmError::VmNotRunning)
631         }
632     }
633 
634     fn vm_restore(&mut self, restore_cfg: RestoreConfig) -> result::Result<(), VmError> {
635         if self.vm.is_some() || self.vm_config.is_some() {
636             return Err(VmError::VmAlreadyCreated);
637         }
638 
639         let source_url = restore_cfg.source_url.as_path().to_str();
640         if source_url.is_none() {
641             return Err(VmError::InvalidRestoreSourceUrl);
642         }
643         // Safe to unwrap as we checked it was Some(&str).
644         let source_url = source_url.unwrap();
645 
646         let vm_config = Arc::new(Mutex::new(
647             recv_vm_config(source_url).map_err(VmError::Restore)?,
648         ));
649         let snapshot = recv_vm_state(source_url).map_err(VmError::Restore)?;
650         #[cfg(all(feature = "kvm", target_arch = "x86_64"))]
651         let vm_snapshot = get_vm_snapshot(&snapshot).map_err(VmError::Restore)?;
652 
653         #[cfg(all(feature = "kvm", target_arch = "x86_64"))]
654         self.vm_check_cpuid_compatibility(&vm_config, &vm_snapshot.common_cpuid)
655             .map_err(VmError::Restore)?;
656 
657         self.vm_config = Some(Arc::clone(&vm_config));
658 
659         let exit_evt = self.exit_evt.try_clone().map_err(VmError::EventFdClone)?;
660         let reset_evt = self.reset_evt.try_clone().map_err(VmError::EventFdClone)?;
661         #[cfg(feature = "guest_debug")]
662         let debug_evt = self
663             .vm_debug_evt
664             .try_clone()
665             .map_err(VmError::EventFdClone)?;
666         let activate_evt = self
667             .activate_evt
668             .try_clone()
669             .map_err(VmError::EventFdClone)?;
670 
671         let vm = Vm::new(
672             vm_config,
673             exit_evt,
674             reset_evt,
675             #[cfg(feature = "guest_debug")]
676             debug_evt,
677             &self.seccomp_action,
678             self.hypervisor.clone(),
679             activate_evt,
680             None,
681             None,
682             None,
683             Some(snapshot),
684             Some(source_url),
685             Some(restore_cfg.prefault),
686         )?;
687         self.vm = Some(vm);
688 
689         // Now we can restore the rest of the VM.
690         if let Some(ref mut vm) = self.vm {
691             vm.restore()
692         } else {
693             Err(VmError::VmNotCreated)
694         }
695     }
696 
697     #[cfg(all(target_arch = "x86_64", feature = "guest_debug"))]
698     fn vm_coredump(&mut self, destination_url: &str) -> result::Result<(), VmError> {
699         if let Some(ref mut vm) = self.vm {
700             vm.coredump(destination_url).map_err(VmError::Coredump)
701         } else {
702             Err(VmError::VmNotRunning)
703         }
704     }
705 
706     fn vm_shutdown(&mut self) -> result::Result<(), VmError> {
707         if let Some(ref mut vm) = self.vm.take() {
708             vm.shutdown()
709         } else {
710             Err(VmError::VmNotRunning)
711         }
712     }
713 
714     fn vm_reboot(&mut self) -> result::Result<(), VmError> {
715         // First we stop the current VM
716         let (config, serial_pty, console_pty, console_resize_pipe) =
717             if let Some(mut vm) = self.vm.take() {
718                 let config = vm.get_config();
719                 let serial_pty = vm.serial_pty();
720                 let console_pty = vm.console_pty();
721                 let console_resize_pipe = vm
722                     .console_resize_pipe()
723                     .as_ref()
724                     .map(|pipe| pipe.try_clone().unwrap());
725                 vm.shutdown()?;
726                 (config, serial_pty, console_pty, console_resize_pipe)
727             } else {
728                 return Err(VmError::VmNotCreated);
729             };
730 
731         let exit_evt = self.exit_evt.try_clone().map_err(VmError::EventFdClone)?;
732         let reset_evt = self.reset_evt.try_clone().map_err(VmError::EventFdClone)?;
733         #[cfg(feature = "guest_debug")]
734         let debug_evt = self
735             .vm_debug_evt
736             .try_clone()
737             .map_err(VmError::EventFdClone)?;
738         let activate_evt = self
739             .activate_evt
740             .try_clone()
741             .map_err(VmError::EventFdClone)?;
742 
743         // The Linux kernel fires off an i8042 reset after doing the ACPI reset so there may be
744         // an event sitting in the shared reset_evt. Without doing this we get very early reboots
745         // during the boot process.
746         if self.reset_evt.read().is_ok() {
747             warn!("Spurious second reset event received. Ignoring.");
748         }
749 
750         // Then we create the new VM
751         let mut vm = Vm::new(
752             config,
753             exit_evt,
754             reset_evt,
755             #[cfg(feature = "guest_debug")]
756             debug_evt,
757             &self.seccomp_action,
758             self.hypervisor.clone(),
759             activate_evt,
760             serial_pty,
761             console_pty,
762             console_resize_pipe,
763             None,
764             None,
765             None,
766         )?;
767 
768         // And we boot it
769         vm.boot()?;
770 
771         self.vm = Some(vm);
772 
773         Ok(())
774     }
775 
776     fn vm_info(&self) -> result::Result<VmInfo, VmError> {
777         match &self.vm_config {
778             Some(config) => {
779                 let state = match &self.vm {
780                     Some(vm) => vm.get_state()?,
781                     None => VmState::Created,
782                 };
783 
784                 let config = Arc::clone(config);
785 
786                 let mut memory_actual_size = config.lock().unwrap().memory.total_size();
787                 if let Some(vm) = &self.vm {
788                     memory_actual_size -= vm.balloon_size();
789                 }
790 
791                 let device_tree = self.vm.as_ref().map(|vm| vm.device_tree());
792 
793                 Ok(VmInfo {
794                     config,
795                     state,
796                     memory_actual_size,
797                     device_tree,
798                 })
799             }
800             None => Err(VmError::VmNotCreated),
801         }
802     }
803 
804     fn vmm_ping(&self) -> VmmPingResponse {
805         VmmPingResponse {
806             version: self.version.clone(),
807         }
808     }
809 
810     fn vm_delete(&mut self) -> result::Result<(), VmError> {
811         if self.vm_config.is_none() {
812             return Ok(());
813         }
814 
815         // If a VM is booted, we first try to shut it down.
816         if self.vm.is_some() {
817             self.vm_shutdown()?;
818         }
819 
820         self.vm_config = None;
821 
822         event!("vm", "deleted");
823 
824         Ok(())
825     }
826 
827     fn vmm_shutdown(&mut self) -> result::Result<(), VmError> {
828         self.vm_delete()?;
829         event!("vmm", "shutdown");
830         Ok(())
831     }
832 
833     fn vm_resize(
834         &mut self,
835         desired_vcpus: Option<u8>,
836         desired_ram: Option<u64>,
837         desired_balloon: Option<u64>,
838     ) -> result::Result<(), VmError> {
839         self.vm_config.as_ref().ok_or(VmError::VmNotCreated)?;
840 
841         if let Some(ref mut vm) = self.vm {
842             if let Err(e) = vm.resize(desired_vcpus, desired_ram, desired_balloon) {
843                 error!("Error when resizing VM: {:?}", e);
844                 Err(e)
845             } else {
846                 Ok(())
847             }
848         } else {
849             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap();
850             if let Some(desired_vcpus) = desired_vcpus {
851                 config.cpus.boot_vcpus = desired_vcpus;
852             }
853             if let Some(desired_ram) = desired_ram {
854                 config.memory.size = desired_ram;
855             }
856             if let Some(desired_balloon) = desired_balloon {
857                 if let Some(balloon_config) = &mut config.balloon {
858                     balloon_config.size = desired_balloon;
859                 }
860             }
861             Ok(())
862         }
863     }
864 
865     fn vm_resize_zone(&mut self, id: String, desired_ram: u64) -> result::Result<(), VmError> {
866         self.vm_config.as_ref().ok_or(VmError::VmNotCreated)?;
867 
868         if let Some(ref mut vm) = self.vm {
869             if let Err(e) = vm.resize_zone(id, desired_ram) {
870                 error!("Error when resizing VM: {:?}", e);
871                 Err(e)
872             } else {
873                 Ok(())
874             }
875         } else {
876             // Update VmConfig by setting the new desired ram.
877             let memory_config = &mut self.vm_config.as_ref().unwrap().lock().unwrap().memory;
878 
879             if let Some(zones) = &mut memory_config.zones {
880                 for zone in zones.iter_mut() {
881                     if zone.id == id {
882                         zone.size = desired_ram;
883                         return Ok(());
884                     }
885                 }
886             }
887 
888             error!("Could not find the memory zone {} for the resize", id);
889             Err(VmError::ResizeZone)
890         }
891     }
892 
893     fn vm_add_device(
894         &mut self,
895         device_cfg: DeviceConfig,
896     ) -> result::Result<Option<Vec<u8>>, VmError> {
897         self.vm_config.as_ref().ok_or(VmError::VmNotCreated)?;
898 
899         {
900             // Validate the configuration change in a cloned configuration
901             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap().clone();
902             add_to_config(&mut config.devices, device_cfg.clone());
903             config.validate().map_err(VmError::ConfigValidation)?;
904         }
905 
906         if let Some(ref mut vm) = self.vm {
907             let info = vm.add_device(device_cfg).map_err(|e| {
908                 error!("Error when adding new device to the VM: {:?}", e);
909                 e
910             })?;
911             serde_json::to_vec(&info)
912                 .map(Some)
913                 .map_err(VmError::SerializeJson)
914         } else {
915             // Update VmConfig by adding the new device.
916             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap();
917             add_to_config(&mut config.devices, device_cfg);
918             Ok(None)
919         }
920     }
921 
922     fn vm_add_user_device(
923         &mut self,
924         device_cfg: UserDeviceConfig,
925     ) -> result::Result<Option<Vec<u8>>, VmError> {
926         self.vm_config.as_ref().ok_or(VmError::VmNotCreated)?;
927 
928         {
929             // Validate the configuration change in a cloned configuration
930             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap().clone();
931             add_to_config(&mut config.user_devices, device_cfg.clone());
932             config.validate().map_err(VmError::ConfigValidation)?;
933         }
934 
935         if let Some(ref mut vm) = self.vm {
936             let info = vm.add_user_device(device_cfg).map_err(|e| {
937                 error!("Error when adding new user device to the VM: {:?}", e);
938                 e
939             })?;
940             serde_json::to_vec(&info)
941                 .map(Some)
942                 .map_err(VmError::SerializeJson)
943         } else {
944             // Update VmConfig by adding the new device.
945             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap();
946             add_to_config(&mut config.user_devices, device_cfg);
947             Ok(None)
948         }
949     }
950 
951     fn vm_remove_device(&mut self, id: String) -> result::Result<(), VmError> {
952         if let Some(ref mut vm) = self.vm {
953             if let Err(e) = vm.remove_device(id) {
954                 error!("Error when removing new device to the VM: {:?}", e);
955                 Err(e)
956             } else {
957                 Ok(())
958             }
959         } else {
960             Err(VmError::VmNotRunning)
961         }
962     }
963 
964     fn vm_add_disk(&mut self, disk_cfg: DiskConfig) -> result::Result<Option<Vec<u8>>, VmError> {
965         self.vm_config.as_ref().ok_or(VmError::VmNotCreated)?;
966 
967         {
968             // Validate the configuration change in a cloned configuration
969             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap().clone();
970             add_to_config(&mut config.disks, disk_cfg.clone());
971             config.validate().map_err(VmError::ConfigValidation)?;
972         }
973 
974         if let Some(ref mut vm) = self.vm {
975             let info = vm.add_disk(disk_cfg).map_err(|e| {
976                 error!("Error when adding new disk to the VM: {:?}", e);
977                 e
978             })?;
979             serde_json::to_vec(&info)
980                 .map(Some)
981                 .map_err(VmError::SerializeJson)
982         } else {
983             // Update VmConfig by adding the new device.
984             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap();
985             add_to_config(&mut config.disks, disk_cfg);
986             Ok(None)
987         }
988     }
989 
990     fn vm_add_fs(&mut self, fs_cfg: FsConfig) -> result::Result<Option<Vec<u8>>, VmError> {
991         self.vm_config.as_ref().ok_or(VmError::VmNotCreated)?;
992 
993         {
994             // Validate the configuration change in a cloned configuration
995             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap().clone();
996             add_to_config(&mut config.fs, fs_cfg.clone());
997             config.validate().map_err(VmError::ConfigValidation)?;
998         }
999 
1000         if let Some(ref mut vm) = self.vm {
1001             let info = vm.add_fs(fs_cfg).map_err(|e| {
1002                 error!("Error when adding new fs to the VM: {:?}", e);
1003                 e
1004             })?;
1005             serde_json::to_vec(&info)
1006                 .map(Some)
1007                 .map_err(VmError::SerializeJson)
1008         } else {
1009             // Update VmConfig by adding the new device.
1010             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap();
1011             add_to_config(&mut config.fs, fs_cfg);
1012             Ok(None)
1013         }
1014     }
1015 
1016     fn vm_add_pmem(&mut self, pmem_cfg: PmemConfig) -> result::Result<Option<Vec<u8>>, VmError> {
1017         self.vm_config.as_ref().ok_or(VmError::VmNotCreated)?;
1018 
1019         {
1020             // Validate the configuration change in a cloned configuration
1021             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap().clone();
1022             add_to_config(&mut config.pmem, pmem_cfg.clone());
1023             config.validate().map_err(VmError::ConfigValidation)?;
1024         }
1025 
1026         if let Some(ref mut vm) = self.vm {
1027             let info = vm.add_pmem(pmem_cfg).map_err(|e| {
1028                 error!("Error when adding new pmem device to the VM: {:?}", e);
1029                 e
1030             })?;
1031             serde_json::to_vec(&info)
1032                 .map(Some)
1033                 .map_err(VmError::SerializeJson)
1034         } else {
1035             // Update VmConfig by adding the new device.
1036             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap();
1037             add_to_config(&mut config.pmem, pmem_cfg);
1038             Ok(None)
1039         }
1040     }
1041 
1042     fn vm_add_net(&mut self, net_cfg: NetConfig) -> result::Result<Option<Vec<u8>>, VmError> {
1043         self.vm_config.as_ref().ok_or(VmError::VmNotCreated)?;
1044 
1045         {
1046             // Validate the configuration change in a cloned configuration
1047             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap().clone();
1048             add_to_config(&mut config.net, net_cfg.clone());
1049             config.validate().map_err(VmError::ConfigValidation)?;
1050         }
1051 
1052         if let Some(ref mut vm) = self.vm {
1053             let info = vm.add_net(net_cfg).map_err(|e| {
1054                 error!("Error when adding new network device to the VM: {:?}", e);
1055                 e
1056             })?;
1057             serde_json::to_vec(&info)
1058                 .map(Some)
1059                 .map_err(VmError::SerializeJson)
1060         } else {
1061             // Update VmConfig by adding the new device.
1062             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap();
1063             add_to_config(&mut config.net, net_cfg);
1064             Ok(None)
1065         }
1066     }
1067 
1068     fn vm_add_vdpa(&mut self, vdpa_cfg: VdpaConfig) -> result::Result<Option<Vec<u8>>, VmError> {
1069         self.vm_config.as_ref().ok_or(VmError::VmNotCreated)?;
1070 
1071         {
1072             // Validate the configuration change in a cloned configuration
1073             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap().clone();
1074             add_to_config(&mut config.vdpa, vdpa_cfg.clone());
1075             config.validate().map_err(VmError::ConfigValidation)?;
1076         }
1077 
1078         if let Some(ref mut vm) = self.vm {
1079             let info = vm.add_vdpa(vdpa_cfg).map_err(|e| {
1080                 error!("Error when adding new vDPA device to the VM: {:?}", e);
1081                 e
1082             })?;
1083             serde_json::to_vec(&info)
1084                 .map(Some)
1085                 .map_err(VmError::SerializeJson)
1086         } else {
1087             // Update VmConfig by adding the new device.
1088             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap();
1089             add_to_config(&mut config.vdpa, vdpa_cfg);
1090             Ok(None)
1091         }
1092     }
1093 
1094     fn vm_add_vsock(&mut self, vsock_cfg: VsockConfig) -> result::Result<Option<Vec<u8>>, VmError> {
1095         self.vm_config.as_ref().ok_or(VmError::VmNotCreated)?;
1096 
1097         {
1098             // Validate the configuration change in a cloned configuration
1099             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap().clone();
1100 
1101             if config.vsock.is_some() {
1102                 return Err(VmError::TooManyVsockDevices);
1103             }
1104 
1105             config.vsock = Some(vsock_cfg.clone());
1106             config.validate().map_err(VmError::ConfigValidation)?;
1107         }
1108 
1109         if let Some(ref mut vm) = self.vm {
1110             let info = vm.add_vsock(vsock_cfg).map_err(|e| {
1111                 error!("Error when adding new vsock device to the VM: {:?}", e);
1112                 e
1113             })?;
1114             serde_json::to_vec(&info)
1115                 .map(Some)
1116                 .map_err(VmError::SerializeJson)
1117         } else {
1118             // Update VmConfig by adding the new device.
1119             let mut config = self.vm_config.as_ref().unwrap().lock().unwrap();
1120             config.vsock = Some(vsock_cfg);
1121             Ok(None)
1122         }
1123     }
1124 
1125     fn vm_counters(&mut self) -> result::Result<Option<Vec<u8>>, VmError> {
1126         if let Some(ref mut vm) = self.vm {
1127             let info = vm.counters().map_err(|e| {
1128                 error!("Error when getting counters from the VM: {:?}", e);
1129                 e
1130             })?;
1131             serde_json::to_vec(&info)
1132                 .map(Some)
1133                 .map_err(VmError::SerializeJson)
1134         } else {
1135             Err(VmError::VmNotRunning)
1136         }
1137     }
1138 
1139     fn vm_power_button(&mut self) -> result::Result<(), VmError> {
1140         if let Some(ref mut vm) = self.vm {
1141             vm.power_button()
1142         } else {
1143             Err(VmError::VmNotRunning)
1144         }
1145     }
1146 
1147     fn vm_receive_config<T>(
1148         &mut self,
1149         req: &Request,
1150         socket: &mut T,
1151         existing_memory_files: Option<HashMap<u32, File>>,
1152     ) -> std::result::Result<Arc<Mutex<MemoryManager>>, MigratableError>
1153     where
1154         T: Read + Write,
1155     {
1156         // Read in config data along with memory manager data
1157         let mut data: Vec<u8> = Vec::new();
1158         data.resize_with(req.length() as usize, Default::default);
1159         socket
1160             .read_exact(&mut data)
1161             .map_err(MigratableError::MigrateSocket)?;
1162 
1163         let vm_migration_config: VmMigrationConfig =
1164             serde_json::from_slice(&data).map_err(|e| {
1165                 MigratableError::MigrateReceive(anyhow!("Error deserialising config: {}", e))
1166             })?;
1167 
1168         #[cfg(all(feature = "kvm", target_arch = "x86_64"))]
1169         self.vm_check_cpuid_compatibility(
1170             &vm_migration_config.vm_config,
1171             &vm_migration_config.common_cpuid,
1172         )?;
1173 
1174         let config = vm_migration_config.vm_config.clone();
1175         self.vm_config = Some(vm_migration_config.vm_config);
1176 
1177         let vm = Vm::create_hypervisor_vm(
1178             &self.hypervisor,
1179             #[cfg(feature = "tdx")]
1180             false,
1181         )
1182         .map_err(|e| {
1183             MigratableError::MigrateReceive(anyhow!(
1184                 "Error creating hypervisor VM from snapshot: {:?}",
1185                 e
1186             ))
1187         })?;
1188 
1189         let phys_bits = vm::physical_bits(config.lock().unwrap().cpus.max_phys_bits);
1190 
1191         let memory_manager = MemoryManager::new(
1192             vm,
1193             &config.lock().unwrap().memory.clone(),
1194             None,
1195             phys_bits,
1196             #[cfg(feature = "tdx")]
1197             false,
1198             Some(&vm_migration_config.memory_manager_data),
1199             existing_memory_files,
1200             #[cfg(target_arch = "x86_64")]
1201             None,
1202         )
1203         .map_err(|e| {
1204             MigratableError::MigrateReceive(anyhow!(
1205                 "Error creating MemoryManager from snapshot: {:?}",
1206                 e
1207             ))
1208         })?;
1209 
1210         Response::ok().write_to(socket)?;
1211 
1212         Ok(memory_manager)
1213     }
1214 
1215     fn vm_receive_state<T>(
1216         &mut self,
1217         req: &Request,
1218         socket: &mut T,
1219         mm: Arc<Mutex<MemoryManager>>,
1220     ) -> std::result::Result<(), MigratableError>
1221     where
1222         T: Read + Write,
1223     {
1224         // Read in state data
1225         let mut data: Vec<u8> = Vec::new();
1226         data.resize_with(req.length() as usize, Default::default);
1227         socket
1228             .read_exact(&mut data)
1229             .map_err(MigratableError::MigrateSocket)?;
1230         let snapshot: Snapshot = serde_json::from_slice(&data).map_err(|e| {
1231             MigratableError::MigrateReceive(anyhow!("Error deserialising snapshot: {}", e))
1232         })?;
1233 
1234         let exit_evt = self.exit_evt.try_clone().map_err(|e| {
1235             MigratableError::MigrateReceive(anyhow!("Error cloning exit EventFd: {}", e))
1236         })?;
1237         let reset_evt = self.reset_evt.try_clone().map_err(|e| {
1238             MigratableError::MigrateReceive(anyhow!("Error cloning reset EventFd: {}", e))
1239         })?;
1240         #[cfg(feature = "guest_debug")]
1241         let debug_evt = self.vm_debug_evt.try_clone().map_err(|e| {
1242             MigratableError::MigrateReceive(anyhow!("Error cloning debug EventFd: {}", e))
1243         })?;
1244         let activate_evt = self.activate_evt.try_clone().map_err(|e| {
1245             MigratableError::MigrateReceive(anyhow!("Error cloning activate EventFd: {}", e))
1246         })?;
1247 
1248         let timestamp = Instant::now();
1249         let hypervisor_vm = mm.lock().unwrap().vm.clone();
1250         let mut vm = Vm::new_from_memory_manager(
1251             self.vm_config.clone().unwrap(),
1252             mm,
1253             hypervisor_vm,
1254             exit_evt,
1255             reset_evt,
1256             #[cfg(feature = "guest_debug")]
1257             debug_evt,
1258             &self.seccomp_action,
1259             self.hypervisor.clone(),
1260             activate_evt,
1261             timestamp,
1262             None,
1263             None,
1264             None,
1265             Some(snapshot),
1266         )
1267         .map_err(|e| {
1268             MigratableError::MigrateReceive(anyhow!("Error creating VM from snapshot: {:?}", e))
1269         })?;
1270 
1271         // Create VM
1272         vm.restore().map_err(|e| {
1273             Response::error().write_to(socket).ok();
1274             MigratableError::MigrateReceive(anyhow!("Failed restoring the Vm: {}", e))
1275         })?;
1276         self.vm = Some(vm);
1277 
1278         Response::ok().write_to(socket)?;
1279 
1280         Ok(())
1281     }
1282 
1283     fn vm_receive_memory<T>(
1284         &mut self,
1285         req: &Request,
1286         socket: &mut T,
1287         memory_manager: &mut MemoryManager,
1288     ) -> std::result::Result<(), MigratableError>
1289     where
1290         T: Read + Write,
1291     {
1292         // Read table
1293         let table = MemoryRangeTable::read_from(socket, req.length())?;
1294 
1295         // And then read the memory itself
1296         memory_manager
1297             .receive_memory_regions(&table, socket)
1298             .map_err(|e| {
1299                 Response::error().write_to(socket).ok();
1300                 e
1301             })?;
1302         Response::ok().write_to(socket)?;
1303         Ok(())
1304     }
1305 
1306     fn socket_url_to_path(url: &str) -> result::Result<PathBuf, MigratableError> {
1307         url.strip_prefix("unix:")
1308             .ok_or_else(|| {
1309                 MigratableError::MigrateSend(anyhow!("Could not extract path from URL: {}", url))
1310             })
1311             .map(|s| s.into())
1312     }
1313 
1314     fn vm_receive_migration(
1315         &mut self,
1316         receive_data_migration: VmReceiveMigrationData,
1317     ) -> result::Result<(), MigratableError> {
1318         info!(
1319             "Receiving migration: receiver_url = {}",
1320             receive_data_migration.receiver_url
1321         );
1322 
1323         let path = Self::socket_url_to_path(&receive_data_migration.receiver_url)?;
1324         let listener = UnixListener::bind(&path).map_err(|e| {
1325             MigratableError::MigrateReceive(anyhow!("Error binding to UNIX socket: {}", e))
1326         })?;
1327         let (mut socket, _addr) = listener.accept().map_err(|e| {
1328             MigratableError::MigrateReceive(anyhow!("Error accepting on UNIX socket: {}", e))
1329         })?;
1330         std::fs::remove_file(&path).map_err(|e| {
1331             MigratableError::MigrateReceive(anyhow!("Error unlinking UNIX socket: {}", e))
1332         })?;
1333 
1334         let mut started = false;
1335         let mut memory_manager: Option<Arc<Mutex<MemoryManager>>> = None;
1336         let mut existing_memory_files = None;
1337         loop {
1338             let req = Request::read_from(&mut socket)?;
1339             match req.command() {
1340                 Command::Invalid => info!("Invalid Command Received"),
1341                 Command::Start => {
1342                     info!("Start Command Received");
1343                     started = true;
1344 
1345                     Response::ok().write_to(&mut socket)?;
1346                 }
1347                 Command::Config => {
1348                     info!("Config Command Received");
1349 
1350                     if !started {
1351                         warn!("Migration not started yet");
1352                         Response::error().write_to(&mut socket)?;
1353                         continue;
1354                     }
1355                     memory_manager = Some(self.vm_receive_config(
1356                         &req,
1357                         &mut socket,
1358                         existing_memory_files.take(),
1359                     )?);
1360                 }
1361                 Command::State => {
1362                     info!("State Command Received");
1363 
1364                     if !started {
1365                         warn!("Migration not started yet");
1366                         Response::error().write_to(&mut socket)?;
1367                         continue;
1368                     }
1369                     if let Some(mm) = memory_manager.take() {
1370                         self.vm_receive_state(&req, &mut socket, mm)?;
1371                     } else {
1372                         warn!("Configuration not sent yet");
1373                         Response::error().write_to(&mut socket)?;
1374                     }
1375                 }
1376                 Command::Memory => {
1377                     info!("Memory Command Received");
1378 
1379                     if !started {
1380                         warn!("Migration not started yet");
1381                         Response::error().write_to(&mut socket)?;
1382                         continue;
1383                     }
1384                     if let Some(mm) = memory_manager.as_ref() {
1385                         self.vm_receive_memory(&req, &mut socket, &mut mm.lock().unwrap())?;
1386                     } else {
1387                         warn!("Configuration not sent yet");
1388                         Response::error().write_to(&mut socket)?;
1389                     }
1390                 }
1391                 Command::MemoryFd => {
1392                     info!("MemoryFd Command Received");
1393 
1394                     if !started {
1395                         warn!("Migration not started yet");
1396                         Response::error().write_to(&mut socket)?;
1397                         continue;
1398                     }
1399 
1400                     let mut buf = [0u8; 4];
1401                     let (_, file) = socket.recv_with_fd(&mut buf).map_err(|e| {
1402                         MigratableError::MigrateReceive(anyhow!(
1403                             "Error receiving slot from socket: {}",
1404                             e
1405                         ))
1406                     })?;
1407 
1408                     if existing_memory_files.is_none() {
1409                         existing_memory_files = Some(HashMap::default())
1410                     }
1411 
1412                     if let Some(ref mut existing_memory_files) = existing_memory_files {
1413                         let slot = u32::from_le_bytes(buf);
1414                         existing_memory_files.insert(slot, file.unwrap());
1415                     }
1416 
1417                     Response::ok().write_to(&mut socket)?;
1418                 }
1419                 Command::Complete => {
1420                     info!("Complete Command Received");
1421                     if let Some(ref mut vm) = self.vm.as_mut() {
1422                         vm.resume()?;
1423                         Response::ok().write_to(&mut socket)?;
1424                     } else {
1425                         warn!("VM not created yet");
1426                         Response::error().write_to(&mut socket)?;
1427                     }
1428                     break;
1429                 }
1430                 Command::Abandon => {
1431                     info!("Abandon Command Received");
1432                     self.vm = None;
1433                     self.vm_config = None;
1434                     Response::ok().write_to(&mut socket).ok();
1435                     break;
1436                 }
1437             }
1438         }
1439 
1440         Ok(())
1441     }
1442 
1443     // Returns true if there were dirty pages to send
1444     fn vm_maybe_send_dirty_pages<T>(
1445         vm: &mut Vm,
1446         socket: &mut T,
1447     ) -> result::Result<bool, MigratableError>
1448     where
1449         T: Read + Write,
1450     {
1451         // Send (dirty) memory table
1452         let table = vm.dirty_log()?;
1453 
1454         // But if there are no regions go straight to pause
1455         if table.regions().is_empty() {
1456             return Ok(false);
1457         }
1458 
1459         Request::memory(table.length()).write_to(socket).unwrap();
1460         table.write_to(socket)?;
1461         // And then the memory itself
1462         vm.send_memory_regions(&table, socket)?;
1463         let res = Response::read_from(socket)?;
1464         if res.status() != Status::Ok {
1465             warn!("Error during dirty memory migration");
1466             Request::abandon().write_to(socket)?;
1467             Response::read_from(socket).ok();
1468             return Err(MigratableError::MigrateSend(anyhow!(
1469                 "Error during dirty memory migration"
1470             )));
1471         }
1472 
1473         Ok(true)
1474     }
1475 
1476     fn send_migration(
1477         vm: &mut Vm,
1478         #[cfg(all(feature = "kvm", target_arch = "x86_64"))] hypervisor: Arc<
1479             dyn hypervisor::Hypervisor,
1480         >,
1481         send_data_migration: VmSendMigrationData,
1482     ) -> result::Result<(), MigratableError> {
1483         let path = Self::socket_url_to_path(&send_data_migration.destination_url)?;
1484         let mut socket = UnixStream::connect(path).map_err(|e| {
1485             MigratableError::MigrateSend(anyhow!("Error connecting to UNIX socket: {}", e))
1486         })?;
1487 
1488         // Start the migration
1489         Request::start().write_to(&mut socket)?;
1490         let res = Response::read_from(&mut socket)?;
1491         if res.status() != Status::Ok {
1492             warn!("Error starting migration");
1493             Request::abandon().write_to(&mut socket)?;
1494             Response::read_from(&mut socket).ok();
1495             return Err(MigratableError::MigrateSend(anyhow!(
1496                 "Error starting migration"
1497             )));
1498         }
1499 
1500         // Send config
1501         let vm_config = vm.get_config();
1502         #[cfg(all(feature = "kvm", target_arch = "x86_64"))]
1503         let common_cpuid = {
1504             let phys_bits = vm::physical_bits(vm_config.lock().unwrap().cpus.max_phys_bits);
1505             arch::generate_common_cpuid(
1506                 &hypervisor,
1507                 None,
1508                 None,
1509                 phys_bits,
1510                 vm_config.lock().unwrap().cpus.kvm_hyperv,
1511                 #[cfg(feature = "tdx")]
1512                 vm_config.lock().unwrap().is_tdx_enabled(),
1513             )
1514             .map_err(|e| {
1515                 MigratableError::MigrateReceive(anyhow!("Error generating common cpuid': {:?}", e))
1516             })?
1517         };
1518 
1519         if send_data_migration.local {
1520             vm.send_memory_fds(&mut socket)?;
1521         }
1522 
1523         let vm_migration_config = VmMigrationConfig {
1524             vm_config,
1525             #[cfg(all(feature = "kvm", target_arch = "x86_64"))]
1526             common_cpuid,
1527             memory_manager_data: vm.memory_manager_data(),
1528         };
1529         let config_data = serde_json::to_vec(&vm_migration_config).unwrap();
1530         Request::config(config_data.len() as u64).write_to(&mut socket)?;
1531         socket
1532             .write_all(&config_data)
1533             .map_err(MigratableError::MigrateSocket)?;
1534         let res = Response::read_from(&mut socket)?;
1535         if res.status() != Status::Ok {
1536             warn!("Error during config migration");
1537             Request::abandon().write_to(&mut socket)?;
1538             Response::read_from(&mut socket).ok();
1539             return Err(MigratableError::MigrateSend(anyhow!(
1540                 "Error during config migration"
1541             )));
1542         }
1543 
1544         // Let every Migratable object know about the migration being started.
1545         vm.start_migration()?;
1546 
1547         if send_data_migration.local {
1548             // Now pause VM
1549             vm.pause()?;
1550         } else {
1551             // Start logging dirty pages
1552             vm.start_dirty_log()?;
1553 
1554             // Send memory table
1555             let table = vm.memory_range_table()?;
1556             Request::memory(table.length())
1557                 .write_to(&mut socket)
1558                 .unwrap();
1559             table.write_to(&mut socket)?;
1560             // And then the memory itself
1561             vm.send_memory_regions(&table, &mut socket)?;
1562             let res = Response::read_from(&mut socket)?;
1563             if res.status() != Status::Ok {
1564                 warn!("Error during memory migration");
1565                 Request::abandon().write_to(&mut socket)?;
1566                 Response::read_from(&mut socket).ok();
1567                 return Err(MigratableError::MigrateSend(anyhow!(
1568                     "Error during memory migration"
1569                 )));
1570             }
1571 
1572             // Try at most 5 passes of dirty memory sending
1573             const MAX_DIRTY_MIGRATIONS: usize = 5;
1574             for i in 0..MAX_DIRTY_MIGRATIONS {
1575                 info!("Dirty memory migration {} of {}", i, MAX_DIRTY_MIGRATIONS);
1576                 if !Self::vm_maybe_send_dirty_pages(vm, &mut socket)? {
1577                     break;
1578                 }
1579             }
1580 
1581             // Now pause VM
1582             vm.pause()?;
1583 
1584             // Send last batch of dirty pages
1585             Self::vm_maybe_send_dirty_pages(vm, &mut socket)?;
1586 
1587             // Stop logging dirty pages
1588             vm.stop_dirty_log()?;
1589         }
1590         // Capture snapshot and send it
1591         let vm_snapshot = vm.snapshot()?;
1592         let snapshot_data = serde_json::to_vec(&vm_snapshot).unwrap();
1593         Request::state(snapshot_data.len() as u64).write_to(&mut socket)?;
1594         socket
1595             .write_all(&snapshot_data)
1596             .map_err(MigratableError::MigrateSocket)?;
1597         let res = Response::read_from(&mut socket)?;
1598         if res.status() != Status::Ok {
1599             warn!("Error during state migration");
1600             Request::abandon().write_to(&mut socket)?;
1601             Response::read_from(&mut socket).ok();
1602             return Err(MigratableError::MigrateSend(anyhow!(
1603                 "Error during state migration"
1604             )));
1605         }
1606 
1607         // Complete the migration
1608         Request::complete().write_to(&mut socket)?;
1609         let res = Response::read_from(&mut socket)?;
1610         if res.status() != Status::Ok {
1611             warn!("Error completing migration");
1612             Request::abandon().write_to(&mut socket)?;
1613             Response::read_from(&mut socket).ok();
1614             return Err(MigratableError::MigrateSend(anyhow!(
1615                 "Error completing migration"
1616             )));
1617         }
1618         info!("Migration complete");
1619 
1620         // Let every Migratable object know about the migration being complete
1621         vm.complete_migration()
1622     }
1623 
1624     fn vm_send_migration(
1625         &mut self,
1626         send_data_migration: VmSendMigrationData,
1627     ) -> result::Result<(), MigratableError> {
1628         info!(
1629             "Sending migration: destination_url = {}, local = {}",
1630             send_data_migration.destination_url, send_data_migration.local
1631         );
1632 
1633         if !self
1634             .vm_config
1635             .as_ref()
1636             .unwrap()
1637             .lock()
1638             .unwrap()
1639             .backed_by_shared_memory()
1640             && send_data_migration.local
1641         {
1642             return Err(MigratableError::MigrateSend(anyhow!(
1643                 "Local migration requires shared memory or hugepages enabled"
1644             )));
1645         }
1646 
1647         if let Some(vm) = self.vm.as_mut() {
1648             Self::send_migration(
1649                 vm,
1650                 #[cfg(all(feature = "kvm", target_arch = "x86_64"))]
1651                 self.hypervisor.clone(),
1652                 send_data_migration,
1653             )
1654             .map_err(|migration_err| {
1655                 error!("Migration failed: {:?}", migration_err);
1656 
1657                 // Stop logging dirty pages
1658                 if let Err(e) = vm.stop_dirty_log() {
1659                     return e;
1660                 }
1661 
1662                 if vm.get_state().unwrap() == VmState::Paused {
1663                     if let Err(e) = vm.resume() {
1664                         return e;
1665                     }
1666                 }
1667 
1668                 migration_err
1669             })?;
1670 
1671             // Shutdown the VM after the migration succeeded
1672             self.exit_evt.write(1).map_err(|e| {
1673                 MigratableError::MigrateSend(anyhow!(
1674                     "Failed shutting down the VM after migration: {:?}",
1675                     e
1676                 ))
1677             })
1678         } else {
1679             Err(MigratableError::MigrateSend(anyhow!("VM is not running")))
1680         }
1681     }
1682 
1683     #[cfg(all(feature = "kvm", target_arch = "x86_64"))]
1684     fn vm_check_cpuid_compatibility(
1685         &self,
1686         src_vm_config: &Arc<Mutex<VmConfig>>,
1687         src_vm_cpuid: &[hypervisor::arch::x86::CpuIdEntry],
1688     ) -> result::Result<(), MigratableError> {
1689         // We check the `CPUID` compatibility of between the source vm and destination, which is
1690         // mostly about feature compatibility and "topology/sgx" leaves are not relevant.
1691         let dest_cpuid = &{
1692             let vm_config = &src_vm_config.lock().unwrap();
1693 
1694             let phys_bits = vm::physical_bits(vm_config.cpus.max_phys_bits);
1695             arch::generate_common_cpuid(
1696                 &self.hypervisor.clone(),
1697                 None,
1698                 None,
1699                 phys_bits,
1700                 vm_config.cpus.kvm_hyperv,
1701                 #[cfg(feature = "tdx")]
1702                 vm_config.is_tdx_enabled(),
1703             )
1704             .map_err(|e| {
1705                 MigratableError::MigrateReceive(anyhow!("Error generating common cpuid: {:?}", e))
1706             })?
1707         };
1708         arch::CpuidFeatureEntry::check_cpuid_compatibility(src_vm_cpuid, dest_cpuid).map_err(|e| {
1709             MigratableError::MigrateReceive(anyhow!(
1710                 "Error checking cpu feature compatibility': {:?}",
1711                 e
1712             ))
1713         })
1714     }
1715 
1716     fn control_loop(
1717         &mut self,
1718         api_receiver: Arc<Receiver<ApiRequest>>,
1719         #[cfg(feature = "guest_debug")] gdb_receiver: Arc<Receiver<gdb::GdbRequest>>,
1720     ) -> Result<()> {
1721         const EPOLL_EVENTS_LEN: usize = 100;
1722 
1723         let mut events = vec![epoll::Event::new(epoll::Events::empty(), 0); EPOLL_EVENTS_LEN];
1724         let epoll_fd = self.epoll.as_raw_fd();
1725 
1726         'outer: loop {
1727             let num_events = match epoll::wait(epoll_fd, -1, &mut events[..]) {
1728                 Ok(res) => res,
1729                 Err(e) => {
1730                     if e.kind() == io::ErrorKind::Interrupted {
1731                         // It's well defined from the epoll_wait() syscall
1732                         // documentation that the epoll loop can be interrupted
1733                         // before any of the requested events occurred or the
1734                         // timeout expired. In both those cases, epoll_wait()
1735                         // returns an error of type EINTR, but this should not
1736                         // be considered as a regular error. Instead it is more
1737                         // appropriate to retry, by calling into epoll_wait().
1738                         continue;
1739                     }
1740                     return Err(Error::Epoll(e));
1741                 }
1742             };
1743 
1744             for event in events.iter().take(num_events) {
1745                 let dispatch_event: EpollDispatch = event.data.into();
1746                 match dispatch_event {
1747                     EpollDispatch::Unknown => {
1748                         let event = event.data;
1749                         warn!("Unknown VMM loop event: {}", event);
1750                     }
1751                     EpollDispatch::Exit => {
1752                         info!("VM exit event");
1753                         // Consume the event.
1754                         self.exit_evt.read().map_err(Error::EventFdRead)?;
1755                         self.vmm_shutdown().map_err(Error::VmmShutdown)?;
1756 
1757                         break 'outer;
1758                     }
1759                     EpollDispatch::Reset => {
1760                         info!("VM reset event");
1761                         // Consume the event.
1762                         self.reset_evt.read().map_err(Error::EventFdRead)?;
1763                         self.vm_reboot().map_err(Error::VmReboot)?;
1764                     }
1765                     EpollDispatch::ActivateVirtioDevices => {
1766                         if let Some(ref vm) = self.vm {
1767                             let count = self.activate_evt.read().map_err(Error::EventFdRead)?;
1768                             info!(
1769                                 "Trying to activate pending virtio devices: count = {}",
1770                                 count
1771                             );
1772                             vm.activate_virtio_devices()
1773                                 .map_err(Error::ActivateVirtioDevices)?;
1774                         }
1775                     }
1776                     EpollDispatch::Api => {
1777                         // Consume the events.
1778                         for _ in 0..self.api_evt.read().map_err(Error::EventFdRead)? {
1779                             // Read from the API receiver channel
1780                             let api_request = api_receiver.recv().map_err(Error::ApiRequestRecv)?;
1781 
1782                             info!("API request event: {:?}", api_request);
1783                             match api_request {
1784                                 ApiRequest::VmCreate(config, sender) => {
1785                                     let response = self
1786                                         .vm_create(config)
1787                                         .map_err(ApiError::VmCreate)
1788                                         .map(|_| ApiResponsePayload::Empty);
1789 
1790                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1791                                 }
1792                                 ApiRequest::VmDelete(sender) => {
1793                                     let response = self
1794                                         .vm_delete()
1795                                         .map_err(ApiError::VmDelete)
1796                                         .map(|_| ApiResponsePayload::Empty);
1797 
1798                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1799                                 }
1800                                 ApiRequest::VmBoot(sender) => {
1801                                     let response = self
1802                                         .vm_boot()
1803                                         .map_err(ApiError::VmBoot)
1804                                         .map(|_| ApiResponsePayload::Empty);
1805 
1806                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1807                                 }
1808                                 ApiRequest::VmShutdown(sender) => {
1809                                     let response = self
1810                                         .vm_shutdown()
1811                                         .map_err(ApiError::VmShutdown)
1812                                         .map(|_| ApiResponsePayload::Empty);
1813 
1814                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1815                                 }
1816                                 ApiRequest::VmReboot(sender) => {
1817                                     let response = self
1818                                         .vm_reboot()
1819                                         .map_err(ApiError::VmReboot)
1820                                         .map(|_| ApiResponsePayload::Empty);
1821 
1822                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1823                                 }
1824                                 ApiRequest::VmInfo(sender) => {
1825                                     let response = self
1826                                         .vm_info()
1827                                         .map_err(ApiError::VmInfo)
1828                                         .map(ApiResponsePayload::VmInfo);
1829 
1830                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1831                                 }
1832                                 ApiRequest::VmmPing(sender) => {
1833                                     let response = ApiResponsePayload::VmmPing(self.vmm_ping());
1834 
1835                                     sender.send(Ok(response)).map_err(Error::ApiResponseSend)?;
1836                                 }
1837                                 ApiRequest::VmPause(sender) => {
1838                                     let response = self
1839                                         .vm_pause()
1840                                         .map_err(ApiError::VmPause)
1841                                         .map(|_| ApiResponsePayload::Empty);
1842 
1843                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1844                                 }
1845                                 ApiRequest::VmResume(sender) => {
1846                                     let response = self
1847                                         .vm_resume()
1848                                         .map_err(ApiError::VmResume)
1849                                         .map(|_| ApiResponsePayload::Empty);
1850 
1851                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1852                                 }
1853                                 ApiRequest::VmSnapshot(snapshot_data, sender) => {
1854                                     let response = self
1855                                         .vm_snapshot(&snapshot_data.destination_url)
1856                                         .map_err(ApiError::VmSnapshot)
1857                                         .map(|_| ApiResponsePayload::Empty);
1858 
1859                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1860                                 }
1861                                 ApiRequest::VmRestore(restore_data, sender) => {
1862                                     let response = self
1863                                         .vm_restore(restore_data.as_ref().clone())
1864                                         .map_err(ApiError::VmRestore)
1865                                         .map(|_| ApiResponsePayload::Empty);
1866 
1867                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1868                                 }
1869                                 #[cfg(all(target_arch = "x86_64", feature = "guest_debug"))]
1870                                 ApiRequest::VmCoredump(coredump_data, sender) => {
1871                                     let response = self
1872                                         .vm_coredump(&coredump_data.destination_url)
1873                                         .map_err(ApiError::VmCoredump)
1874                                         .map(|_| ApiResponsePayload::Empty);
1875 
1876                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1877                                 }
1878                                 ApiRequest::VmmShutdown(sender) => {
1879                                     let response = self
1880                                         .vmm_shutdown()
1881                                         .map_err(ApiError::VmmShutdown)
1882                                         .map(|_| ApiResponsePayload::Empty);
1883 
1884                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1885 
1886                                     break 'outer;
1887                                 }
1888                                 ApiRequest::VmResize(resize_data, sender) => {
1889                                     let response = self
1890                                         .vm_resize(
1891                                             resize_data.desired_vcpus,
1892                                             resize_data.desired_ram,
1893                                             resize_data.desired_balloon,
1894                                         )
1895                                         .map_err(ApiError::VmResize)
1896                                         .map(|_| ApiResponsePayload::Empty);
1897                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1898                                 }
1899                                 ApiRequest::VmResizeZone(resize_zone_data, sender) => {
1900                                     let response = self
1901                                         .vm_resize_zone(
1902                                             resize_zone_data.id.clone(),
1903                                             resize_zone_data.desired_ram,
1904                                         )
1905                                         .map_err(ApiError::VmResizeZone)
1906                                         .map(|_| ApiResponsePayload::Empty);
1907                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1908                                 }
1909                                 ApiRequest::VmAddDevice(add_device_data, sender) => {
1910                                     let response = self
1911                                         .vm_add_device(add_device_data.as_ref().clone())
1912                                         .map_err(ApiError::VmAddDevice)
1913                                         .map(ApiResponsePayload::VmAction);
1914                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1915                                 }
1916                                 ApiRequest::VmAddUserDevice(add_device_data, sender) => {
1917                                     let response = self
1918                                         .vm_add_user_device(add_device_data.as_ref().clone())
1919                                         .map_err(ApiError::VmAddUserDevice)
1920                                         .map(ApiResponsePayload::VmAction);
1921                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1922                                 }
1923                                 ApiRequest::VmRemoveDevice(remove_device_data, sender) => {
1924                                     let response = self
1925                                         .vm_remove_device(remove_device_data.id.clone())
1926                                         .map_err(ApiError::VmRemoveDevice)
1927                                         .map(|_| ApiResponsePayload::Empty);
1928                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1929                                 }
1930                                 ApiRequest::VmAddDisk(add_disk_data, sender) => {
1931                                     let response = self
1932                                         .vm_add_disk(add_disk_data.as_ref().clone())
1933                                         .map_err(ApiError::VmAddDisk)
1934                                         .map(ApiResponsePayload::VmAction);
1935                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1936                                 }
1937                                 ApiRequest::VmAddFs(add_fs_data, sender) => {
1938                                     let response = self
1939                                         .vm_add_fs(add_fs_data.as_ref().clone())
1940                                         .map_err(ApiError::VmAddFs)
1941                                         .map(ApiResponsePayload::VmAction);
1942                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1943                                 }
1944                                 ApiRequest::VmAddPmem(add_pmem_data, sender) => {
1945                                     let response = self
1946                                         .vm_add_pmem(add_pmem_data.as_ref().clone())
1947                                         .map_err(ApiError::VmAddPmem)
1948                                         .map(ApiResponsePayload::VmAction);
1949                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1950                                 }
1951                                 ApiRequest::VmAddNet(add_net_data, sender) => {
1952                                     let response = self
1953                                         .vm_add_net(add_net_data.as_ref().clone())
1954                                         .map_err(ApiError::VmAddNet)
1955                                         .map(ApiResponsePayload::VmAction);
1956                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1957                                 }
1958                                 ApiRequest::VmAddVdpa(add_vdpa_data, sender) => {
1959                                     let response = self
1960                                         .vm_add_vdpa(add_vdpa_data.as_ref().clone())
1961                                         .map_err(ApiError::VmAddVdpa)
1962                                         .map(ApiResponsePayload::VmAction);
1963                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1964                                 }
1965                                 ApiRequest::VmAddVsock(add_vsock_data, sender) => {
1966                                     let response = self
1967                                         .vm_add_vsock(add_vsock_data.as_ref().clone())
1968                                         .map_err(ApiError::VmAddVsock)
1969                                         .map(ApiResponsePayload::VmAction);
1970                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1971                                 }
1972                                 ApiRequest::VmCounters(sender) => {
1973                                     let response = self
1974                                         .vm_counters()
1975                                         .map_err(ApiError::VmInfo)
1976                                         .map(ApiResponsePayload::VmAction);
1977                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1978                                 }
1979                                 ApiRequest::VmReceiveMigration(receive_migration_data, sender) => {
1980                                     let response = self
1981                                         .vm_receive_migration(
1982                                             receive_migration_data.as_ref().clone(),
1983                                         )
1984                                         .map_err(ApiError::VmReceiveMigration)
1985                                         .map(|_| ApiResponsePayload::Empty);
1986                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1987                                 }
1988                                 ApiRequest::VmSendMigration(send_migration_data, sender) => {
1989                                     let response = self
1990                                         .vm_send_migration(send_migration_data.as_ref().clone())
1991                                         .map_err(ApiError::VmSendMigration)
1992                                         .map(|_| ApiResponsePayload::Empty);
1993                                     sender.send(response).map_err(Error::ApiResponseSend)?;
1994                                 }
1995                                 ApiRequest::VmPowerButton(sender) => {
1996                                     let response = self
1997                                         .vm_power_button()
1998                                         .map_err(ApiError::VmPowerButton)
1999                                         .map(|_| ApiResponsePayload::Empty);
2000 
2001                                     sender.send(response).map_err(Error::ApiResponseSend)?;
2002                                 }
2003                             }
2004                         }
2005                     }
2006                     #[cfg(feature = "guest_debug")]
2007                     EpollDispatch::Debug => {
2008                         // Consume the events.
2009                         for _ in 0..self.debug_evt.read().map_err(Error::EventFdRead)? {
2010                             // Read from the API receiver channel
2011                             let gdb_request = gdb_receiver.recv().map_err(Error::GdbRequestRecv)?;
2012 
2013                             let response = if let Some(ref mut vm) = self.vm {
2014                                 vm.debug_request(&gdb_request.payload, gdb_request.cpu_id)
2015                             } else {
2016                                 Err(VmError::VmNotRunning)
2017                             }
2018                             .map_err(gdb::Error::Vm);
2019 
2020                             gdb_request
2021                                 .sender
2022                                 .send(response)
2023                                 .map_err(Error::GdbResponseSend)?;
2024                         }
2025                     }
2026                     #[cfg(not(feature = "guest_debug"))]
2027                     EpollDispatch::Debug => {}
2028                 }
2029             }
2030         }
2031 
2032         // Trigger the termination of the signal_handler thread
2033         if let Some(signals) = self.signals.take() {
2034             signals.close();
2035         }
2036 
2037         // Wait for all the threads to finish
2038         for thread in self.threads.drain(..) {
2039             thread.join().map_err(Error::ThreadCleanup)?
2040         }
2041 
2042         Ok(())
2043     }
2044 }
2045 
2046 const CPU_MANAGER_SNAPSHOT_ID: &str = "cpu-manager";
2047 const MEMORY_MANAGER_SNAPSHOT_ID: &str = "memory-manager";
2048 const DEVICE_MANAGER_SNAPSHOT_ID: &str = "device-manager";
2049 
2050 #[cfg(test)]
2051 mod unit_tests {
2052     use super::*;
2053     use config::{
2054         ConsoleConfig, ConsoleOutputMode, CpusConfig, HotplugMethod, MemoryConfig, PayloadConfig,
2055         RngConfig, VmConfig,
2056     };
2057 
2058     fn create_dummy_vmm() -> Vmm {
2059         Vmm::new(
2060             "dummy".to_string(),
2061             EventFd::new(EFD_NONBLOCK).unwrap(),
2062             #[cfg(feature = "guest_debug")]
2063             EventFd::new(EFD_NONBLOCK).unwrap(),
2064             #[cfg(feature = "guest_debug")]
2065             EventFd::new(EFD_NONBLOCK).unwrap(),
2066             SeccompAction::Allow,
2067             hypervisor::new().unwrap(),
2068             EventFd::new(EFD_NONBLOCK).unwrap(),
2069         )
2070         .unwrap()
2071     }
2072 
2073     fn create_dummy_vm_config() -> Arc<Mutex<VmConfig>> {
2074         Arc::new(Mutex::new(VmConfig {
2075             cpus: CpusConfig {
2076                 boot_vcpus: 1,
2077                 max_vcpus: 1,
2078                 topology: None,
2079                 kvm_hyperv: false,
2080                 max_phys_bits: 46,
2081                 affinity: None,
2082                 features: config::CpuFeatures::default(),
2083             },
2084             memory: MemoryConfig {
2085                 size: 536_870_912,
2086                 mergeable: false,
2087                 hotplug_method: HotplugMethod::Acpi,
2088                 hotplug_size: None,
2089                 hotplugged_size: None,
2090                 shared: true,
2091                 hugepages: false,
2092                 hugepage_size: None,
2093                 prefault: false,
2094                 zones: None,
2095                 thp: true,
2096             },
2097             payload: Some(PayloadConfig {
2098                 kernel: Some(PathBuf::from("/path/to/kernel")),
2099                 ..Default::default()
2100             }),
2101             disks: None,
2102             net: None,
2103             rng: RngConfig {
2104                 src: PathBuf::from("/dev/urandom"),
2105                 iommu: false,
2106             },
2107             balloon: None,
2108             fs: None,
2109             pmem: None,
2110             serial: ConsoleConfig {
2111                 file: None,
2112                 mode: ConsoleOutputMode::Null,
2113                 iommu: false,
2114             },
2115             console: ConsoleConfig {
2116                 file: None,
2117                 mode: ConsoleOutputMode::Tty,
2118                 iommu: false,
2119             },
2120             devices: None,
2121             user_devices: None,
2122             vdpa: None,
2123             vsock: None,
2124             iommu: false,
2125             #[cfg(target_arch = "x86_64")]
2126             sgx_epc: None,
2127             numa: None,
2128             watchdog: false,
2129             #[cfg(feature = "guest_debug")]
2130             gdb: false,
2131             platform: None,
2132             tpm: None,
2133         }))
2134     }
2135 
2136     #[test]
2137     fn test_vmm_vm_create() {
2138         let mut vmm = create_dummy_vmm();
2139         let config = create_dummy_vm_config();
2140 
2141         assert!(matches!(vmm.vm_create(config.clone()), Ok(())));
2142         assert!(matches!(
2143             vmm.vm_create(config),
2144             Err(VmError::VmAlreadyCreated)
2145         ));
2146     }
2147 
2148     #[test]
2149     fn test_vmm_vm_cold_add_device() {
2150         let mut vmm = create_dummy_vmm();
2151         let device_config = DeviceConfig::parse("path=/path/to/device").unwrap();
2152 
2153         assert!(matches!(
2154             vmm.vm_add_device(device_config.clone()),
2155             Err(VmError::VmNotCreated)
2156         ));
2157 
2158         let _ = vmm.vm_create(create_dummy_vm_config());
2159         assert!(vmm
2160             .vm_config
2161             .as_ref()
2162             .unwrap()
2163             .lock()
2164             .unwrap()
2165             .devices
2166             .is_none());
2167 
2168         let result = vmm.vm_add_device(device_config.clone());
2169         assert!(result.is_ok());
2170         assert!(result.unwrap().is_none());
2171         assert_eq!(
2172             vmm.vm_config
2173                 .as_ref()
2174                 .unwrap()
2175                 .lock()
2176                 .unwrap()
2177                 .devices
2178                 .clone()
2179                 .unwrap()
2180                 .len(),
2181             1
2182         );
2183         assert_eq!(
2184             vmm.vm_config
2185                 .as_ref()
2186                 .unwrap()
2187                 .lock()
2188                 .unwrap()
2189                 .devices
2190                 .clone()
2191                 .unwrap()[0],
2192             device_config
2193         );
2194     }
2195 
2196     #[test]
2197     fn test_vmm_vm_cold_add_user_device() {
2198         let mut vmm = create_dummy_vmm();
2199         let user_device_config =
2200             UserDeviceConfig::parse("socket=/path/to/socket,id=8,pci_segment=2").unwrap();
2201 
2202         assert!(matches!(
2203             vmm.vm_add_user_device(user_device_config.clone()),
2204             Err(VmError::VmNotCreated)
2205         ));
2206 
2207         let _ = vmm.vm_create(create_dummy_vm_config());
2208         assert!(vmm
2209             .vm_config
2210             .as_ref()
2211             .unwrap()
2212             .lock()
2213             .unwrap()
2214             .user_devices
2215             .is_none());
2216 
2217         let result = vmm.vm_add_user_device(user_device_config.clone());
2218         assert!(result.is_ok());
2219         assert!(result.unwrap().is_none());
2220         assert_eq!(
2221             vmm.vm_config
2222                 .as_ref()
2223                 .unwrap()
2224                 .lock()
2225                 .unwrap()
2226                 .user_devices
2227                 .clone()
2228                 .unwrap()
2229                 .len(),
2230             1
2231         );
2232         assert_eq!(
2233             vmm.vm_config
2234                 .as_ref()
2235                 .unwrap()
2236                 .lock()
2237                 .unwrap()
2238                 .user_devices
2239                 .clone()
2240                 .unwrap()[0],
2241             user_device_config
2242         );
2243     }
2244 
2245     #[test]
2246     fn test_vmm_vm_cold_add_disk() {
2247         let mut vmm = create_dummy_vmm();
2248         let disk_config = DiskConfig::parse("path=/path/to_file").unwrap();
2249 
2250         assert!(matches!(
2251             vmm.vm_add_disk(disk_config.clone()),
2252             Err(VmError::VmNotCreated)
2253         ));
2254 
2255         let _ = vmm.vm_create(create_dummy_vm_config());
2256         assert!(vmm
2257             .vm_config
2258             .as_ref()
2259             .unwrap()
2260             .lock()
2261             .unwrap()
2262             .disks
2263             .is_none());
2264 
2265         let result = vmm.vm_add_disk(disk_config.clone());
2266         assert!(result.is_ok());
2267         assert!(result.unwrap().is_none());
2268         assert_eq!(
2269             vmm.vm_config
2270                 .as_ref()
2271                 .unwrap()
2272                 .lock()
2273                 .unwrap()
2274                 .disks
2275                 .clone()
2276                 .unwrap()
2277                 .len(),
2278             1
2279         );
2280         assert_eq!(
2281             vmm.vm_config
2282                 .as_ref()
2283                 .unwrap()
2284                 .lock()
2285                 .unwrap()
2286                 .disks
2287                 .clone()
2288                 .unwrap()[0],
2289             disk_config
2290         );
2291     }
2292 
2293     #[test]
2294     fn test_vmm_vm_cold_add_fs() {
2295         let mut vmm = create_dummy_vmm();
2296         let fs_config = FsConfig::parse("tag=mytag,socket=/tmp/sock").unwrap();
2297 
2298         assert!(matches!(
2299             vmm.vm_add_fs(fs_config.clone()),
2300             Err(VmError::VmNotCreated)
2301         ));
2302 
2303         let _ = vmm.vm_create(create_dummy_vm_config());
2304         assert!(vmm.vm_config.as_ref().unwrap().lock().unwrap().fs.is_none());
2305 
2306         let result = vmm.vm_add_fs(fs_config.clone());
2307         assert!(result.is_ok());
2308         assert!(result.unwrap().is_none());
2309         assert_eq!(
2310             vmm.vm_config
2311                 .as_ref()
2312                 .unwrap()
2313                 .lock()
2314                 .unwrap()
2315                 .fs
2316                 .clone()
2317                 .unwrap()
2318                 .len(),
2319             1
2320         );
2321         assert_eq!(
2322             vmm.vm_config
2323                 .as_ref()
2324                 .unwrap()
2325                 .lock()
2326                 .unwrap()
2327                 .fs
2328                 .clone()
2329                 .unwrap()[0],
2330             fs_config
2331         );
2332     }
2333 
2334     #[test]
2335     fn test_vmm_vm_cold_add_pmem() {
2336         let mut vmm = create_dummy_vmm();
2337         let pmem_config = PmemConfig::parse("file=/tmp/pmem,size=128M").unwrap();
2338 
2339         assert!(matches!(
2340             vmm.vm_add_pmem(pmem_config.clone()),
2341             Err(VmError::VmNotCreated)
2342         ));
2343 
2344         let _ = vmm.vm_create(create_dummy_vm_config());
2345         assert!(vmm
2346             .vm_config
2347             .as_ref()
2348             .unwrap()
2349             .lock()
2350             .unwrap()
2351             .pmem
2352             .is_none());
2353 
2354         let result = vmm.vm_add_pmem(pmem_config.clone());
2355         assert!(result.is_ok());
2356         assert!(result.unwrap().is_none());
2357         assert_eq!(
2358             vmm.vm_config
2359                 .as_ref()
2360                 .unwrap()
2361                 .lock()
2362                 .unwrap()
2363                 .pmem
2364                 .clone()
2365                 .unwrap()
2366                 .len(),
2367             1
2368         );
2369         assert_eq!(
2370             vmm.vm_config
2371                 .as_ref()
2372                 .unwrap()
2373                 .lock()
2374                 .unwrap()
2375                 .pmem
2376                 .clone()
2377                 .unwrap()[0],
2378             pmem_config
2379         );
2380     }
2381 
2382     #[test]
2383     fn test_vmm_vm_cold_add_net() {
2384         let mut vmm = create_dummy_vmm();
2385         let net_config = NetConfig::parse(
2386             "mac=de:ad:be:ef:12:34,host_mac=12:34:de:ad:be:ef,vhost_user=true,socket=/tmp/sock",
2387         )
2388         .unwrap();
2389 
2390         assert!(matches!(
2391             vmm.vm_add_net(net_config.clone()),
2392             Err(VmError::VmNotCreated)
2393         ));
2394 
2395         let _ = vmm.vm_create(create_dummy_vm_config());
2396         assert!(vmm
2397             .vm_config
2398             .as_ref()
2399             .unwrap()
2400             .lock()
2401             .unwrap()
2402             .net
2403             .is_none());
2404 
2405         let result = vmm.vm_add_net(net_config.clone());
2406         assert!(result.is_ok());
2407         assert!(result.unwrap().is_none());
2408         assert_eq!(
2409             vmm.vm_config
2410                 .as_ref()
2411                 .unwrap()
2412                 .lock()
2413                 .unwrap()
2414                 .net
2415                 .clone()
2416                 .unwrap()
2417                 .len(),
2418             1
2419         );
2420         assert_eq!(
2421             vmm.vm_config
2422                 .as_ref()
2423                 .unwrap()
2424                 .lock()
2425                 .unwrap()
2426                 .net
2427                 .clone()
2428                 .unwrap()[0],
2429             net_config
2430         );
2431     }
2432 
2433     #[test]
2434     fn test_vmm_vm_cold_add_vdpa() {
2435         let mut vmm = create_dummy_vmm();
2436         let vdpa_config = VdpaConfig::parse("path=/dev/vhost-vdpa,num_queues=2").unwrap();
2437 
2438         assert!(matches!(
2439             vmm.vm_add_vdpa(vdpa_config.clone()),
2440             Err(VmError::VmNotCreated)
2441         ));
2442 
2443         let _ = vmm.vm_create(create_dummy_vm_config());
2444         assert!(vmm
2445             .vm_config
2446             .as_ref()
2447             .unwrap()
2448             .lock()
2449             .unwrap()
2450             .vdpa
2451             .is_none());
2452 
2453         let result = vmm.vm_add_vdpa(vdpa_config.clone());
2454         assert!(result.is_ok());
2455         assert!(result.unwrap().is_none());
2456         assert_eq!(
2457             vmm.vm_config
2458                 .as_ref()
2459                 .unwrap()
2460                 .lock()
2461                 .unwrap()
2462                 .vdpa
2463                 .clone()
2464                 .unwrap()
2465                 .len(),
2466             1
2467         );
2468         assert_eq!(
2469             vmm.vm_config
2470                 .as_ref()
2471                 .unwrap()
2472                 .lock()
2473                 .unwrap()
2474                 .vdpa
2475                 .clone()
2476                 .unwrap()[0],
2477             vdpa_config
2478         );
2479     }
2480 
2481     #[test]
2482     fn test_vmm_vm_cold_add_vsock() {
2483         let mut vmm = create_dummy_vmm();
2484         let vsock_config = VsockConfig::parse("socket=/tmp/sock,cid=1,iommu=on").unwrap();
2485 
2486         assert!(matches!(
2487             vmm.vm_add_vsock(vsock_config.clone()),
2488             Err(VmError::VmNotCreated)
2489         ));
2490 
2491         let _ = vmm.vm_create(create_dummy_vm_config());
2492         assert!(vmm
2493             .vm_config
2494             .as_ref()
2495             .unwrap()
2496             .lock()
2497             .unwrap()
2498             .vsock
2499             .is_none());
2500 
2501         let result = vmm.vm_add_vsock(vsock_config.clone());
2502         assert!(result.is_ok());
2503         assert!(result.unwrap().is_none());
2504         assert_eq!(
2505             vmm.vm_config
2506                 .as_ref()
2507                 .unwrap()
2508                 .lock()
2509                 .unwrap()
2510                 .vsock
2511                 .clone()
2512                 .unwrap(),
2513             vsock_config
2514         );
2515     }
2516 }
2517