1.3.5 head.s開始執行(2)
小貼士取段暫存器指令(load segment instruction):該組指令的功能是把記憶體單元的乙個「低字」傳送給指令中指定的16位暫存器,把隨後的乙個「高字」傳給相應的段暫存器(ds、es、fs、gs和ss)。其指令格式如下:
lds/les/lfs/lgs/lss reg, mem指令lds(load data segment register)和les(load extra segment register)在8086cpu中就存在,而lfs和lgs(load extra segment register)、lss(load stack segment register)是80386及其以後cpu中才有的指令。 如果reg是16位暫存器,那麼mem必須是32位指標;如果reg是32位暫存器,那麼men必須是48位指標,其低32位給指令中指定的暫存器,高16位給指令中的段暫存器。
0x10將ss的值設定為與前面4個段選擇符的值相同。這樣,ss與前面講解過的4個段選擇符相同,段基址都指向0x000000,段限長都是8mb,特權級都是核心特權級,後面的壓棧動作就要在這裡進行。
特別值得一提的是,現在剛剛從實模式轉變到保護模式,段基址的使用方法和實模式差別非常大,要使用gdt產生段基址,前面講到的那幾行設定段選擇符的指令本身都是要用gdt定址的。現在就能清楚地看出,如果沒有setup程式在16位實模式下模擬32位保護模式而建立的gdt,恐怕前面這幾行指令都無法執行。
注意,棧頂的增長方向是從高位址向低位址的。參見圖1-27的下部,注意棧段基址和esp在圖中的位置。
我們現在回憶一下圖1-8中對棧指標暫存器的設定,那時是設定sp,而這時是設定esp,多了乙個字母e,這是為適應保護模式而做的調整。這段內容對應的**如下:
//**路徑:boot/head.s圖1-27 設定棧
head程式接下來對中斷描述符表進行設定,**如下所示:
//**路徑:boot/head.s小貼士call setup_idt
……
setup_idt:
lea ignore_int,%edx
movl $0x00080000,%eax
movw %dx,%ax /*
selector
= 0x0008
= cs */
movw $0x8e00,%dx /* interrupt
gate-dpl=0
, present */
lea _idt,%edi
mov $256,%ecx
rp_sidt:
movl %eax,(%edi)
movl %edx,4(%edi)
addl $8,%edi
dec %ecx
jne rp_sidt
lidt idt_descr
ret
乙個中斷描述符的結構如下:
中斷描述符為64位,包含了其對應中斷服務程式的段內偏移位址(offset)、所在段選擇符(selector)、段特權級(dpl)、段存在標誌(p)、段描述符型別(type)等資訊,供cpu在程式中需要進行中斷服務時找到相應的中斷服務程式。其中,第0~15位和第48~63位組合成32位的中斷服務程式的段內偏移位址;第16~31位為段選擇符(selector),定位中斷服務程式所在段;第47位為段存在標誌(p),用於標識此段是否存在於記憶體中,為虛擬儲存提供支援;第45~46位為特權級標誌(dpl),特權級範圍從0~3;第40~43位為段描述符型別標誌(tpye),中斷描述符對應的型別標誌為1110(0xe),即將此段描述符標記為「386中斷門」。
這是重建保護模式下中斷服務體系的開始,程式先讓所有的中斷描述符預設指向ignore_int這個位置(將來main函式裡面還要讓中斷描述符對應具體的中斷服務程式),之後還要對中斷描述符表暫存器的值進行設定。圖1-28顯示了具體的操作狀態。
圖1-28 設定中斷描述符表 點評
構造中斷描述符表,並使所有中斷服務程式指向同一段只顯示一行提示資訊就返回的服務程式,先使中斷機制的整體架構搭建起來(實際的中斷服務程式掛接則在main函式中完成)。從程式設計技術上講,這是乙個佔位的操作方式,也防止了「野指標」。
現在,head程式要廢除已有的gdt,並在核心中的新位置重新建立全域性描述符表,如圖1-29所示。其中第二項和第三項分別為核心**段描述符和核心資料段描述符,其段限長均被設定為16mb,並設定全域性描述符表暫存器的值。
圖1-29 重新建立gdt
1 3 5 head s開始執行(5)
1.3.5 head.s開始執行 5 上述動作的 如下 路徑 boot head.s movl pg0 7,pg dir set present bit user r w movl pg1 7,pg dir 4 movl pg2 7,pg dir 8 movl pg3 7,pg dir 12 mov...
kernel啟動流程 head S的執行 1 概述
kernel版本 5.10 平台 arm64 本專題主要基於 arm64 linux head.s的執行流程 系列文章,前者是基於3.18,本專題針對的是核心5.10。主要分析head.s的執行過程。vmlinux.lds中定義了入口點為 text entry text sections kimag...
開始 執行 命令大全
1.gpedit.msc 組策略 2.sndrec32 錄音機 3.nslookup ip位址偵測器 4.explorer 開啟資源管理器 5.logoff 登出命令 6.tsshutdn 60秒倒計時關機命令 7.lusrmgr.msc 本機使用者和組 8.services.msc 本地服務設定 ...