Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
70 commits
Select commit Hold shift + click to select a range
0e92e00
refactor: deps git to crates-io
ZR233 Aug 14, 2025
40051ba
fix: feature
ZR233 Sep 9, 2025
d419798
refactor: support guest dyn entry
ZR233 Sep 10, 2025
ecdc6b6
refactor: add Clone trait to VMImageConfig
ZR233 Sep 10, 2025
b4f561f
fix: update arm_vcpu branch to 'next'
ZR233 Sep 12, 2025
c10b3c8
add fdt support and add some AxVMConfig impl
Sep 25, 2025
d0b1e63
fix fmt bug
Sep 25, 2025
62dc146
fix bug: when no phys_cpu_ids panic
Sep 29, 2025
a5b6c03
add function map_reserved_memory_region (#28)
buhenxihuan Oct 15, 2025
22437d2
add passthrough address (#29)
bullhh Nov 6, 2025
2e1fb68
添加 AArch64 和 x86_64 架构支持,重构 Vm 结构及相关操作,新增 VmId 和状态管理
ZR233 Nov 11, 2025
0c19481
修复状态获取逻辑中的引用问题
ZR233 Nov 13, 2025
8b7a17f
重构 AArch64 虚拟机实现,添加设备管理和内存映射功能
ZR233 Nov 13, 2025
c664eb1
更新地址空间初始化,移除 4-level-ept 特性支持,添加 x86_64 和 FDT 模块
ZR233 Nov 13, 2025
0f87ca2
更新 Cargo.toml,调整依赖项版本,移除不必要的特性支持,并优化格式
ZR233 Nov 13, 2025
77357c2
更新 Cargo.toml,添加 axhal、axruntime 和 fdt-parser 依赖;重构 AArch64 架构的 cpu 模…
ZR233 Nov 14, 2025
f14b41c
Refactor VM and vCPU structures; remove unused HAL trait
ZR233 Nov 14, 2025
e8a7fea
更新 Cargo.toml,添加新的依赖项并调整现有依赖项;重构 vhal 模块,新增定时器功能并移除旧的 vhal 实现
ZR233 Nov 14, 2025
bf4ab3a
更新 Cargo.toml,添加 aarch64-cpu 依赖;重构 AArch64 架构的 CPU 模块,新增 CpuData 结构体并…
ZR233 Nov 14, 2025
c784a55
重构 AArch64 CPU 模块,新增 vpercpu 和 max_guest_page_table_levels 字段;实现 CpuD…
ZR233 Nov 17, 2025
f280d08
update
ZR233 Nov 18, 2025
5b74a37
移除 enable_viretualization 函数中的 panic! 调用,并添加文档注释以说明硬件虚拟化支持的启用
ZR233 Nov 19, 2025
61497b0
fix task_stack_size
ZR233 Nov 19, 2025
9adb387
Refactor AArch64 architecture: Introduce HCpu struct, update VM handl…
ZR233 Nov 24, 2025
4550ca5
重构 AArch64 CPU 和虚拟化模块,添加 HCpuExclusive 结构体,更新 CPU ID 管理,优化 Cargo.toml…
ZR233 Nov 25, 2025
c951529
重构 VCpu 和 ArchVm 结构,更新 CPU ID 管理,优化虚拟机初始化逻辑,添加 CpuConfig 结构体以支持物理 CPU…
ZR233 Nov 25, 2025
c9dd964
重构虚拟机配置和 vCPU 创建逻辑,更新 CPU 数量管理,优化内存地址处理
ZR233 Nov 25, 2025
70ccc72
重构虚拟机内存管理,添加内存区域支持,更新 RunData 结构,优化设备信息管理
ZR233 Nov 25, 2025
c43052a
重构虚拟机架构,优化内存区域管理,添加缓存刷新功能,更新配置结构,改进虚拟机初始化逻辑
ZR233 Nov 26, 2025
db7db82
feat: add cache flush
ZR233 Nov 27, 2025
8a32bdb
feat: 添加虚拟机状态管理和命令处理机制,重构相关结构体和逻辑
ZR233 Nov 27, 2025
f484c89
feat: 重构虚拟机状态管理,移除无用的轮询逻辑,优化运行循环
ZR233 Nov 27, 2025
67e0384
feat: 添加 VCpuHandle 结构,优化 vCPU 运行逻辑,支持激活状态管理
ZR233 Nov 27, 2025
e57b577
fmt code
ZR233 Nov 28, 2025
84b54ff
feat: 重构虚拟机内存管理,移除冗余代码并引入 VmData 结构
ZR233 Dec 1, 2025
cd4c8e2
feat: 实现 vCPU 退出原因处理逻辑,添加 MMIO 和系统寄存器读写支持
ZR233 Dec 1, 2025
f6a5e4d
feat: 添加 FDT 生成器,优化虚拟机内存管理和设备节点处理逻辑
ZR233 Dec 1, 2025
ce088b1
feat: 更新 FDT 生成逻辑,优化内存映射处理,添加对节点的动态管理
ZR233 Dec 3, 2025
59133e1
feat: 优化 VCpu 退出处理逻辑,添加设备地址空间映射功能
ZR233 Dec 3, 2025
59cedb7
feat: 更新 fdt_edit 依赖版本,优化虚拟机内存节点处理逻辑
ZR233 Dec 10, 2025
c687314
feat: 优化内存映射处理,添加设备名称到设备区域合并逻辑
ZR233 Dec 12, 2025
f953635
feat: 移除冗余的 FDT 生成逻辑,优化 fdt_edit 函数实现
ZR233 Dec 12, 2025
9925b65
feat: 添加虚拟机初始化和地址空间管理模块,优化内存映射处理
ZR233 Dec 15, 2025
47d5d05
feat: 重构虚拟机初始化和地址空间管理,优化 vCPU 创建逻辑和内存映射处理
ZR233 Dec 15, 2025
f92d4eb
feat: 添加内存映射区域处理,优化直通区域映射逻辑
ZR233 Dec 15, 2025
8902a28
feat: 移除冗余的 4-level-ept 特性,优化 CPU 分配逻辑,增强设备映射标志
ZR233 Dec 15, 2025
f4eea00
fix: 修正获取启动参数的函数调用,确保正确获取设备树地址
ZR233 Dec 18, 2025
8b64d8a
fmt code
ZR233 Dec 18, 2025
aff70e1
feat: 移除冗余的 vcpu 模块,简化 VM 配置结构
ZR233 Dec 18, 2025
70bd7a6
update
ZR233 Dec 19, 2025
7ac8334
Refactor VM data management and address space handling
ZR233 Dec 19, 2025
faca4ac
feat: 添加 VM 初始化和运行管理模块,优化 CPU 处理逻辑
ZR233 Dec 19, 2025
2c2cf9e
feat: 实现 VCpu 操作接口,增强虚拟 CPU 管理功能
ZR233 Dec 19, 2025
c158651
feat: 更新 VmMachineRunning 和 VmStatusStopping 结构,增强 VM 停止逻辑
ZR233 Dec 19, 2025
f3c369d
refactor: 清理未使用的导入和结构,优化代码可读性
ZR233 Dec 19, 2025
d1cf7b0
refactor: 移除未使用的常量和字段,优化代码结构
ZR233 Dec 19, 2025
731be1f
feat: 增强虚拟机管理功能,添加 CPU 启动和运行管理逻辑,清理未使用的代码
ZR233 Dec 19, 2025
bc4914b
feat: 增强 vCPU 调试信息,优化 CPU 启动逻辑
ZR233 Dec 19, 2025
323836b
feat: 添加 CPU vCPU 调试信息,增强 CPU 启动过程的可追踪性
ZR233 Dec 19, 2025
5a2ad13
feat: 增强 vCPU 启动过程的调试信息,优化 CPU 启动逻辑
ZR233 Dec 22, 2025
a46d06b
feat: 优化虚拟机等待逻辑,修复 CPU 启动时的线程状态检查
ZR233 Dec 22, 2025
91852c4
feat: 增强 vCPU 调试信息,添加 CPU 运行时的 VM ID 追踪
ZR233 Dec 22, 2025
9725b83
feat: 添加对 initrd 的支持,增强 FDT 构建功能
ZR233 Dec 22, 2025
b735d46
feat: 修改 FdtBuilder 的 setup_initrd 方法为 setup_chosen,增强对引导参数的处理
ZR233 Dec 22, 2025
ce4ce80
feat: 重命名 MemoryKind 枚举中的 Passthrough 为 Reserved,增强内存区域描述
ZR233 Dec 22, 2025
e1d5326
feat: 添加 x86_64 架构支持,包含 CPU 和 HAL 模块的实现
ZR233 Dec 22, 2025
b80c27e
feat: 添加 pa_bits 字段到 HCpu 和 VmMachineUninit 结构体,增强物理地址处理能力
ZR233 Dec 22, 2025
f362f85
feat: 实现 x86_64 架构的虚拟机管理,添加 VM 初始化和运行逻辑
ZR233 Dec 23, 2025
b87ca8f
feat: 优化 setup_chosen 方法,简化 initrd 属性处理逻辑
ZR233 Dec 23, 2025
bce19d9
fmt
ZR233 Dec 23, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
50 changes: 36 additions & 14 deletions Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,40 +1,62 @@
[package]
edition = "2024"
name = "axvm"
version = "0.1.0"
edition = "2024"

[features]
default = ["vmx"]
vmx = []
4-level-ept = ["arm_vcpu/4-level-ept"] # TODO: Realize 4-level-ept on x86_64 and riscv64.
# Note: 4-level-ept support is now provided through dynamic page table selection in axaddrspace
# The feature gate is no longer needed

[dependencies]
log = "0.4"
anyhow = {version = "1.0", default-features = false}
cfg-if = "1.0"
spin = "0.9"
lazyinit = "0.2"
log = "0.4"
ranges-ext.workspace = true
spin = "0.10"
thiserror = {version = "2", default-features = false}
timer_list = "0.1"

# System independent crates provided by ArceOS.
axerrno = "0.1.0"
bitmap-allocator = "0.2.1"
cpumask = "0.1.0"
# kspin = "0.1.0"
kspin = "0.1"
memory_addr = "0.4"
page_table_entry = { version = "0.5", features = ["arm-el2"] }
page_table_entry = {version = "0.5", features = ["arm-el2"]}
page_table_multiarch = "0.5"
percpu = { version = "0.2.0", features = ["arm-el2"] }
percpu = {version = "0.2", features = ["arm-el2"]}
vm-allocator.workspace = true

# System dependent modules provided by ArceOS-Hypervisor.
axvcpu = "0.1"
axaddrspace = "0.1"
axdevice = { git = "https://github.com/arceos-hypervisor/axdevice.git" }
axdevice_base = "0.1"
axvmconfig = { version = "0.1", default-features = false }
axaddrspace = "0.2"
# axdevice = {git = "https://github.com/arceos-hypervisor/axdevice.git"}
# axdevice_base = "0.1"
# axvcpu = "0.1"
axhal.workspace = true
axruntime.workspace = true
axstd.workspace = true
axvm-types.workspace = true
axvmconfig = {version = "0.1", default-features = false}
fdt-edit = "0.1"

[target.'cfg(target_arch = "x86_64")'.dependencies]
raw-cpuid = "11"
x86_vcpu = "0.1"
axplat-x86-qemu-q35.workspace = true

[target.'cfg(target_arch = "riscv64")'.dependencies]
riscv_vcpu = "0.1"
# riscv_vcpu = "0.1"

[target.'cfg(target_arch = "aarch64")'.dependencies]
aarch64-cpu = "11.0"
aarch64-cpu-ext = "0.1"
arm_vcpu = "0.1"
arm_vgic = { version = "0.1", features = ["vgicv3"] }
# arm_vgic = {version = "0.1", features = ["vgicv3"]}

[patch.crates-io]
arm_vcpu = {git = "https://github.com/arceos-hypervisor/arm_vcpu", branch = "next"}
axvcpu = {git = "https://github.com/arceos-hypervisor/axvcpu.git", branch = "next"}
axvmconfig = {git = "https://github.com/arceos-hypervisor/axvmconfig.git", branch = "next"}
209 changes: 209 additions & 0 deletions src/arch/aarch64/cpu.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,209 @@
use core::{
fmt::{self, Debug, Display},
ops::Deref,
};

use aarch64_cpu::registers::*;
use arm_vcpu::{Aarch64PerCpu, Aarch64VCpuCreateConfig};
use axvm_types::addr::*;

use crate::{
RunError,
data::VmDataWeak,
vcpu::{VCpuCommon, VCpuOp},
vhal::{
ArchCpuData,
cpu::{CpuHardId, CpuId},
},
};

pub struct HCpu {
pub id: CpuId,
pub hard_id: CpuHardId,
vpercpu: Aarch64PerCpu,
max_guest_page_table_levels: usize,
pub pa_range: core::ops::Range<usize>,
pub pa_bits: usize,
}

impl HCpu {
pub fn new(id: CpuId) -> Self {
let mpidr = MPIDR_EL1.get() as usize;
let hard_id = mpidr & 0xff_ff_ff;

let vpercpu = Aarch64PerCpu::new();

HCpu {
id,
hard_id: CpuHardId::new(hard_id),
vpercpu,
max_guest_page_table_levels: 0,
pa_range: 0..0,
pa_bits: 0,
}
}

pub fn init(&mut self) -> anyhow::Result<()> {
self.vpercpu.hardware_enable();
self.max_guest_page_table_levels = self.vpercpu.max_guest_page_table_levels();
self.pa_range = self.vpercpu.pa_range();
self.pa_bits = self.vpercpu.pa_bits();
Ok(())
}

pub fn max_guest_page_table_levels(&self) -> usize {
self.max_guest_page_table_levels
}
}

impl ArchCpuData for HCpu {
fn hard_id(&self) -> CpuHardId {
self.hard_id
}
}

impl Display for HCpu {
fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
write!(
f,
"
CPU {}:
Hard ID: {}
PT Levels: {}",
self.id, self.hard_id, self.max_guest_page_table_levels
)
}
}

pub(super) struct VCpuHal;

impl arm_vcpu::CpuHal for VCpuHal {
fn irq_hanlder(&self) {
axhal::irq::irq_handler(0);
}

fn inject_interrupt(&self, irq: usize) {
todo!()
}
}

pub struct VCpu {
pub vcpu: arm_vcpu::Aarch64VCpu,
common: VCpuCommon,
}

impl VCpu {
pub fn new(
host_cpuid: Option<CpuId>,
dtb_addr: GuestPhysAddr,
vm: VmDataWeak,
) -> anyhow::Result<Self> {
let common = VCpuCommon::new_exclusive(host_cpuid, vm)?;

let hard_id = common.hard_id();

let vcpu = arm_vcpu::Aarch64VCpu::new(Aarch64VCpuCreateConfig {
mpidr_el1: hard_id.raw() as u64,
dtb_addr: dtb_addr.as_usize(),
})
.unwrap();
Ok(VCpu { vcpu, common })
}

pub fn set_pt_level(&mut self, level: usize) {
self.vcpu.pt_level = level;
}

pub fn set_pa_bits(&mut self, pa_bits: usize) {
self.vcpu.pa_bits = pa_bits;
}
}

impl VCpuOp for VCpu {
fn bind_id(&self) -> CpuId {
self.common.bind_id()
}

fn hard_id(&self) -> CpuHardId {
self.common.hard_id()
}

fn run(&mut self) -> Result<(), RunError> {
info!("Starting vCPU {}", self.bind_id());

self.vcpu
.setup_current_cpu(self.vm_id().into())
.map_err(|e| anyhow!("{e}"))?;
while self.is_active() {
debug!("vCPU {} entering guest", self.bind_id());
let exit_reason = self.vcpu.run().map_err(|e| anyhow!("{e}"))?;
debug!(
"vCPU {} exited with reason: {:?}",
self.bind_id(),
exit_reason
);
match exit_reason {
arm_vcpu::AxVCpuExitReason::Hypercall { nr, args } => todo!(),
arm_vcpu::AxVCpuExitReason::MmioRead {
addr,
width,
reg,
reg_width,
signed_ext,
} => todo!(),
arm_vcpu::AxVCpuExitReason::MmioWrite { addr, width, data } => todo!(),
arm_vcpu::AxVCpuExitReason::SysRegRead { addr, reg } => todo!(),
arm_vcpu::AxVCpuExitReason::SysRegWrite { addr, value } => todo!(),
arm_vcpu::AxVCpuExitReason::ExternalInterrupt => {
axhal::irq::irq_handler(0);
}
arm_vcpu::AxVCpuExitReason::CpuUp {
target_cpu,
entry_point,
arg,
} => {
debug!("vCPU {} requested CPU {} up", self.bind_id(), target_cpu);
self.vm()?.with_machine_running_mut(|running| {
debug!("vCPU {} is bringing up CPU {}", self.bind_id(), target_cpu);
running.cpu_up(CpuHardId::new(target_cpu as _), entry_point, arg)
})??;
self.vcpu.set_gpr(0, 0);
}
arm_vcpu::AxVCpuExitReason::CpuDown { _state } => todo!(),
arm_vcpu::AxVCpuExitReason::SystemDown => {
info!("vCPU {} requested system shutdown", self.bind_id());
self.vm()?.stop()?;
}
arm_vcpu::AxVCpuExitReason::Nothing => {}
arm_vcpu::AxVCpuExitReason::SendIPI {
target_cpu,
target_cpu_aux,
send_to_all,
send_to_self,
vector,
} => todo!(),
_ => todo!(),
}
}

Ok(())
}
}

impl Deref for VCpu {
type Target = VCpuCommon;

fn deref(&self) -> &Self::Target {
&self.common
}
}

impl Debug for VCpu {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
f.debug_struct("VCpu")
.field("bind_id", &self.bind_id())
.field("hard_id", &self.hard_id())
.field("vcpu", &self.vcpu)
.finish()
}
}
47 changes: 47 additions & 0 deletions src/arch/aarch64/hal.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
use alloc::vec::Vec;

