// Copyright 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved. // SPDX-License-Identifier: Apache-2.0 /// Module for the global interrupt controller configuration. pub mod gic; mod gicv2; mod gicv3; /// Layout for this aarch64 system. pub mod layout; /// Logic for configuring aarch64 registers. pub mod regs; use crate::RegionType; use kvm_ioctls::*; use std::fmt::Debug; use vm_memory::{ Address, GuestAddress, GuestMemory, GuestMemoryAtomic, GuestMemoryMmap, GuestUsize, }; #[derive(Debug)] pub enum Error {} impl From for super::Error { fn from(e: Error) -> super::Error { super::Error::AArch64Setup(e) } } /// Stub function that needs to be implemented when aarch64 functionality is added. pub fn arch_memory_regions(size: GuestUsize) -> Vec<(GuestAddress, usize, RegionType)> { vec![(GuestAddress(0), size as usize, RegionType::Ram)] } #[derive(Debug, Copy, Clone)] /// Specifies the entry point address where the guest must start /// executing code. pub struct EntryPoint { /// Address in guest memory where the guest must start execution pub entry_addr: GuestAddress, } pub fn configure_vcpu( _fd: &VcpuFd, _id: u8, _kernel_entry_point: Option, _vm_memory: &GuestMemoryAtomic, ) -> super::Result<()> { unimplemented!(); } /// Stub function that needs to be implemented when aarch64 functionality is added. pub fn configure_system( _guest_mem: &GuestMemoryMmap, _cmdline_addr: GuestAddress, _cmdline_size: usize, _num_cpus: u8, _rsdp_addr: Option, ) -> super::Result<()> { Ok(()) } /// Stub function that needs to be implemented when aarch64 functionality is added. pub fn get_reserved_mem_addr() -> usize { 0 } // Auxiliary function to get the address where the device tree blob is loaded. fn get_fdt_addr(mem: &GuestMemoryMmap) -> u64 { // If the memory allocated is smaller than the size allocated for the FDT, // we return the start of the DRAM so that // we allow the code to try and load the FDT. if let Some(addr) = mem.last_addr().checked_sub(layout::FDT_MAX_SIZE as u64 - 1) { if mem.address_in_range(addr) { return addr.raw_value(); } } layout::RAM_64BIT_START } pub fn get_host_cpu_phys_bits() -> u8 { // The value returned here is used to determine the physical address space size // for a VM (IPA size). // In recent kernel versions, the maxium IPA size supported by the host can be // known by querying cap KVM_CAP_ARM_VM_IPA_SIZE. And the IPA size for a // guest can be configured smaller. // But in Cloud-Hypervisor we simply use the maxium value for the VM. // Reference https://lwn.net/Articles/766767/. // // The correct way to query KVM_CAP_ARM_VM_IPA_SIZE is via rust-vmm/kvm-ioctls, // which wraps all IOCTL's and provides easy interface to user hypervisors. // For now the cap hasn't been supported. A separate patch will be submitted to // rust-vmm to add it. // So a hardcoded value is used here as a temporary solution. // It will be replace once rust-vmm/kvm-ioctls is ready. // 40 } pub fn check_required_kvm_extensions(kvm: &Kvm) -> super::Result<()> { if !kvm.check_extension(Cap::SignalMsi) { return Err(super::Error::CapabilityMissing(Cap::SignalMsi)); } Ok(()) }