实验题目

  • 单中断请求实验:利用系统总线上中断请求信号MIR7,设计一个单一中断请求实验
  • 双中断优先级实验:利用系统总线上中断请求信号MIR6和MIR7,设计一个双中断优先级应用实验,观察8253对中断优先级的控制

实验要求

  • (1)单中断请求实验:单脉冲KK1+与主片8259的IR7相连。每按KK1+,进入一次中断,输出7;
    (2)双中断优先级实验:单脉冲KK1+连主片8259的IR7,KK2+连其IR6。每当KK1+按下时显示“7”,每当KK2+按下显示“6”;

了解8259

中断控制器8259简介

在Intel 386EX芯片中集成有中断控制单元(ICU),该单元包含有两个级联中断控制器,一个为主控制器,一个为从控制器。该中断控制单元就功能而言与工业上标准的82C59A是一致的,操作方法也相同。从片的INT连接到主片的IR2信号上构成两片8259的级联。

在TD-PITE实验系统中,将主控制器的IR6、IR7以及从控制器的IR1开放出来供实验使用,主片8259的IR4供系统串口使用。8259的内部连接及外部管脚引出如图:

汇编语言--8259中断_中断请求


操作命令字1寄存器(OCW1)说明:

注:这里就简单的提下OCW1控制命令字的格式,ICW1–ICW4一般电脑都默认初始化了的,只不过我们自己在实验过程中需要自己编写代码初始化的,但是格式是一样的,记住模板就行了,OCW1却是会变换的,所以学习下OCW1的写法

  1. OCW1简单说来就是,需要哪个中断(8259有7个,IR0-IR7),我们就把哪个中断置0,这是提醒一下,IR4都是会使用的,供系统串口使用,所以IR4那位一直是0,比如这里我们需要7号中断(IR7),那么格式就是01101111,也就是6F。
  2. 在这里,海轰其实一直有个疑问?为什么要设置操作命令字?操作命令字是干什么的? emmmm,说说海轰的理解:8259作为一款芯片,可以做的事情很多,但是一般来说,我们产品只需要一个功能,比如在这里就是需要7号中断。那么事先我们就需要通过程序来使得该芯片的功能确定下来。简单说来就是:确定芯片的工作方式(它要工作,首先它得知道需要干什么吧)

汇编语言--8259中断_中断请求_02

单中断请求流程

这个理解记住,代码就会写了!

汇编语言--8259中断_初始化_03

单中断请求实验代码

CODE SEGMENT
ASSUME CS:CODE
START: ;DOS调用写入法
CLI ;关中断,防止硬件中断对程序的干扰
PUSH DS ;设置中断向量
MOV AX,8
MOV DX,AX

;下面几句就是CPU收到中断请求时,把需要执行的子程序的段地址、偏移地址放到中断向量中
;为什么要这样做?
;计算机中有个规则,CPU只会得到中断类型号,然后乘4,得到其子程序入口地址,开始子程序
;但是自定义中断,子程序是千变万化的,为了让计算机执行我们自己编写的程序,所以我们自己就需要
;把子程序入口地址放到类型号*4的地址那去
MOV AX,OFFSET MIR7 ;取MIR7的偏移地址
MOV BX,003CH ;中断类型号为n,BX设置为4*n
MOV [BX],AX ;偏移地址放入4n,4n+1单元
MOV AX,SEG MIR7 ;取MIR7的段地址
MOV [BX+2],AX ;偏移地址放入4n+2,4n+3单元

POP DS

;初始或ICW 固定模式
MOV AL,11H ;初始化ICM1
OUT 20H,AL
MOV AL,08H ;初始化ICM2
OUT 21H,AL
MOV AL,04H ;初始化ICM3
OUT 21H,AL
MOV AL,01H ;初始化ICM4
OUT 21H,AL

;初始化OCW1 01101111,开放IR7和IR4(4是作为系统串口使用,必须接入),
MOV AL,6FH ;设置OCW1,开放MIR7和IR4

OUT 21H,AL
STI ;开中断

WIN:JMP WIN ;等待中断

;子程序
MIR7:
STI
MOV AX,0137H ;显示字符7
INT 10H
MOV AX,0120H ;显示空格
INT 10H
MOV AL,20H ;中断结束命令
OUT 20H,AL
IRET ;中断返回
CODE ENDS
END START

解释

MOV AX,OFFSET MIR7    ;取MIR7的偏移地址 
MOV BX,003CH ;中断类型号为n,BX设置为4*n
MOV [BX],AX ;偏移地址放入4n,4n+1单元
MOV AX,SEG MIR7 ;取MIR7的段地址
MOV [BX+2],AX ;偏移地址放入4n+2,4n+3单元

为什么上面几行代码中地址是003C和003E?

首先我们知道子程序入口是中断类型号*4,那么IR7的中断类型号是多少呢?

从下图可以看出,IR7的中断类型号是F(0F),0F×4=003C

003E=0F×4+2

现在知道入口地址怎么来了吧 O(∩_∩)O哈哈~

汇编语言--8259中断_子程序_04


为什么ICW1送入20H,而ICW2-ICW3,OCW1都送入21H呢?

MOV AL,11H        ;初始化ICM1
OUT 20H,AL
MOV AL,08H ;初始化ICM2
OUT 21H,AL

这也比较好理解:首先我们需要初始化ICW、OCW,就是给他们赋初值。那么第一步肯定得知道他们在哪吧,然后再赋值。8088规定的是ICW1送入地址在20H,其他在21H(别问为什么,我也不知道,按照规则办事就行)。

双中断优先级实验代码(前一个代码懂了,这一个就简单了 )

CODE SEGMENT
ASSUME CS:CODE
START:
CLI
PUSH DS ;设置中断向量
MOV AX,8
MOV DX,AX
MOV AX,OFFSET MIR7
MOV BX,003CH
MOV [BX],AX
MOV AX,SEG MIR7
MOV [BX+2],AX

MOV AX,8 ;设置中断向量
MOV DX,AX
MOV AX,OFFSET SIR1
MOV BX,00C4H
MOV [BX],AX
MOV AX,SEG SIR1
MOV [BX+2],AX
POP DS

MOV AL,11H ;初始化ICW1-ICW4
OUT 20H,AL
MOV AL,08H
OUT 21H,AL
MOV AL,04H
OUT 21H,AL
MOV AL,01H
OUT 21H,AL

MOV AL,11H ;初始化ICW1-ICW4
OUT 0A0H,AL
MOV AL,30H
OUT 0A1H,AL
MOV AL,02H
OUT 0A1H,AL
MOV AL,01H
OUT 0A1H,AL

MOV AL,6BH ;01101011
OUT 21H,AL
MOV AL,0FDH ;设置OCM1,开放MIR7和SIR1
OUT 0A1H,AL
STI

WIN:JMP WIN ;主程序循环
MIR7:
STI
MOV AX,014DH ;显示M
INT 10H
MOV AX,0137H ;显示7
INT 10H
MOV AX,0120H ;显示空格
INT 10H
MOV AL,20H
OUT 20H,AL
IRET
SIR1:
STI
MOV AX,0153H ;显示S
INT 10H
MOV AX,0131H ;显示1
INT 10H
MOV AX,0120H
INT 10H ;显示空格
MOV AL,20H
OUT 0A0H,AL
OUT 20H,AL
IRET
CODE ENDS
END START