Corrector: TinyCorrect v0.1 - [tounix spaces toc comments tables images urls epw]
Author: XiakaiPan 13212017962@163.com
Date: 2022/10/21
Revisor: walimis, Falcon
Project: RISC-V Linux 內核剖析
Proposal: RISC-V 虛擬化技術調研與分析
Sponsor: PLCT Lab, ISCAS
本周繼續連載 Risc-v Kvm Excp Impl 系列文章,記得收藏分享+關注,寫文章領補貼:gitee.com/tinylab/riscv-linux
該活動統一采用泰曉社區自研 Linux Lab 開源實驗環境,也可選用免裝即插即跑 Linux Lab Disk (https://tinylab.org/linux-lab-disk),某寶檢索“泰曉 Linux”可找到。Linux Lab v1.1 Inside —— 內核開發從未像今天這般簡單!
RISC-V 異常處理在 KVM 中的實現
前言
Trap 處理是 RISC-V 虛擬化實現中的重要部分,包括異常和中斷兩個部分。當前 KVM 是 RISC-V 虛擬化擴展在軟件層面較為可靠的實現,本文將結合 RISC-V 特權指令集手冊的規定,分析 KVM 中有關異常處理的實現,中斷部分由于涉及較多驅動層面的內容,故將在之后的文章中結合 MMIO,timer 等做具體探討。
軟件版本
KVM 異常處理
異常處理入口
在 KVM 對 RISC-V H 擴展的實現中,與異常處理相關的函數調用關系如下圖所示。目前的實現中,KVM 能夠處理三類異常。即虛擬機內的 page fault、虛擬指令異常和系統調用,三種不同的異常處理分別對應了不同的實現。
異常分類及其定義
kvm_arch_vcpu_ioctl_run 函數用于實現 vCPU 的運行。其調用 kvm_riscv_vcpu_enter_exit 函數進入 vCPU 的運行,此時 Guest 進入運行狀態,CPU 處于 VS 或者 VU 模式。當 Guest 發生無法處理的異常時,Guest 退出,CPU 進入 HS 模式,隨后 KVM 調用 kvm_riscv_vcpu_exit 來實現對異常的處理。
kvm_riscv_vcpu_exit 函數內部包含三個部分,分別對應三種異常的處理,代碼如下:
如上所示,KVM 的實現中包含了三類異常:
虛擬指令異常;
Guest page fault;
SBI 系統調用。
特權指令集手冊 中規定了每種異常對應的編碼(即 scause 的可能的值),在進行異常處理時,可依據據 scause 的具體值確定其處理方式,如下表所示。
cause code
在 KVM 中,其對應宏的定義如下:
虛擬指令異常
其中,EXC_VIRTUAL_INST_FAULT 即 virtual instruction exception 對應如下情況:
在 VS-Mode 或 VU-Mode 下訪問特定 CSR 的特定位;
在 VS-Mode 或 VU-Mode 下執行無權限的指令如 HFENCE, HLV, HSV 等。
KVM 中 virtual instruction 異常的處理如下:
其中用于處理具體指令的函數其原型或定義如下:
處理非法壓縮指令時,用于從 Guest 獲取合法指令的 kvm_riscv_vcpu_unpriv_read 函數:
對合法的壓縮指令以及非 SYSTEM 類型的非壓縮指令,不進行額外處理,直接調用 truly_illegal_insn 函數處理,保存當前 trap 的具體信息,將 Guest PC 設置為 Guest 中對應的異常向量, 然后返回到到 Guest 中對異常進行處理:
其調用關系如下圖所示:
SBI 系統調用
系統調用的處理通過調用 kvm_riscv_vcpu_sbi_ecall 函數實現,如下方代碼塊所示:
SBI(Supervisor Binary Interface) 是直接運行在 Machine Mode 下的,為上層 OS 提供統一接口的程序,具有最高權限。而 Guest 訪問 SBI 系統調用,是在 KVM 中模擬實現,不是實際訪問 Machine Mode 中的 SBI firmware。KVM 通過直接訪問和設置寄存器(cp->a7, cp->a0, cp->a0 等)的值來實現對 SBI 系統調用的處理。
總結
本文結合 KVM 中有關異常處理的實現,討論了在添加 H 擴展之后的虛擬指令異常、guest page fault 以及來自 guest 的系統調用的處理。
參考資料
RISC-V 特權指令集手冊
RISC-V Linux
首發地址:https://tinylab.org/riscv-kvm-excp-impl
技術服務:https://tinylab.org/ruma.tech