告别EVT依赖!手把手教你为沁恒CH573创建专属MounRiver工程(保姆级配置流程)
2026/6/8 6:20:17
assume cs:code stack segment db 128 dup(0) ; 定义栈段,大小128字节 stack ends code segment start: ;设置各段地址 mov ax,stack mov ss,ax mov sp,128 ; 栈顶指向栈段末尾(128字节栈,sp初始为128) push cs pop ds ; 让ds = cs(代码段和数据段同段,方便访问自定义中断例程 mov ax,0 mov es,ax ; es指向0段(中断向量表所在的段) ;安装新程序(自定义int9程序安装在0:204位置处) mov si,offset int9 ; si = 自定义int9例程的偏移地址 mov di,204h ; di = 0段204H(新例程的存放地址) mov cx,offset int9end - offset int9 ;cx = 新例程的字节长度 cld ; 方向标志DF=0(串操作时si/di递增) rep movsb ; 循环复制:将cs:[si]的内容复制到es:[di],共cx字节 ;将原中断地址保存在0:200单元处 push es:[9*4] pop es:[200H] push es:[9*4+2] pop es:[202H] ;将自定义的int9程序所在地址CS:IP写入---向量表中,向量表触发时就转到0:204处的自定义int9处 cli ; 关中断(禁止CPU响应外部中断,防止修改向量时被打断) mov word ptr es:[9*4],204H ; int9偏移地址 = 204H(新例程偏移) mov word ptr es:[9*4+2],0 ; int9段地址 = 0(新例程段地址) sti ; 开中断(恢复中断响应) mov ax,4c00h int 21h ;定义新中断例程 int9: push ax push bx push cx push es in al,60H pushf ;仅将标志位寄存器压入栈中 ;调用旧中断例程 call dword ptr cs:[200h] ;调用原系统向量表保存的CS:IP地址,并执行; ;处理F1键 cmp al,3BH jne int9ret mov ax,0B800H mov es,ax mov bx,1 mov cx,2000 s: inc byte ptr es:[bx] add bx,2 loop s int9ret: pop es pop cx pop bx pop ax iret int9end:nop code ends end start在 Intel 8086 CPU 中,IRET(Interrupt Return,中断返回)是一条用于从中断服务程序(ISR, Interrupt Service Routine)返回到被中断程序的指令。
IRET指令的主要作用是恢复被中断时的程序执行上下文。它会从堆栈中弹出以下内容(按顺序):
注意:8086 是实模式处理器,不支持保护模式下的特权级切换,因此
IRET在 8086 中只处理上述三个寄存器。
假设堆栈指针为 SP,堆栈向下增长(向低地址方向),执行IRET相当于以下操作:
POP IP POP CS POP FLAGS即:
IRET必须用在中断服务例程的末尾,用于:
例如:
; 中断服务程序示例 my_isr: push ax push dx ; ... 中断处理代码 ... pop dx pop ax iret ; 返回到被中断的程序注意:在进入 ISR 时,CPU 自动将 FLAGS、CS、IP 压入堆栈;因此必须用
IRET返回,不能用RET,否则无法恢复 FLAGS,可能导致中断系统异常(如 IF 标志未恢复,导致后续中断被屏蔽)。