mirror of
https://github.com/cloud-hypervisor/cloud-hypervisor.git
synced 2024-10-02 11:35:46 +00:00
arch, vmm: Extend the data being snapshot
Storing multiple data coming from the MemoryManager in order to be able to restore without creating everything from scratch. Signed-off-by: Sebastien Boeuf <sebastien.boeuf@intel.com>
This commit is contained in:
parent
f440976a7c
commit
5b177b205b
@ -17,6 +17,9 @@ use std::collections::BTreeMap;
|
|||||||
use std::fmt;
|
use std::fmt;
|
||||||
use std::result;
|
use std::result;
|
||||||
use std::sync::Arc;
|
use std::sync::Arc;
|
||||||
|
use versionize::{VersionMap, Versionize, VersionizeError, VersionizeResult};
|
||||||
|
use versionize_derive::Versionize;
|
||||||
|
use vm_migration::VersionMapped;
|
||||||
|
|
||||||
type GuestMemoryMmap = vm_memory::GuestMemoryMmap<vm_memory::bitmap::AtomicBitmap>;
|
type GuestMemoryMmap = vm_memory::GuestMemoryMmap<vm_memory::bitmap::AtomicBitmap>;
|
||||||
type GuestRegionMmap = vm_memory::GuestRegionMmap<vm_memory::bitmap::AtomicBitmap>;
|
type GuestRegionMmap = vm_memory::GuestRegionMmap<vm_memory::bitmap::AtomicBitmap>;
|
||||||
@ -54,7 +57,7 @@ pub enum Error {
|
|||||||
pub type Result<T> = result::Result<T, Error>;
|
pub type Result<T> = result::Result<T, Error>;
|
||||||
|
|
||||||
/// Type for memory region types.
|
/// Type for memory region types.
|
||||||
#[derive(PartialEq, Debug)]
|
#[derive(Clone, Copy, PartialEq, Debug, Versionize)]
|
||||||
pub enum RegionType {
|
pub enum RegionType {
|
||||||
/// RAM type
|
/// RAM type
|
||||||
Ram,
|
Ram,
|
||||||
@ -72,6 +75,8 @@ pub enum RegionType {
|
|||||||
Reserved,
|
Reserved,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl VersionMapped for RegionType {}
|
||||||
|
|
||||||
/// Module for aarch64 related functionality.
|
/// Module for aarch64 related functionality.
|
||||||
#[cfg(target_arch = "aarch64")]
|
#[cfg(target_arch = "aarch64")]
|
||||||
pub mod aarch64;
|
pub mod aarch64;
|
||||||
|
@ -63,7 +63,7 @@ const MPOL_BIND: u32 = 2;
|
|||||||
const MPOL_MF_STRICT: u32 = 1;
|
const MPOL_MF_STRICT: u32 = 1;
|
||||||
const MPOL_MF_MOVE: u32 = 1 << 1;
|
const MPOL_MF_MOVE: u32 = 1 << 1;
|
||||||
|
|
||||||
#[derive(Default)]
|
#[derive(Clone, Default, Versionize)]
|
||||||
struct HotPlugState {
|
struct HotPlugState {
|
||||||
base: u64,
|
base: u64,
|
||||||
length: u64,
|
length: u64,
|
||||||
@ -121,6 +121,7 @@ impl MemoryZone {
|
|||||||
|
|
||||||
pub type MemoryZones = HashMap<String, MemoryZone>;
|
pub type MemoryZones = HashMap<String, MemoryZone>;
|
||||||
|
|
||||||
|
#[derive(Clone, Versionize)]
|
||||||
struct GuestRamMapping {
|
struct GuestRamMapping {
|
||||||
slot: u32,
|
slot: u32,
|
||||||
gpa: u64,
|
gpa: u64,
|
||||||
@ -130,6 +131,13 @@ struct GuestRamMapping {
|
|||||||
file_offset: u64,
|
file_offset: u64,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Clone, Versionize)]
|
||||||
|
struct ArchMemRegion {
|
||||||
|
base: u64,
|
||||||
|
size: usize,
|
||||||
|
r_type: RegionType,
|
||||||
|
}
|
||||||
|
|
||||||
pub struct MemoryManager {
|
pub struct MemoryManager {
|
||||||
boot_guest_memory: GuestMemoryMmap,
|
boot_guest_memory: GuestMemoryMmap,
|
||||||
guest_memory: GuestMemoryAtomic<GuestMemoryMmap>,
|
guest_memory: GuestMemoryAtomic<GuestMemoryMmap>,
|
||||||
@ -155,7 +163,7 @@ pub struct MemoryManager {
|
|||||||
snapshot_memory_ranges: MemoryRangeTable,
|
snapshot_memory_ranges: MemoryRangeTable,
|
||||||
memory_zones: MemoryZones,
|
memory_zones: MemoryZones,
|
||||||
log_dirty: bool, // Enable dirty logging for created RAM regions
|
log_dirty: bool, // Enable dirty logging for created RAM regions
|
||||||
arch_mem_regions: Vec<(GuestAddress, usize, RegionType)>,
|
arch_mem_regions: Vec<ArchMemRegion>,
|
||||||
|
|
||||||
// Keep track of calls to create_userspace_mapping() for guest RAM.
|
// Keep track of calls to create_userspace_mapping() for guest RAM.
|
||||||
// This is useful for getting the dirty pages as we need to know the
|
// This is useful for getting the dirty pages as we need to know the
|
||||||
@ -784,7 +792,7 @@ impl MemoryManager {
|
|||||||
|
|
||||||
// Allocate SubRegion and Reserved address ranges.
|
// Allocate SubRegion and Reserved address ranges.
|
||||||
for region in self.arch_mem_regions.iter() {
|
for region in self.arch_mem_regions.iter() {
|
||||||
if region.2 == RegionType::Ram {
|
if region.r_type == RegionType::Ram {
|
||||||
// Ignore the RAM type since ranges have already been allocated
|
// Ignore the RAM type since ranges have already been allocated
|
||||||
// based on the GuestMemory regions.
|
// based on the GuestMemory regions.
|
||||||
continue;
|
continue;
|
||||||
@ -792,7 +800,11 @@ impl MemoryManager {
|
|||||||
self.allocator
|
self.allocator
|
||||||
.lock()
|
.lock()
|
||||||
.unwrap()
|
.unwrap()
|
||||||
.allocate_mmio_addresses(Some(region.0), region.1 as GuestUsize, None)
|
.allocate_mmio_addresses(
|
||||||
|
Some(GuestAddress(region.base)),
|
||||||
|
region.size as GuestUsize,
|
||||||
|
None,
|
||||||
|
)
|
||||||
.ok_or(Error::MemoryRangeAllocation)?;
|
.ok_or(Error::MemoryRangeAllocation)?;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -820,6 +832,15 @@ impl MemoryManager {
|
|||||||
.map(|r| (r.0, r.1))
|
.map(|r| (r.0, r.1))
|
||||||
.collect();
|
.collect();
|
||||||
|
|
||||||
|
let arch_mem_regions: Vec<ArchMemRegion> = arch_mem_regions
|
||||||
|
.iter()
|
||||||
|
.map(|(a, b, c)| ArchMemRegion {
|
||||||
|
base: a.0,
|
||||||
|
size: *b,
|
||||||
|
r_type: *c,
|
||||||
|
})
|
||||||
|
.collect();
|
||||||
|
|
||||||
let (mem_regions, mut memory_zones) =
|
let (mem_regions, mut memory_zones) =
|
||||||
Self::create_memory_regions_from_zones(&ram_regions, &zones, prefault)?;
|
Self::create_memory_regions_from_zones(&ram_regions, &zones, prefault)?;
|
||||||
|
|
||||||
@ -2049,6 +2070,15 @@ impl Pausable for MemoryManager {}
|
|||||||
#[derive(Versionize)]
|
#[derive(Versionize)]
|
||||||
pub struct MemoryManagerSnapshotData {
|
pub struct MemoryManagerSnapshotData {
|
||||||
memory_ranges: MemoryRangeTable,
|
memory_ranges: MemoryRangeTable,
|
||||||
|
guest_ram_mappings: Vec<GuestRamMapping>,
|
||||||
|
start_of_device_area: u64,
|
||||||
|
boot_ram: u64,
|
||||||
|
current_ram: u64,
|
||||||
|
arch_mem_regions: Vec<ArchMemRegion>,
|
||||||
|
hotplug_slots: Vec<HotPlugState>,
|
||||||
|
next_memory_slot: u32,
|
||||||
|
selected_slot: usize,
|
||||||
|
next_hotplug_slot: usize,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl VersionMapped for MemoryManagerSnapshotData {}
|
impl VersionMapped for MemoryManagerSnapshotData {}
|
||||||
@ -2075,7 +2105,18 @@ impl Snapshottable for MemoryManager {
|
|||||||
|
|
||||||
memory_manager_snapshot.add_data_section(SnapshotDataSection::new_from_versioned_state(
|
memory_manager_snapshot.add_data_section(SnapshotDataSection::new_from_versioned_state(
|
||||||
MEMORY_MANAGER_SNAPSHOT_ID,
|
MEMORY_MANAGER_SNAPSHOT_ID,
|
||||||
&MemoryManagerSnapshotData { memory_ranges },
|
&MemoryManagerSnapshotData {
|
||||||
|
memory_ranges,
|
||||||
|
guest_ram_mappings: self.guest_ram_mappings.clone(),
|
||||||
|
start_of_device_area: self.start_of_device_area.0,
|
||||||
|
boot_ram: self.boot_ram,
|
||||||
|
current_ram: self.current_ram,
|
||||||
|
arch_mem_regions: self.arch_mem_regions.clone(),
|
||||||
|
hotplug_slots: self.hotplug_slots.clone(),
|
||||||
|
next_memory_slot: self.next_memory_slot,
|
||||||
|
selected_slot: self.selected_slot,
|
||||||
|
next_hotplug_slot: self.next_hotplug_slot,
|
||||||
|
},
|
||||||
)?);
|
)?);
|
||||||
|
|
||||||
Ok(memory_manager_snapshot)
|
Ok(memory_manager_snapshot)
|
||||||
|
Loading…
Reference in New Issue
Block a user