微机接口技术实验.docx

上传人:b****4 文档编号:3933682 上传时间:2022-11-26 格式:DOCX 页数:15 大小:147.13KB
下载 相关 举报
微机接口技术实验.docx_第1页
第1页 / 共15页
微机接口技术实验.docx_第2页
第2页 / 共15页
微机接口技术实验.docx_第3页
第3页 / 共15页
微机接口技术实验.docx_第4页
第4页 / 共15页
微机接口技术实验.docx_第5页
第5页 / 共15页
点击查看更多>>
下载资源
资源描述

微机接口技术实验.docx

《微机接口技术实验.docx》由会员分享,可在线阅读,更多相关《微机接口技术实验.docx(15页珍藏版)》请在冰豆网上搜索。

微机接口技术实验.docx

微机接口技术实验

 

微机接口技术实验

实验五保护模式下的中断处理

 

姓名:

胡诣嵩

学号:

20053449

日期:

2008-5-30

 

一实验名称

保护模式下的中断处理

二实验目的

1.通过本实验了解、熟悉保护模式下的中断以及它的处理方式。

2.巩固微机接口课程学习的80386DX在保护模式下相关的知识点。

三简述程序执行过程

1、作切换到保护方式的准备

2、切换到保护方式

3、程序循环等待,当有键盘和时钟中断时,调用中断服务程序显示字符

4、切换回实模式

四实验源程序

;功能:

演示保护方式下的中断处理过程

.386P

;----------------------------------------------------------------------------

;存储段描述符结构类型定义

;----------------------------------------------------------------------------

DescSTRUC

LimitLDW0;段界限(BIT0-15)

BaseLDW0;段基地址(BIT0-15)

BaseMDB0;段基地址(BIT16-23)

AttributesDB0;段属性

LimitHDB0;段界限(BIT16-19)(含段属性的高4位)

BaseHDB0;段基地址(BIT24-31)

DescENDS

;----------------------------------------------------------------------------

;伪描述符结构类型定义(用于装入全局或中断描述符表寄存器)

;----------------------------------------------------------------------------

PDescSTRUC

LimitDW0;16位界限

BaseDD0;32位基地址

PDescENDS

;----------------------------------------------------------------------------

;门描述符结构类型定义

;----------------------------------------------------------------------------

GateSTRUC

OffsetLDW0;32位偏移的低16位

SelectorDW0;选择子

DCountDB0;双字计数

GTypeDB0;类型

OffsetHDW0;32位偏移的高16位

GateENDS

;----------------------------------------------------------------------------

;存储段描述符类型值说明

;----------------------------------------------------------------------------

ATDREQU90h;存在的只读数据段类型值

ATDWEQU92h;存在的可读写数据段属性值

ATDWAEQU93h;存在的已访问可读写数据段类型值

ATCEEQU98h;存在的只执行代码段属性值

ATCEREQU9ah;存在的可执行可读代码段属性值

ATCCOEQU9ch;存在的只执行一致代码段属性值

ATCCOREQU9eh;存在的可执行可读一致代码段属性值

DA_386IGateEQU8Eh;386中断门类型值

;----------------------------------------------------------------------------

DSEGSEGMENTUSE16;16位数据段

;----------------------------------------------------------------------------

_SavedIMREG_Mdb0;中断屏蔽寄存器值

_SavedIMREG_Sdb0;

DB512dup(0)

TopOfStackLABELBYTE

GDTLABELBYTE;全局描述符表

DUMMYDesc<>;空描述符

CodeDesc<0ffffh,,,ATCER,,>;代码段描述符

DataVDesc<0ffffh,,,ATDW,,>;源数据段描述符

DataPDesc<0ffffh,,,ATDWA,,>;目标数据段描述符

Code32Desc<0ffffh,,,ATCER,40h,>;代码段描述符

;----------------------------------------------------------------------------

GDTLen=$-GDT;全局描述符表长度

VGDTRPDesc;伪描述符

;----------------------------------------------------------------------------

Code_Sel=Code-GDT;代码段选择子

DataV_Sel=DataV-GDT;源数据段选择子

DataP_Sel=DataP-GDT;目标数据段选择子

Code32_Sel=Code32-GDT;目标数据段选择子

;----------------------------------------------------------------------------

;IDT

ALIGN32

IDTLABELBYTE

