xv6源码阅读——xv6的启动,进程初识
生活随笔
收集整理的這篇文章主要介紹了
xv6源码阅读——xv6的启动,进程初识
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
目錄
- 說明
- 1.xv6的啟動
- 1.1.kernel/entry.S
- 1.2.kernel/start.c
- 1.3.kernel/main.c
- 1.4.kernel/proc.c
- 2.進程
- 2.1.進程管理
- 2.2 進程狀態
- 參考資料
說明
- 閱讀的代碼是 xv6-riscv 版本的
涉及到的文件如下
- kernel
entry.S、start.c、main.c、kalloc.c、vm.c、proc.c、swtch.S、proc.h、printf.c、trap.c - user
initcode.S
1.xv6的啟動
- 這一部分講述xv6 在啟動過程中的配置以及 xv6 中第一個 shell 進程的創建過程
1.1.kernel/entry.S
-
當 xv6 的系統啟動的時候,首先會啟動一個引導加載程序(存在 ROM 里面),之后裝載內核程序進內存
注意由于只有一個內核棧,內核棧部分的地址空間可以是固定,因此 xv6 啟動的時候并沒有開啟硬件支持的 paging 策略,也就是說,對于內核棧而言,它的物理地址和虛擬地址是一樣的 -
在機器模式下,CPU是從_entry開始執行的
1.2.kernel/start.c
- 函數start執行一些僅在機器模式下允許的配置,然后切換到管理模式。RISC-V提供指令mret以進入管理模式,該指令最常用于將管理模式切換到機器模式的調用中返回。而start并非從這樣的調用返回,而是執行以下操作:它在寄存器mstatus中將先前的運行模式改為管理模式,它通過將main函數的地址寫入寄存器mepc將返回地址設為main,它通過向頁表寄存器satp寫入0來在管理模式下禁用虛擬地址轉換,并將所有的中斷和異常委托給管理模式。
- strart()函數的調用
- 函數start執行一些僅在機器模式下允許的配置,然后切換到管理模式。
- 它在寄存器mstatus中將先前的運行模式改為管理模式
- 它通過將main函數的地址寫入寄存器mepc將返回地址設為main
- 它通過向頁表寄存器satp寫入0來在管理模式下禁用虛擬地址轉換,并將所有的中斷和異常委托給管理模式。
- 對時鐘芯片進行編程以產生計時器中斷。
- start通過調用mret“返回”到管理模式。
- 函數start執行一些僅在機器模式下允許的配置,然后切換到管理模式。
1.3.kernel/main.c
- 主要工作就是初始化一些配置
1.4.kernel/proc.c
- 下面我們看一看userinit()函數具體干了些什么
調用邏輯
- 調用allocproc()函數來獲取一個空閑進程,及狀態為 UNUSED 的進程
- 在proc[NPROC]中尋找一個 狀態為 UNUSED 的進程
- 找不到返回0
- 找到了對該進程進行一些初始化配置,然后返回一個struct proc
- 計算 pid
- 調用 kalloc() 分配一個 trapframe 。
- 從空閑鏈表中分配一塊空閑頁
- 分配失敗則調用freeproc(p)釋放
- 調用函數proc_pagetable(p)為用戶態分配一個頁表
- 設置 context 寄存器 ra、sp(進程切換)
- ra:用戶態執行的上下文
- sp:棧指針
- 把初始化代碼(一段機器代碼)放入進程的頁表中(只是加載進去,并沒有執行)
- 準備從內核到用戶的第一次“返回”。
- epc = 0 用戶程序計數器
- sp = PGSIZE用戶棧指針
- 設置進程名稱為 initcode,進程工作目錄為 /
- 設置進程狀態為 RUNNABLE
- 在proc[NPROC]中尋找一個 狀態為 UNUSED 的進程
- 最后返回 kernel/main.c 中執行進程調度程序 scheduler(),然后經調度后才開始執行那一段機器代碼。
2.進程
2.1.進程管理
- proc結構體
- 用于管理進程的變量和函數
2.2 進程狀態
在xv6中進程會有5中狀態
UNUSED
SLEEPING
RUNNABLE
RUNNING
ZOMBIE
參考資料
- http://xv6.dgs.zone/tranlate_books/book-riscv-rev1/c1/s0.html
- xv6-riscv源碼
總結
以上是生活随笔為你收集整理的xv6源码阅读——xv6的启动,进程初识的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: lightgbm 数据不平衡_不平衡数据
- 下一篇: 关于神经网络训练的一些建议笔记