dafengqixi
初级用户
积分 54
发帖 17
注册 2009-11-27
状态 离线
|
『楼 主』:
谁能详细解释一下下面这段代码?
下面就来告诉大家怎么做到在实模式下访问4GB内存。这种技术需要保护模式支持,所以只能在80386以上的CPU中运行。 学过一点保护模式的读者都知道,在保护模式下段地址寄存器中内容的不再象实模式那样是段的基地址,而只是描述符表中的一个索引,段的真正信息(基地址、限长、访问权限等)放在描述符表中,当访问一数据时CPU会从描述符表取出段的描述信息来检查访问是否合法,不合法就产生异常,合法则允许访问。每次访问都要读出描述符信息再检查是一个比较费时的过程,为了提高内存访问的速度,Intel公司在CPU中为每个段寄存器配备了一个高速缓冲器来存放段的描述符信息,这样访问内存时就不用频繁地访问描述表,只要从高速缓冲进行校验就行,只有在改变段寄存器的值时才访问描述符表将新的段描述符装入高速缓冲中。我们就利用CPU的这个特性来达成我们的目的。首先进入保护模式,把某个段寄存器设为基地址0H,限长4GB,然后再退回实模式。这样就可以通过该段寄存器直接访问4GB的内存了(实际上只能访问你的机器上所有的内存而并不是4GB)!还有一点要注意的是一定要打开A20线,否则……别怪我言之不预!
下面列出所需要的代码:
========================================================
Make4GBSegment MACRO _seg
local MyGdt,PM_Service,Old_GDTR,GDTR,Real_Service,MyGdt
local _Exit
Push DS
Push ES
Pushad
Pushfd ;保护现场
Sub EBX,EBX
Mov BX,CS
Mov DS,BX
Shl EBX,4
Push EBX
Rol EBX,8
Mov BYTE Ptr MyGdt[8+7],BL
Mov BL,BYTE Ptr MyGdt[8+5]
Ror EBX,8
Mov Dword Ptr MyGdt[8+2],EBX
Pop EBX
lea EBX,[EBX+MyGdt]
Mov DWORD Ptr [GDTR+2],EBX
Mov WORD Ptr [GDTR],31 ;建立新的GDTR
Cli
Sgdt FWORD Ptr [Old_GDTR] ;保存旧的GDTR
Lgdt FWORD Ptr [GDTR] ;设置新的GDTR
Mov EBX,CR0
Or BL,1
Mov CR0,EBX ;进入保护模式
db 0eah
DW PM_Service
DW 8 ;跳转到保护模式代码执行
PM_Service:
Mov AX,16
Mov _seg,AX
Mov EBX,CR0
And EBX,0fffffffeh
Mov CR0,EBX
DB 0eah
DW Real_Service
DW seg Real_Service
Real_Service:
Lgdt FWORD Ptr [Old_GDTR]
Popfd ;恢复现场
Popad
Pop ES
Pop DS
Jmp _Exit
MyGdt DQ 0
DW -1,0,9a00h,0
DW -1,0,9200h,0cfh
DQ 0
Old_GDTR DW 0,0,0
GDTR DW 0,0,0
_Exit:
Endm
========================================================
在这里为了方便我只把FS改成4GB段,读者可以按需要自行决定使用哪个段寄存器。只要将这段代码拷贝到你的程序中,然后在开始的时候调用它,就可以通过该段寄存器直接访问大内存了,爽吧!最后还有一点一定要注意:如果你的程序运行时有任何扩展内存管理程序存在(HIMEM、EMM386等)都要千万小心,因为很容易会破坏到它们的内部数据或其他程序的数据,如果是这样就只有死机一条路可走了。切记切记!我的建议是最好从内存顶端开始使用扩展内存。这时破坏其他数据的可能要小一些。
===========================================
这是我找到的一些资料,但是对其中的代码不甚了解,这段程序的作用都已经给出来了,希望能有高人详细解释一番,如果能每行都注释更好
|
|