您的位置:首页 > 产品设计 > 产品经理

【PM复习】进入保护模式改进

2010-01-24 12:07 274 查看
在前面的建立GDT的代码中,只是用db,dw直接来写二进制的数据,当我们要在GDT中添加很多描述符的时候,这样做就显得很晦涩难懂。在这里我们就建立1个宏,此宏以比较方便的方法来建立1个描述符,有3个入口参数,分别是段基址,段界限和段属性,代码如下:

Code:

;%1 Base

;%2 Limit

;%3 Attr

%macro Descriptor 3

dw %2 & 0ffffh

dw %1 & 0ffffh

db (%1 >> 16) & 0ffh

db %3 & 0ffh

db ((%3 >> 8) & 0ffh) | ((%2 >> 16) & 0fh)

db (%1 >> 24) & 0ffh

%endmacro

我们看到,就是把入口参数通过移位和逻辑操作符来分隔到合适的地方,对照着描述符的结构就可以很轻松地完成此工作。

还有1个地方可以抽象,就是填充描述符的段基址的代码,如果要填充很多个描述符的段基址,那么重复的代码就会很多,可以选择用函数或者宏来实现,我们这里用宏来实现吧。入口地址有2个,一个是段描述符在实模式下的偏移,另一个是目标代码段的偏移,代码如下:

Code:

;%1 Descriptor's Offset

;%2 Segment's Offset

%macro Fill_Descriptor 2

xor eax,eax

mov ax,cs

shl eax,4

add eax,%2

mov word [%1 + 2],ax

shr eax,16

mov byte [%1 + 4],al

mov byte [%1 + 7],ah

%endmacro

这样我们的代码就可以简洁很多了,下面在上一节的基础上修改的代码:

Code:

;%1 Base

;%2 Limit

;%3 Attr

%macro Descriptor 3

dw %2 & 0ffffh

dw %1 & 0ffffh

db (%1 >> 16) & 0ffh

db %3 & 0ffh

db ((%3 >> 8) & 0ffh) | ((%2 >> 16) & 0fh)

db (%1 >> 24) & 0ffh

%endmacro



;%1 Descriptor's Offset

;%2 Segment's Offset

%macro Fill_Descriptor 2

xor eax,eax

mov ax,cs

shl eax,4

add eax,%2

mov word [%1 + 2],ax

shr eax,16

mov byte [%1 + 4],al

mov byte [%1 + 7],ah

%endmacro



org 0100h

jmp LABEL_BEGIN



[section .gdt]

LABEL_DESC_DUMMY:

Descriptor 0,0,0

LABEL_DESC_CODE32:

Descriptor 0,0ffffh,409ch

LABEL_DESC_VIDEO:

Descriptor 0b8000h,0ffffh,4092h



GDT_Len equ $ - LABEL_DESC_DUMMY

GDT_Ptr:

dw GDT_Len - 1

dd 0



Selector_Code32 equ LABEL_DESC_CODE32 - LABEL_DESC_DUMMY

Selector_Video equ LABEL_DESC_VIDEO - LABEL_DESC_DUMMY



[section .s16]

[bits 16]

LABEL_BEGIN:

mov ax,cs

mov ds,ax

mov es,ax



Fill_Descriptor LABEL_DESC_CODE32,LABEL_CODE32



xor eax,eax

mov ax,ds

shl eax,4

add eax,LABEL_DESC_DUMMY

mov dword [GDT_Ptr + 2],eax



lgdt [GDT_Ptr]



cli



in al,92h

or al,00000010b

out 92h,al



mov eax,cr0

or al,1

mov cr0,eax



jmp Selector_Code32:0



[section .s32]

[bits 32]

LABEL_CODE32:

mov ax,Selector_Video

mov gs,ax

mov ah,0ch

mov al,'x'

mov [gs:80 * 10],ax

jmp $

运行结果与上一节相同。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: