進入保護模式

2021-07-10 03:21:44 字數 2984 閱讀 3527

本文為

每個描述符佔8位元組, 下圖中, 上面位高32位, 下面為低32位

disk&boot --> ata channel 0 --> first hd/cd on channel 0 --> type of disk image這個選項是vpc, 我用2.6.2配置時選vpc無法啟動, 得選flat才可以, 2.6.0貌似選vpc可以

[plain]view plain

copy

print

?mov ax, cs  

mov ss, ax  

mov sp, 0x7c00  

; 計算gdt所在位址的邏輯段位址  

mov ax, [cs:gdt_base + 0x7c00]  

mov dx, [cs:gdt_base + 2 +0x7c00]  

mov bx, 0x10  

div bx  

mov ds, ax              ; 商為段位址  

mov bx, dx              ; 餘數為偏移位址  

; 全域性描述符#0, 第一項必須為0  

mov dword [bx + 0x00], 0x00000000  

mov dword [bx + 0x04], 0x00000000  

; 全域性描述符#1, **段描述符  

; 粒度位位元組(g = 0), 屬於儲存器段(s = 1)  

; 32位的段(d/b = 1), 位於記憶體當中(p = 1)  

; 段的特權級位0(dpl = 00)  

; 只執行(type = 1000)  

mov dword [bx + 0x08], 0x7c0001ff         

mov dword [bx + 0x0c], 0x00409800  

; 全域性描述符#2, 資料段描述符  

; 粒度位位元組(g = 0), 屬於儲存器段(s = 1)  

; 32位的段(d/b = 1), 位於記憶體當中(p = 1)  

; 段的特權級位0(dpl = 00)  

; 可讀可寫, 向上擴充套件的資料段(type = 0010)  

mov dword [bx + 0x10], 0x8000ffff  

mov dword [bx + 0x14], 0x0040920b  

; 全域性描述符#3, 棧段描述符  

; 粒度位位元組(g = 0), 屬於儲存器段(s = 1)  

; 32位的段(d/b = 1), 位於記憶體當中(p = 1)  

; 段的特權級位0(dpl = 00)  

; 可讀可寫, 向下擴充套件的資料段, 在這裡是棧段(type = 0110)  

mov dword [bx + 0x18], 0x00007a00  

mov dword [bx + 0x1c], 0x00409600  

; 初始化全域性描述符表  

mov word [cs:gdt_size + 0x7c00], 31     ; 全域性描述符表界限(總位元組數 - 1)  

lgdt [cs:gdt_size + 0x7c00]             ; 載入全域性描述符表  

; 開a20  

in al, 0x92  

or al, 0x02  

out 0x92, al  

cli                                     ; 保護模式下中斷機制尚未建立, 關中斷  

; 開啟保護模式, cr0暫存器0位置1  

mov eax, cr0  

or eax, 1  

mov cr0, eax  

; 進入保護模式, 詳情參見本書p199 11.7 清空流水線並序列化處理器  

; 注意, 不管你用的是16位遠轉移, 還是32位遠轉移  

; 因為現在已經處於保護模式下, 處理器都將把第乙個引數0x0008視為選擇子  

; 而不是實模式下的邏輯段位址  

jmp dword 0x0008:_protectmode  

[bits 32]  

_protectmode:  

; 選擇子00000000000_10_000b, 索引為2的描述符  

mov ax, 0x10  

mov ds, ax  

mov byte [0x00], 'h'  

mov byte [0x02], 'e'  

mov byte [0x04], 'l'  

mov byte [0x06], 'l'  

mov byte [0x08], '0'  

mov byte [0x0a], ' '  

mov byte [0x0c], 'o'  

mov byte [0x0e], 'n'  

mov byte [0x10], 'z'  

mov byte [0x12], '.'  

mov byte [0x14], '.'  

mov byte [0x16], '.'  

hlt                   ; 因為關中斷, 所以處理器不會被喚醒  

gdt_size    dw 0  

gdt_base    dd 0x7e00  

times       510 - ($ - $$) db 0  

dw 0xaa55 

進入保護模式

以下圖2,圖4和圖5截自intel手冊 每個描述符佔8位元組,下圖中,上面位高32位,下面為低32位 disk boot ata channel 0 first hd cd on channel 0 type of disk image這個選項是vpc,我用2.6.2配置時選vpc無法啟動,得選fl...

進入保護模式總結

1.最主要的就是那個jmp dword,一切都是為了jmp做準備 2.int 13h讀取扇區,既可以讀硬碟,又可以讀軟盤,應該是兩個的驅動器號不同 這個還沒搞清楚,現在只會讀軟盤 用硬碟映像的時候,總是說找不到引導裝置,不知道是哪兒的引數錯了。一些細節 cl是讀取的扇區號,1就是第1個扇區,並不是從...

PM複習 進入保護模式

我們知道,現在大部分的cpu都是32位的,我們編寫的os當然也想在執行在32位的模式下,因為32位的cpu功能自然比16位的強大許多,32位的cpu在硬體給予了os很大的支援。但是當機器剛剛啟動時,cpu是執行在16位模式下的,所以我們必須學習怎麼樣進入32位模式,也即保護模式。16位模式也就是實模...