機器模式
機器模式(縮寫為 M 模式,M-mode)是 RISC-V 中 hart(hardware thread,硬體線 程)可以執行的最高許可權模式。在 M 模式下執行的 hart 對記憶體,I/O 和一些對於啟動和配 置系統來說必要的底層功能有著完全的使用權。因此它是唯一所有標準 RISC-V 處理器都 必須實現的許可權模式。實際上簡單的 RISC-V 微控制器僅支援 M 模式。
hart 是 硬 件 線 程 (hardware thread)的縮略 形式。 我們用該術語將 它們與大多數程式設計師熟 悉的軟體執行緒區分開 來。軟體執行緒在 harts 上 進行分時複用。 大多數 處理器核都只有一個 hart。
CSR:控制狀態暫存器
機器模式最重要的特性是攔截和處理異常
(不尋常的執行時事件)的能力。
RISC-V 將 異常分為兩類。
- 同步異常:這類異常在指令執行期間產生
- 如訪問了無效的儲存器地址
- 執行了具有無效操作碼的指令
- 中斷:它是與指令流非同步的外部事件,比如鍵盤輸入。
為了方便表述與區分,本文接下來的表述按照如下規則
- 異常:異常分兩類,其中的同步異常
- 中斷:異常分兩類,其中的中斷
RISC-V 異常和中斷的原因
中斷時mcause
的最高有效位被設定成1
,異常時置為0
,剩下的位標識了中斷或者異常的具體原因。
中斷型別(來源)
- 軟體中斷:軟體中斷通過向記憶體對映暫存器中存數來觸發,並通常用於由一個 hart 中斷另一個 hart(在其他架構中稱為處理器間中斷機制)。
- 時鐘中斷:當 hart 的時間比較器(一個名為
mtimecmp
的記憶體對映暫存器)大於實時計數器mtime
時,會觸發時鐘中斷。 - 外部中斷: 有平臺級中斷控制器(大多數外部裝置連線到這個中斷控制器)引發。
機器模式下的異常、中斷處理
八個控制狀態暫存器(CSR)是機器模式下異常、中斷處理的必要部分
mtvec
(Machine Trap Vector)它儲存發生異常/中斷時處理器需要跳轉到的地址。- RISC-V 還支援
向量中斷
,其中處理器跳轉到各類異常/中斷各自對應的地址,而不是一個統一的入口點。這種定址消除 了讀取和解碼mcause
的需要,加快了中斷處理速度。 將mtval [0]
設 置為1
可啟用此功能; 然後根據異常/中斷原因x
將PC
設定為(mtval-1 + 4x ),
而 不 是 通 常 的mtvec
。
- RISC-V 還支援
mepc
(Machine Exception PC)它指向發生異常/中斷的指令。mcause
(Machine Exception Cause)它指示發生異常/中斷的原因(型別)。mie
(Machine Interrupt Enable)它指出處理器當前遮蔽了哪些中斷。mip
(Machine Interrupt Pending)它列出目前正準備處理的中斷(已經到來的中斷)。mtval
(Machine Trap Value)它儲存了陷入(trap)的附加資訊:page fault
中出錯的地址、發生非法指令例外的指令本身,對於其他異常,它的值為 0。mscratch
(Machine Scratch)它暫時存放一個字大小的資料。mstatus
(Machine Status)它儲存全域性中斷使能,以及許多其他的狀態
mstatus
mstatus.MIE
置 1 時才會產生中斷。
mstatus.PMIE
它在異常/中斷髮生後儲存 MIE
的舊值
mie
每個中斷在控制狀態暫存器 mie 中都有自己的使能位。這些位在 mie 中的位置對應於圖[[RISC-V 異常和中斷的原因.png]]。例如,mie[7]=1
對應於 M 模式中的時鐘中斷開啟。
注意:中斷可以被遮蔽,但是異常不能被遮蔽
mip
與 mie
有著相同的佈局,並且指示當前待處理的中斷。
三者相互配合
mstatus.MIE
=1 開啟接收中斷的總開關 = 1mie[7]
= 1 接收時鐘中斷mip[7]
= 1 當前待處理的中斷剛好有時鐘中斷
則可以處理機器的時鐘中斷。mstatus[MIE] & mie[7] & mip[7] ≠ 0
當一個hart 發生異常、中斷時
硬體會自動經歷如下的狀態轉換:
- 異常指令的
PC
被儲存在mepc
中,PC
被設定為mtvec
。- 對於同步異常:
pepc
指向導致異常的指令。 - 對於中斷:它指向中斷處理後應該恢復執行的位置。(這個由軟體設定)
- 對於同步異常:
- 根據異常/中斷源來設定
mcause
暫存器。 - 將
mtval
設定為出錯的地址或者其他適用於特定異常的資訊。 - 將
mstatus
中的MIE
位置置零以禁用中斷,並把先前的MIE
值保留到MPIE
中。 - 發生異常之前的許可權模式保留在
mstatus
的MPP
域中,再把許可權模式更改為M
。(如果處理器僅實現 M 模式,則有效地跳過這個步驟)。
處理中
為避免覆蓋整數暫存器中的內容,異常/中斷處理程式先在最開始用 mscratch
和整數暫存器(例如 a0
)中的值交換。通常,軟體會讓 mscratch
包含指向附加臨時記憶體空間的指標,處理程式用該指標來儲存其主體中將會用到的整數暫存器。在主體執行之 後,中斷程式會恢復它儲存到記憶體中的暫存器,然後再次使用 mscratch
和 a0
交換, 將兩個暫存器恢復到它們在發生異常之前的值。
返回
- 使用
mret
指令返回,mret
將PC
設定為mepc
- 將
mstatus
的MPIE
域複製到MIE
來恢復之前的中斷使能設定 - 並將許可權模式設定為
mstatus
的MPP
域中的值
委託
預設情況下,發生所有異常(不論在什麼許可權模式下)的時候,控制權都會被移交到 M
模式的異常處理程式。但是 Unix 系統中的大多數例外都應該進行 S
模式下的系統調 用。M
模式的異常處理程式可以將異常重新導向 S
模式,但這些額外的操作會減慢大多數 異常的處理速度。因此,RISC-V 提供了一種異常委託機制
。通過該機制可以選擇性地將中斷和同步異常交給 S 模式處理,而完全繞過 M 模式。
委託中斷
mideleg(Machine Interrupt Delegation,機器中斷委託)CSR控制將哪些中斷委託給 S模式
與 mip
和 mie
一樣,mideleg
中的每個位對應於”異常/中斷原因圖“相同的中斷。例如, mideleg[5]
對應於 S 模式的時鐘中斷,如果把它置位,S 模式的時鐘中斷將會移交 S 模式 的異常處理程式,而不是 M 模式的異常處理程式。
遮蔽委託的中斷
委託給 S 模式的任何中斷都可以被 S 模式的sie
CSR遮蔽。
sie
(Supervisor Interrupt Enable,監管者中斷使能)和 sip
(Supervisor Interrupt Pending,監管者中斷待處理)CSR 是 S
模式的控制狀態暫存器,他們是 mie
和 mip
的子集。它們有著和 M
模式下相同的佈局,但在 sie
和 sip
中只有與由 mideleg 委託的中斷對應的位才能讀寫。那些沒有被委派 的中斷對應的位始終為零。
委託異常
M 模式還可以通過 medeleg CSR 將同步異常委託給 S 模式
medeleg[15]
便會把 store page fault
(store 過程中出現的缺頁)委託給 S 模式。
基於頁面的虛擬記憶體
S 模式提供了一種傳統的虛擬記憶體系統,它將記憶體劃分為固定大小的頁來進行地址轉 換和對記憶體內容的保護。啟用分頁的時候,大多數地址(包括 load 和 store 的有效地址和 PC 中的地址)都是虛擬地址。要訪問實體記憶體,它們必須被轉換為真正的實體地址,這通 過遍歷一種稱為頁表的多叉樹實現。 RISC-V 的分頁方案以 SvX 的模式命名,其中 X 是以位為單位的虛擬地址的長度。RV64 支援多種分頁方案,但我們只介紹最受歡迎的一種,Sv39。
標誌位 | 說明 |
---|---|
V | 決定了該頁表項的其餘部分是否有效(V = 1 時有效) 。若 V = 0,則任何遍歷到此頁表項的虛址轉換操作都會導致頁錯誤。 |
R、W 和 X | 位分別表示此頁是否可以讀取、寫入和執行。如果這三個位都是 0,V=1 那麼這個頁表項是指向下一級頁表的指標,否則它是頁表樹的一個葉節點。 |
U | 位表示該頁是否是使用者頁面。若 U = 0,則 U 模式不能訪問此頁面,但 S 模式 可以。若 U = 1,則 U 模式下能訪問這個頁面 。 |
G | 表示這個對映是否對所有虛址空間有效,硬體可以用這個資訊來提高地址轉換的效能。這一位通常只用於屬於作業系統的頁面 |
A | 位表示自從上次 A 位被清除以來,該頁面是否被訪問過。 |
D | 位表示自從上次清除 D 位以來頁面是否被弄髒(例如被寫入)。 |
RSW | 域留給作業系統使用,它會被硬體忽略。 |
PNN | PPN 域包含物理頁號,這是實體地址的一部分。若這個頁表項是一個葉節點,那 麼 PPN 是轉換後實體地址的一部分。否則 PPN 給出下一節頁表的地址。 |
作業系統依賴於 A 位和 D 位來決定將哪些頁面 交換到輔存。定期清除 A 位有助於 OS 判斷哪 些頁面是最近最少使用 的。 置上 D 位表示換 出該頁面的成本更高, 因為它必須寫回輔存。
一個叫 satp(Supervisor Address Translation and Protection,監管者地址轉換和保護) 的 S 模式控制狀態暫存器控制了分頁系統。satp 有三個域。Mode域可以開啟分頁並選擇頁表級數。ASID(Address Space Identifier, 地址空間識別符號)域是可選的,它可以用來降低上下文切換的開銷。最後,PPN 欄位儲存 了根頁表的實體地址,它以 4 KiB 的頁面大小為單位。通常 M 模式的程式在第一次進入 S 模式之前會把零寫入 satp 以禁用分頁,然後 S 模式的程式在初始化頁表以後會再次進行 satp 暫存器的寫操
清除TLB快取
所有現代的處理器都用地 址轉換快取(通常稱為 TLB,全稱為 Translation Lookaside Buffer)來減少這種開銷。為了 降低這個快取本身的開銷,大多數處理器不會讓它時刻與頁表保持一致。這意味著如果操 作系統修改了頁表,那麼這個快取會變得陳舊而不可用。S 模式新增了另一條指令來解決 這個問題。這條sfence.vma
會通知處理器,軟體可能已經修改了頁表,於是處理器可以 相應地重新整理轉換快取。它需要兩個可選的引數,這樣可以縮小快取重新整理的範圍。一個位於 rs1,它指示了頁表哪個虛址對應的轉換被修改了;另一個位於 rs2,它給出了被修改頁表 的程式的地址空間識別符號(ASID)。如果兩者都是 x0,便會重新整理整個轉換快取。
特權指令:
mret
: machine-mode trap returnsret
: supervisor-mode trap returnsfence.vma
: supervisor-mode fence.virtual memory addreeewfi
: wait for interruptcsrr
,讀取一個 CSR 的值到通用暫存器。如:csrr t0, mstatus
,讀取mstatus
的值到t0
中。csrw
,把一個通用暫存器中的值寫入 CSR 中。如:csrw mstatus, t0
,將t0
的值寫入mstatus
。csrs
,把 CSR 中指定的 bit 置 1。如:csrsi mstatus, (1 << 2)
,將mstatus
的右起第 3 位置 1。csrc
,把 CSR 中指定的 bit 置 0。如:csrci mstatus, (1 << 2)
,將mstatus
的右起第 3 位置 0。csrrw
,讀取一個 CSR 的值到通用暫存器,然後把另一個值寫入該 CSR。如:csrrw t0, mstatus, t0
,將mstatus
的值與t0
的值交換。csrrs
,讀取一個 CSR 的值到通用暫存器,然後把該 CSR 中指定的 bit 置 1。csrrc
,讀取一個 CSR 的值到通用暫存器,然後把該 CSR 中指定的 bit 置 0。