use aarch64_cpu::registers::*;
use aarch64_cpu_ext::cache::{CacheOp, dcache_range};

use crate::fdt;
use crate::vhal::{
ArchHal,
cpu::{CpuHardId, CpuId},
};

use super::cpu::{HCpu, VCpuHal};

pub struct Hal;

impl ArchHal for Hal {
fn current_cpu_init(id: CpuId) -> anyhow::Result<HCpu> {
info!("Enabling virtualization on cpu {id}");
let mut cpu = HCpu::new(id);
cpu.init()?;
info!("{cpu}");
Ok(cpu)
}

fn init() -> anyhow::Result<()> {
arm_vcpu::init_hal(&VCpuHal);

Ok(())
}

fn cpu_list() -> Vec<CpuHardId> {
fdt::cpu_list()
.unwrap()
.into_iter()
.map(CpuHardId::new)
.collect()
}

fn cpu_hard_id() -> CpuHardId {
let mpidr = MPIDR_EL1.get() as usize;
CpuHardId::new(mpidr)
}

fn cache_flush(vaddr: arm_vcpu::HostVirtAddr, size: usize) {
dcache_range(CacheOp::CleanAndInvalidate, vaddr.as_usize(), size);
}
}
7 changes: 7 additions & 0 deletions src/arch/aarch64/mod.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
pub mod cpu;
mod hal;
mod vm;

