自己写操作系统2——进入保护模式


实模式下不能访问1M以上的内存,而且实模式不能提供内存保护。

启示开启实模式只要3个步骤

1.设置gdt全局描述符表

2.设置a20开始访问1M以上内存的必须步骤

3.设置cr0的pe为1,这个表明已经进入了保护模式中。

;
;protect.ASM
;
;
;
SECTION ALIGN=16 VSTART=0x7E00
MOV AX , [cs:SS_BASE]
MOV SS , AX
XOR SP , SP
MOV AX , [cs:DS_BASE]
MOV DS , AX
MOV BX ,  0x7C00

;创建#1描述符,保护模式下的代码段描述符
mov dword [bx],0x0
mov dword [bx+0x04],0x0
;创建#1描述符,保护模式下的代码段描述符
mov dword [bx+0x08],0x7e0001ff    
mov dword [bx+0x0c],0x00409800     

;创建#2描述符,保护模式下的数据段描述符(文本模式下的显示缓冲区) 
mov dword [bx+0x10],0x8000ffff     
mov dword [bx+0x14],0x0040920b     

;创建#3描述符,保护模式下的堆栈段描述符
mov dword [bx+0x18],0x00007a00
mov dword [bx+0x1c],0x00409600

;创建#4描述符,保护模式下的代码段描述符
mov dword [bx+0x20],0x7e0001ff
mov dword [bx+0x24],0x00F09800

;创建#5描述符,保护模式下的数据段描述符(文本模式下的显示缓冲区)
mov dword [bx+0x28],0x8000ffff
mov dword [bx+0x2C],0x00F0920b

;创建#6描述符,保护模式下的堆栈段描述符
mov dword [bx+0x30],0x00007a00
mov dword [bx+0x34],0x00F09600

mov bx , GDT_SIZE
mov word [bx] , 47
mov dword [bx+2], 0x7C00

lgdt [bx]

in al , 0x92
or al , 0000_0010B
out 0x92,al

cli
mov eax , cr0
or eax , 0x01
mov cr0 ,eax

jmp dword 0x0008:(PROTECT_BEGIN-0x7E00)

DS_BASE DW 0x0000
SS_BASE DW 0x2000
[bits 32]
ZERO_SECTOR    DD 0x0,0x0
CS_SECTOR      DD 0x0,0x0
DS_SECTOR      DD 0x0,0x0
SS_SECTOR      DD 0x0,0x0
CS_DPL3_SECTOR DD 0x0,0x0
DS_DPL3_SECTOR DD 0x0,0x0
GDT_SIZE       DW 0x00
DGT_BASE       DD 0x00000000

PROTECT_BEGIN:
mov ax , 16
mov ds , ax
mov byte [0] , 'P'
mov byte [1] , 0x07
mov byte [2] , 'r'
mov byte [3] , 0x07
mov byte [4] , 'o'
mov byte [5] , 0x07
mov byte [6] , 't'
mov byte [7] , 0x07
mov byte [8] , 'e'
mov byte [9] , 0x07
mov byte [10] , 'c'
mov byte [11] , 0x07
mov byte [12] , 't'
mov byte [13] , 0x07



jmp $


times 512 - ($-$$) db 0
很多人会问设置了cr0不实就进入到保护模式下了么,那么cpu的cs不就开始做检测了么,为什么jmp还能跳转呢,因为CPU其实使用的实cs段的高速缓存,而不实真正的cs,在实模式下也是如此,只不过实模式下的高速缓存的值是cs向左移动4位形成的,而保护模式是使用选择子去找段描述符,在缓存到高速缓存中的,所以在保护模式下不是每次都去cs的段描述符去查找基地址的,而是去缓存中找,这样速度就快多了。

因为此时的缓存中保护的还是实模式下的内存地址所以程序可以继续执行,但是我们要进入保护模式就必须刷新cs让其变成段选择子的地址,这样就用一个长跳转将cs中的值进行刷新。跳转完成后要设置新的ds,fs,ss的选择子,要不就会出现些一想不到的问题。

mov eax , cr0
or eax , 0x01
mov cr0 ,eax
jmp dword 0x0008:(PROTECT_BEGIN-0x7E00)


最后用dd命令将此程序写入虚拟硬盘镜像的第三个扇区:

dd if=protect.bin of=XXXXX.VHD seek=2 bs=512 count=1

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值