
本文将深入剖析开源 Bao Hypervisor 是如何在瑞萨电子(Renesas)的 RH850/U2Axx 系列微控制器上实现深度移植与适配的。内容侧重于核心架构特性的工程实践,结合代码片段和调试截图,展示这些机制在真实硬件上的运行效果,并探讨未来的演进方向。
我们将从 CPU 管理、内存保护、中断分配三个维度展开,并详细探讨 Bao 如何实现外设模拟(Emulation)。
CPU 核心管理与虚拟化
启动从核
在 RH850/U2Axx 平台上,系统复位后仅核心 0(PE0)处于运行状态。Bao 在初始化阶段将 PE0 指定为主 CPU。在完成基础环境构建后,PE0 会通过改写 BOOTCTRL 寄存器,按序号依次唤醒其余核心。当所有次级核心启动后,虚拟机管理器会通过软件屏障确保全核同步,随后再进入后续的初始化流程。

图:RH850/U2Axx 启动顺序。
处理器间通信
为了实现跨核心的高效协作,Bao 构建了一套基于 IPI(处理器间中断)和内存共享消息列表的通信机制。主 CPU 可以通过此机制请求次级核心执行特定操作,例如同步 MPU 映射关系的更新。
在硬件层面,RH850/U2Axx 通过 IPIR 外设管理 IPI,提供四个独立通道。Bao 采取了“隔离与保留”策略:专门预留 IPIR3 通道供自身内部使用,而将前三个通道开放给客户机(VM)。在中断初始化期间,Bao 会对 IPIR3 寄存器及相关的 EIINT3 资源实施保护,确保客户机对其访问呈现为“写无效/读为零”(WI/RZ),从而保障通信的私密性。

图:Bao中用于MPU同步的IPC示例:(a) PE0将消息写入列表;(b) PE0向PE1发送IPI;(c) PE1读取消息并执行MPU同步;(d) 请求的映射已插入PE1的MPU中。
CPU ID 虚拟化
在 RH850 基础架构中,PEID 寄存器允许软件识别其正在运行的物理 CPU。随着 RH850/U2Axx 虚拟化扩展的引入,该机制通过 GMPEID 寄存器得到扩展,该寄存器使 Bao 能够向客户软件分配虚拟 CPU ID。
在虚拟机配置期间,Bao 为每个 vCPU 分配一个标识符,存储在对应的 vCPU 结构体内部并将其写入对应上下文的 GMPEID寄存器中。因此,尽管底层执行可能发生在任一物理核上,客户机软件仍认为自己运行在按顺序编号的物理核上。

图:RH850/U2Axx中CPU ID虚拟化示例:(a) 在双核虚拟机中将CPU亲和性配置为0x9;(b) 显示vCPU ID为0x1的PE3的vCPU结构;(c) 通过GMPEID寄存器向客户软件暴露vCPU ID。
嵌套内存保护机制
Bao 深度整合了 RH850/U2Axx 的嵌套内存保护机制,实现了自身与客户机双层的权限校验。系统经过 Bao 配置,所有内存访问均需接受宿主机管理条目检查。初始化期间,Bao 仅按递减索引顺序设置这些宿主机管理条目以强制执行内存保护。
为了进一步隔离地址空间,Bao 使用与 MPU 条目关联的系统保护标识符(SPID)。Bao 为其自身地址空间与每个虚拟机分别分配不同的SPID,以此区分用于保护Bao的条目与用于保护客户机地址空间的条目。
最后,Bao 配置 MPU 与异常引擎,实现了对保护违例的分类化处理。由宿主机管理条目捕获的访存异常将被路由至宿主机模式下处理,使 Bao 能够捕获并模拟客户机对受保护域或敏感外设的访问。

图:Bao初始化后从单核看到的内存布局,覆盖Flash、RAM与MMIO区域。
中断分配
Bao 利用了 RH850/U2Axx 虚拟化扩展提供的中断直通机制。在初始化阶段,Bao 为每个虚拟机分配一个唯一标识符(GPID)并将其写入每个物理 CPU 的 PSWH.GPID 字段。硬件使用此 GPID 来确定外部中断的目标分区。
随后,当物理资源分配给客户机时,Bao 配置中断控制器,根据配置将每个中断源绑定到相应的VM。这保证了客户机软件无法访问与虚拟化相关的控制项,也无法修改未分配中断源的配置。

图:RH850/U2Axx中虚拟机中断分配示例。用户将RLIN35中断分配给VM0,TPTPM分配给VM1。
外设模拟 (Emulation)
当客户机试图访问特权资源或多个虚拟机共享的外设时,Bao 会执行模拟操作。在 RH850/U2Axx 平台上,对特权寄存器的访问会触发特权指令异常并被自动捕获。对于需要模拟的内存映射外设(MMIO),Bao 在初始化时将这些 MMIO 区域从客户机地址空间中剔除,并为每个区域分配专用的模拟处理程序。
当客户机触发数据访存保护异常(MDP)时,Bao 从 MEA 系统寄存器获取故障地址,并检查该地址是否属于用于模拟的 MMIO 区域。如果匹配,则从 MEI 寄存器获取访问类型、大小等信息,然后调用相应的模拟处理程序。