pub use cpu::HCpu;
pub use hal::Hal;
pub use vm::*;
43 changes: 43 additions & 0 deletions src/arch/aarch64/vm/inited.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
use std::{string::String, vec::Vec};

use crate::{
VmAddrSpace, VmMachineInitedOps, VmMachineRunningCommon,
arch::{VmMachineRunning, cpu::VCpu},
data::VmDataWeak,
vm::VmId,
};

pub struct VmMachineInited {
pub id: VmId,
pub name: String,
pub vcpus: Vec<VCpu>,
pub vmspace: VmAddrSpace,
}

impl VmMachineInited {}

impl VmMachineInitedOps for VmMachineInited {
type Running = VmMachineRunning;

fn id(&self) -> VmId {
self.id
}

fn name(&self) -> &str {
&self.name
}

fn start(self, vmdata: VmDataWeak) -> Result<Self::Running, anyhow::Error> {
debug!("Starting VM {} ({})", self.id, self.name);
let mut running = VmMachineRunning {
common: VmMachineRunningCommon::new(self.vmspace, self.vcpus, vmdata),
};

let main = running.common.take_cpu()?;

running.common.run_cpu(main)?;

info!("VM {} ({}) main cpu started.", self.id, self.name,);
Ok(running)
}
}
Loading
Loading