IDT_00_1FGate32dup(

IDT_20Gate1dup(

IDT_21Gate1dup();<键盘中断服务程序的中断门>

IDT_21_7FGate94dup(

IDT_80Gate1dup(

IDTLen=$-IDT;中断描述符表长度

VIDTRPDesc;伪描述符

_wSSValueInRealModedw0

_wSPValueInRealModedw0

_SavedIDTRdd0;用于保存IDTR

dd0

;----------------------------------------------------------------------------

DSEGENDS;数据段定义结束

;----------------------------------------------------------------------------

;打开A20地址线

;----------------------------------------------------------------------------

EnableA20MACRO

pushax

inal,92h

oral,00000010b

out92h,al

popax

ENDM

;----------------------------------------------------------------------------

;关闭A20地址线

;----------------------------------------------------------------------------

DisableA20MACRO

pushax

inal,92h

andal,11111101b

out92h,al

popax

ENDM

;----------------------------------------------------------------------------

;16位偏移的段间直接转移指令的宏定义(在16位代码段中使用)

;----------------------------------------------------------------------------

JUMP16MACROSelector,Offset

DB0eah;操作码

DWOffset;16位偏移量

DWSelector;段值或段选择子

ENDM

;----------------------------------------------------------------------------

CSEGSEGMENTUSE16;16位代码段

ASSUMECS:

CSEG,DS:

DSEG

;----------------------------------------------------------------------------

StartPROC

movax,DSEG

movds,ax

mov_wSSValueInRealMode,ss;堆栈段

mov_wSPValueInRealMode,sp;堆栈指针

;准备要加载到GDTR的伪描述符

movbx,16

mulbx

addax,OFFSETGDT;计算并设置基地址

adcdx,0;界限已在定义时设置好

movWORDPTRVGDTR.Base,ax

movWORDPTRVGDTR.Base+2,dx

;准备要加载到IDTR的伪描述符

movax,SEGIDT

movbx,16

mulbx

addax,OFFSETIDT;计算并设置基地址

adcdx,0;界限已在定义时设置好

movWORDPTRVIDTR.Base,ax

movWORDPTRVIDTR.Base+2,dx

;设置代码段描述符

movax,cs

mulbx

movWORDPTRCode.BaseL,ax;代码段开始偏移为0

movBYTEPTRCode.BaseM,dl;代码段界限已在定义时设置好

movBYTEPTRCode.BaseH,dh

movax,segSpuriousHandler

mulbx

movWORDPTRCode32.BaseL,ax;代码段开始偏移为0

movBYTEPTRCode32.BaseM,dl;代码段界限已在定义时设置好

movBYTEPTRCode32.BaseH,dh

movax,8000h

movdx,000BH

movWORDPTRDataV.BaseL,ax

movBYTEPTRDataV.BaseM,dl

movBYTEPTRDataV.BaseH,dh

;设置目标数据段描述符

movax,ds

mulbx;计算并设置目标数据段基址

movWORDPTRDataP.BaseL,ax

movBYTEPTRDataP.BaseM,dl

movBYTEPTRDataP.BaseH,dh

;保存中断屏蔽寄存器(IMREG)值

inal,21h

mov_SavedIMREG_M,al;主片IMR=21h

inal,0A1h

mov_SavedIMREG_S,al;从片IMR=A1h

;保存IDTR

sidtQWORDPTR_SavedIDTR

;加载GDTR

lgdtQWORDPTRVGDTR

cli;关中断

EnableA20;打开地址线A20

lidtQWORDPTRVIDTR;加载IDT

;切换到保护方式

moveax,cr0

oreax,1

movcr0,eax

;清指令预取队列,并真正进入保护方式

JUMP16Code_Sel,

ALIGN32

Virtual:

;现在开始在保护方式下运行

movax,DataV_Sel

movgs,ax;加载源数据段描述符

movax,DataP_Sel

movds,ax;加载源数据段描述符

movss,ax;堆栈段选择子

movsp,offsetTopOfStack

callInit8259A

movah,0Ch;0000黑底1100红字

moval,'!

'

movgs:

[((80*0+72)*2)],ax;屏幕第0行,第72列。

;x:

jmpx

int080h

sti

movebx,0

xorecx,ecx

WaitLoop:

;cmpebx,100

;jbWaitLoop

cmpecx,1;等到Esc

jnzWaitLoop

cli

callSetRealmode8259A

;切换回实模式

moveax,cr0

andal,11111110b

movcr0,eax

;清指令预取队列,进入实方式

JUMP16,

;Init8259A---------------------------------------------------------------------------------------------

Init8259A:

moval,011h

out020h,al;主8259,ICW1.

callio_delay

out0A0h,al;从8259,ICW1.

callio_delay

moval,020h;IRQ0对应中断向量0x20

out021h,al;主8259,ICW2.

callio_delay

moval,028h;IRQ8对应中断向量0x28

out0A1h,al;从8259,ICW2.

callio_delay

moval,004h;IR2对应从8259

out021h,al;主8259,ICW3.

callio_delay

moval,002h;对应主8259的IR2

out0A1h,al;从8259,ICW3.

callio_delay

moval,001h

out021h,al;主8259,ICW4.

callio_delay

out0A1h,al;从8259,ICW4.

callio_delay

moval,11111100b;<同时开启定时器和键盘中断>

out021h,al;主8259,OCW1.

callio_delay

moval,11111111b;屏蔽从8259所有中断

out0A1h,al;从8259,OCW1.

callio_delay

ret

;Init8259A---------------------------------------------------------------------------------------------

 

;SetRealmode8259A---------------------------------------------------------------------------------------------

SetRealmode8259A:

moval,011h

out020h,al;主8259,ICW1.

callio_delay

out0A0h,al;从8259,ICW1.

callio_delay

moval,08h;IRQ0对应中断向量0x20

out021h,al;主8259,ICW2.

callio_delay

moval,70h;IRQ8对应中断向量0x28

out0A1h,al;从8259,ICW2.

callio_delay

moval,004h;IR2对应从8259

out021h,al;主8259,ICW3.

callio_delay

moval,002h;对应主8259的IR2

out0A1h,al;从8259,ICW3.

callio_delay

moval,001h

out021h,al;主8259,ICW4.

callio_delay

out0A1h,al;从8259,ICW4.

callio_delay

moval,11111111b;屏蔽从8259所有中断

out0A1h,al;从8259,OCW1.

callio_delay

moval,_SavedIMREG_M;恢复中断屏蔽寄存器(IMREG)的原值

out021h,al;

callio_delay

;moval,_SavedIMREG_S;恢复中断屏蔽寄存器(IMREG)的原值

;out0A1h,al;

;callio_delay

ret

;SetRealmode8259A---------------------------------------------------------------------------------------------

io_delay:

nop

nop

nop

nop

ret

Real:

;现在又回到实方式

DisableA20

lidtQWORDPTR_SavedIDTR

movax,DSEG

movds,ax

movss,_wSSValueInRealMode

movsp,_wSPValueInRealMode

sti

movax,4c00h

int21h

StartENDP

;----------------------------------------------------------------------------

CSEGENDS;代码段定义结束

;----------------------------------------------------------------------------

CSEG32SEGMENTUSE32

;interrupthandler---------------------------------------------------------------

ASSUMECS:

CSEG32,DS:

DSEG

ClockHandler:

incebx

incbyteptrgs:

[((80*0+70)*2)];屏幕第0行,第70列。

moval,20h

out20h,al;发送EOI

iretd

EscHandler:

;<键盘中断服务程序,用来在屏幕第1行,第70列显示响按键的不断跳动的字符>

inal,60h

cmpal,1

jnzNesc

movecx,1

Nesc:

incbyteptrgs:

[((80*1+70)*2)]

moval,20h

out20h,al

iretd

UserIntHandler:

movah,0Ch;0000黑底1100红字

moval,'I'

movgs:

[((80*0+71)*2)],ax;屏幕第0行,第71列。

iretd

 

SpuriousHandler:

movah,0Ch;0000黑底1100红字

moval,'!

'

movgs:

[((80*0+72)*2)],ax;屏幕第0行,第72列。

iretd

;---------------------------------------------------------------------------

CSEG32ENDS

ENDStart

 

此代码在原先老师所给的代码基础上做了如下的修改:

IDT_21Gate1dup();<键盘中断服务程序的中断门>

IDT_21_7FGate94dup(

加入esc的中断处理

EscHandler:

inal,60h

cmpal,1

jnzNesc

movecx,1

Nesc:

incbyteptrgs:

[((80*1+70)*2)]

moval,20h

out20h,al;发送EOI

iretd

如果键入非esc建则在第二行加一显示字符

五实验结果

刚开始运行时

在屏幕的第一行第70列字符ASCLL码加一并显示,实现字符的跳动.

当输入非esc键时

在屏幕的第二行第70列字符ASCLL码加一并显示

当输入esc键时

退出循环.

 

六心得体会

1、键入非ESC键时,运行时发现按下一次后ascll码却加了2,因为程序中设计成非esc键入就加一,因此是键盘按下时发出一个信号,键盘弹回时又发出一个信号,致使ASCLL码加了两次.

2、通过实验对8259的初始化有了新的认识,对两片8259A的级联有了具体的了解.

3、又重新翻了一遍接口的教材,对全局描述符表GDT,中断

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > PPT模板

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1