仿照着写个bootloader(6) 保护模式下修改代码段

    标题让我想起win驱动中修改只读页的内容:新申请一个PTE指向该页,PTE中的权限改为读写,就能修改页面内容啦。

    现在阶段我的bootloader还没有建立起分页机制,仅仅开启分段,因此,通过修改PTE啥的肯定不奏效,能做的只有修改段描述符了。

    先看下我代码中的段描述表:

mov dword [bx],0x00000000
mov dword [bx+4],0x00000000
;代码段 0x7c00 权限 读执行
add bx,0x08
mov dword [bx],0x7c0001ff 
mov dword [bx+4],0x00409A00
;数据段 0x7c00 权限 读写
add bx,0x08
mov dword [bx],0x7c0001ff 
mov dword [bx+4],0x00409200

mov word [cs:gdtSize+0x7c00],0x08*3-1
lgdt [cs:0x7c00+gdtSize]
读写代码段内存的代码:

Code:
	;1)直接读取代码段
	lea edx,[cs:Code]
	mov eax,[cs:edx]
	
	;2)直接修改代码段
	xor eax,eax
	lea edx,[cs:Code]
	mov [cs:edx],eax
	;3)段选择子指向代码段,但是把权限改为数据段
	xor eax,eax
	mov ax,0x10
	mov ds,ax
	lea edx,[cs:Code]
	mov word [edx],0x9090
jmp Code
运行bochs,执行到1)处时:

【黄色高亮处】反汇编内存0x7c76,数值为2e8d1576,执行完mov eax,[cs:edx]后 eax的内容为0x76158d2e (注意是小端机)。可知,代码成功读取了0x7c76处的内容

再往下执行到2)处:出错了,bochs也提示 no write access to seg。

其实,也不算出错,只是一个页面异常,没被捕获处理。怪我了,还是个简单的bootloader。

回过头看下,进入保护模式时,这个代码段的权限:


bochs说的很清楚了,代码段,起始于0x7c00权限是读执行。当然,如果段描述符的TYPE字段改为0x4096即只执行,那运行到第一步时也会出现异常。

好吧,到这有个问题:难道在未开启页机制前,代码段不能写了?再进一步,没法往代码段设置int 0x3断点了(不能实时调试)?

这倒也不是,只要为该段安装一个新的描述符,并把其可读写的数据段,最后加载该描述符,这样就可以修改代码段内的数据了。现在来看下修改后的代码:

flush:
Code:
	;段选择子指向代码段,但是把权限改为数据段
	xor eax,eax
	mov ax,0x10
	mov ds,ax
	lea edx,[cs:Code]
	mov word [edx],0x9090
jmp Code
bochs运行起来:


ds加载0x10后(第3个段描述符),然后mov ds:[edx],0x90909090,其实就是修改0x7c76处的内存。修改结束后反汇编结果

0x7c76 0x7c77 为nop,修改成功,yes!

   

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值