#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum CoreReg {
X(u8),
Fp,
Lr,
Pc,
Cpsr,
Fpsr,
Fpcr,
}
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum SysReg {
MpidrEl1,
}
pub mod prot {
pub const READ: u64 = 1;
pub const WRITE: u64 = 1 << 1;
pub const EXEC: u64 = 1 << 2;
pub const RW: u64 = READ | WRITE;
pub const RX: u64 = READ | EXEC;
pub const RWX: u64 = READ | WRITE | EXEC;
}
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum VcpuExit {
Canceled,
Exception {
syndrome: u64,
phys_addr: u64,
virt_addr: u64,
},
VTimerActivated,
Io {
port: u16,
write: bool,
size: u8,
data: u32,
},
Mmio {
phys_addr: u64,
write: bool,
len: u8,
data: u64,
},
Halt,
Unknown(u32),
}
pub trait VcpuHandle: Copy + Send + Sync + 'static {
fn force_exit(handles: &[Self]);
}
pub trait HypervisorVcpu {
type Error;
type Handle: VcpuHandle;
type SnapshotState;
fn exit_token(&self) -> Self::Handle;
fn capture_snapshot(&self) -> Result<Self::SnapshotState, Self::Error>;
fn restore_snapshot(&self, state: &Self::SnapshotState) -> Result<(), Self::Error>;
fn write_snapshot_state(
state: &Self::SnapshotState,
w: &mut dyn std::io::Write,
) -> std::io::Result<()>;
fn read_snapshot_state(r: &mut dyn std::io::Read) -> std::io::Result<Self::SnapshotState>;
fn capture_clock_ref(state: &Self::SnapshotState, host_now: u64) -> u64;
fn restore_clock(&self, captured_ref: u64, host_now: u64) -> Result<u64, Self::Error>;
fn get_core(&self, reg: CoreReg) -> Result<u64, Self::Error>;
fn set_core(&self, reg: CoreReg, value: u64) -> Result<(), Self::Error>;
fn get_sys(&self, reg: SysReg) -> Result<u64, Self::Error>;
fn set_sys(&self, reg: SysReg, value: u64) -> Result<(), Self::Error>;
fn step(&self) -> Result<VcpuExit, Self::Error>;
}
pub trait HypervisorVm: Sized {
type Error;
type Vcpu: HypervisorVcpu<Error = Self::Error>;
fn create() -> Result<Self, Self::Error>;
unsafe fn map_ram(
&self,
host_ptr: *mut u8,
gpa: u64,
len: usize,
prot: u64,
) -> Result<(), Self::Error>;
unsafe fn unmap_ram(&self, gpa: u64, len: usize) -> Result<(), Self::Error>;
fn create_vcpu(&self) -> Result<Self::Vcpu, Self::Error>;
fn set_irq(&self, intid: u32, level: bool) -> Result<(), Self::Error>;
fn irq_line(&self) -> std::sync::Arc<dyn Fn(u32, bool) + Send + Sync>;
fn capture_intc(&self) -> Result<Vec<u8>, Self::Error>;
fn restore_intc(&self, blob: &[u8]) -> Result<(), Self::Error>;
fn boot_linux(
&self,
vcpu: &Self::Vcpu,
mem: &mut [u8],
cfg: &LinuxBootConfig,
) -> Result<(), Self::Error>;
fn dax_mapper(self: &std::sync::Arc<Self>) -> std::sync::Arc<dyn crate::fuse::HvfMapper>;
fn host_monotonic_ticks() -> u64;
}
pub struct LinuxBootConfig<'a> {
pub kernel: &'a [u8],
pub initrd: Option<&'a [u8]>,
pub cmdline: &'a str,
pub ram_gpa: u64,
pub ram_size: usize,
pub fdt: Option<&'a [u8]>,
}
pub trait BackendError {
fn other(msg: &str) -> Self;
}
#[cfg(all(target_os = "macos", target_arch = "aarch64"))]
pub type ActiveVm = crate::hvf::Vm;
#[cfg(all(target_os = "macos", target_arch = "aarch64"))]
pub type ActiveVcpu = <ActiveVm as HypervisorVm>::Vcpu;
#[cfg(all(target_os = "macos", target_arch = "aarch64"))]
pub type ActiveVcpuHandle = <ActiveVcpu as HypervisorVcpu>::Handle;
#[cfg(all(target_os = "macos", target_arch = "aarch64"))]
pub type ActiveError = <ActiveVm as HypervisorVm>::Error;
#[cfg(all(target_os = "macos", target_arch = "aarch64"))]
pub type ActiveResult<T> = std::result::Result<T, ActiveError>;
#[cfg(all(target_os = "linux", target_arch = "x86_64"))]
pub type ActiveVm = crate::kvm::KvmVm;
#[cfg(all(target_os = "linux", target_arch = "x86_64"))]
pub type ActiveVcpu = <ActiveVm as HypervisorVm>::Vcpu;
#[cfg(all(target_os = "linux", target_arch = "x86_64"))]
pub type ActiveVcpuHandle = <ActiveVcpu as HypervisorVcpu>::Handle;
#[cfg(all(target_os = "linux", target_arch = "x86_64"))]
pub type ActiveError = <ActiveVm as HypervisorVm>::Error;
#[cfg(all(target_os = "linux", target_arch = "x86_64"))]
pub type ActiveResult<T> = std::result::Result<T, ActiveError>;