图:RH850/U2Axx中模拟处理程序配置示例:(a)Bao为BOOTCTRL外设配置模拟处理程序;(b) 当客户机尝试访问BOOTCTRL寄存器时发生MDP异常;(c) 调用相应的模拟处理程序。
许多 RH850 外设通过位操作指令访问,例如 CLR1、SET1 等。这些指令在触发异常时,其位索引或操作类型无法通过 MEI 寄存器直接获取。为支持这些操作的正确模拟,Bao 在捕获发生时对指令操作码进行解码,提取位序号和操作类型。

图:RH850/U2Axx中位操作指令解码与模拟示例:(a) 客户机执行SET1指令触发异常;(b)Bao解码指令操作码以获取位操作类型和位序号。
在当前移植中,有五个 MMIO 区域被配置用于模拟:INTC1、INTC2、IPIR、BOOTCTRL寄存器和 BARR。
IPIR 模拟
Bao 对 IPIR 模拟以支持同一客户机内虚拟 CPU 之间的 IPI。Bao 保留 IPIR 通道 3 供自身使用,仅允许 VM 使用通道 0-2。为了实现强制隔离,Bao 捕获所有VM对IPIR寄存器的访问,并在虚拟CPU ID与底层物理PEID之间进行转换。

图:RH850/U2Axx中IPI模拟示例:(a) IPIR请求寄存器布局;(b) vCPU1向vCPU0发送IPI;(c)Bao触发对vCPU1的访问并转换vCPU ID。
BOOTCTRL 模拟
BOOTCTRL 寄存器在 Bao 中被完全虚拟化。为了模拟 RH850/U2Axx 预期的启动行为,Bao 在虚拟机启动时将所有次级 vCPU 置于关机状态。Bao 维护一个内部结构体以镜像 BOOTCTRL 寄存器的语义。当客户机软件向 BOOTCTRL 写入以“启动”次级 vCPU 时,Bao 更新该内部结构体并唤醒对应的 vCPU。

图:RH850/U2Axx中BOOTCTRL模拟示例:(a)Bao启动虚拟机并将vCPU1置为关机模式;(b) 虚拟机尝试使用BOOTCTRL启动vCPU1;(c)Bao捕获该访问并通知物理核心;(d)Bao唤醒vCPU1。
BARR 模拟
BARR 是 RH850/U2Axx 平台内置的硬件模块,旨在为物理 CPU 簇提供硬件辅助的屏障同步机制。Bao 对 BARR 完全虚拟化,为每个虚拟机提供了独占16路通道的虚拟视图。该虚拟化方案通过三组按通道维护的位图实现,旨在精确建模物理 BARR 寄存器的行为逻辑。
未来演进与架构扩展探索
Bao 在 RH850/U2Axx 的移植上线时间较短,虽然功能完备,但仍有发展空间。例如对 LDM.GSR/STM.GSR 指令、LDM.MP/STM.MP 指令、后台中断等的支持尚未被充分利用。我们计划在后续工作中集成这些特性。
调度支持相关特性
目前,Bao 采用静态划分 CPU 的方式。然而,已有在 Bao 中引入安全高效 CPU 共享能力的开发工作。一旦支持调度,在不同虚拟机间切换执行时就需要保存和恢复客户机上下文寄存器。届时,RH850/U2Axx 专为快速上下文切换设计的指令将发挥价值。


图:客户机上下文高速保存与恢复指令,以及调度开销示意图。
对调度的类似依赖性也出现在后台中断机制中。随着物理 CPU 共享机制的引入,可能会出现虚拟机未被调度但存在挂起中断的情形。一旦 Bao 集成了调度支持,我们计划利用后台中断使具备高优先级属性的虚拟机在接收到外部中断时能够抢占低优先级分区,从而缩短中断延迟。
从端内存保护
除了通过 MPU 在 CPU 侧强制的内存保护外,RH850/U2Axx 平台还提供了用于控制从端系统模块访问的补充硬件机制:Slave Guard。它在总线主设备(如 CPU 或 DMA 引擎) 发出的内存与外设访问到达从模块之前进行验证。
在虚拟化环境中,由于 Bao 为每个虚拟机分配唯一的SPID,Slave Guard 机制可在硬件层将外设和内存区域直接绑定到指定的虚拟机。这简化了设备分配工作,并可通过在硬件互连层阻止未授权访问来进一步强化隔离。
重要的是,RH850/U2Axx 上的许多外设在内部被划分为多个通道,相应的 guard 功能支持通道粒度的SPID配置。此能力对虚拟化有明显好处,因为它允许 Bao 将通道所有权直接委托给硬件,大幅减少安全共享多通道外设所需的软件模拟开销。我们计划在 Bao 中充分挖掘 Slave Guard 的潜力,尽量利用硬件逻辑来实现隔离,这正是 开源实战 中追求的高效实践。

图:系统级内存保护架构,展示了从SPID管理到CPU模式、内存及外设保护的多层安全结构。
总结
本文详细介绍了 Bao Hypervisor 在 RH850 平台上的核心移植机制,涵盖了从多核启动、计算机基础 层面的CPU虚拟化,到复杂的内存保护、中断分配以及精细的外设模拟。随着未来对调度和Slave Guard等硬件增强特性的集成,Bao 在嵌入式虚拟化领域的表现将更加高效和强大。对于想深入理解嵌入式虚拟化或进行类似移植的开发者,欢迎到 云栈社区 交流探讨。