Big Mode
程序员文章站
2022-05-19 13:40:55
...
- 首先,说下开机后CPU的第一个动作:CS=DS=ES=SS=0xFFFF,IP=0x0000。因为当前模式是实模式,CS:IP指向的地址实际是0xFFFF0,这个地址存的是个far jump,去跳到BIOS的POST阶段(BIOS在FlushROM执行和RAM里执行的细节还需要了解),其中一个目的就是重置CS寄存器。
- 什么是32位Big Mode(或称Flat Mode)?它在什么情景下会被用到?解决什么问题的?中间还会牵扯开启A20
- 80286之前,地址总线是20位的,也就是说最多能寻址2^20次方地址,也就是1M,当然80286增加了地址总线宽度到24位,而这块又会牵扯到A20。那么如果本身物理内存超出1M,而我们又在实模式,怎么办呢?我们就需要Big Mode。但是Big Mode能够解决的问题只是对于大内存的访问问题,对于执行还是限制在1M范围之内。
- 总体来说,其实是实模式利用了保护模式的段选择子特性,才扩大了寻址的范围。
EnterBigMode proc
; construct gdtr
xor eax, eax
mov eax, cs
shl eax, 4
add eax, GDT_TABLE
mov dword ptr[Gdtr + 2], eax
mov word ptr [Gdtr], 0x18
;load gdtr
lgdtr fword ptr [Gdtr]
;set rm jump
mov ax, cs
mov word ptr [RM_Segment], ax
call @f
@@:
pop ax
add ax, RM_Offset - ($ - 1)
add ax, 4
mov word ptr [RM_Offset], ax
;set pm jump
call @f
@@:
pop ax
add ax, PM_Offset - ($ - 1)
add ax, 4
mov word ptr [PM_Offset], ax
EnableA20
;enable pm
mov eax, cr0
or eax, 0x01
mov cr0, eax
; far jump to pm
DB 0xEA
PM_Offset: DW 0
PM_Selector: DW 0x10
mov eax, 0x08
mov es, eax
mov ds, eax
;disable pm
mov eax, cr0
and al, 0xFE
mov cr0, eax
; far jump to rm
DB 0xEA
RM_Offset: DW 0
RM_Segment: DW 0
ret
EnterBigMode Endp
Gdtr:
DW 0 ; Limit
DD 0 ; Base
GDT_TABLE:
DW 0, 0, 0, 0 ; 0x00 :0
DW 0xFFFF, 0, 0x9200, 0x00CF ; 0x08 :DS
DW 0xFFFF, 0, 0x9A00, 0x000F ; 0x10 :CS
EnableA20 macro
push ax
in al, 0x92
or al, 00000010b
out 0x92, al
pop ax
macro