按下‘A’键后,除非不在松开,如果松开,就显示满屏幕的‘A’

来源:互联网 发布:php集成化安装包 编辑:程序博客网 时间:2024/04/30 16:05
 

;安装一个新的int9中断例程,功能:在dos下,按下‘A’键后,除非不在松开,
;如果松开,就显示满屏幕的‘A’,其他键照常处理(松开一个键的扫描码称为断码)
assume cs:code
stack segment
 db 128 dup (0)
stack ends

code segment
start:mov ax,stack
      mov ss,ax
      mov sp,128

      push cs
      pop ds

      mov ax,0
      mov es,ax
     
      mov si,offset int9
      mov di,204h
      mov cx,offset int9end-offset int9   ;将新的int9中断例程安装在0:204处
      cld
      rep movsb

      push es:[9*4]
      pop es:[200h]
      push es:[9*4+2]
      pop es:[202h]   ;将原来的int9中断在中断向量表中的地址保存到es:[200],es:[202]

      cli    ;置IF=0,不响应可屏蔽中断
      mov word ptr es:[9*4],204h
      mov word ptr es:[9*4+2],0 ;将新的int9的程序首地址0:204放到中断向量表中
      sti    ;置IF=1,CPU在执行完当前指令后响应中断
     
      mov ax,4c00h
      int 21h
 
 int9:push ax
      push bx
      push cx
      push es
      
      in al,60h

      pushf
      call dword ptr cs:[200h]  ;当此中断执行时(cs)=0

     cmp ax,9eh  ;'A'键的扫描码
     jne int9ret

     
      mov ax,0b800h
      mov es,ax
      mov bx,0
      mov cx,2000
   s: mov byte ptr es:[bx],'A'
      mov byte ptr es:[bx+1],02h
      add bx,2
      loop s

int9ret:pop es
        pop cx
 pop bx
 pop ax
 iret
int9end:nop
;名称:延时程序
delay:push cx
      mov cx,10ffh
   s1:push cx
      mov cx,10ffh
   s2:nop
      loop s2
      pop cx
      loop s1
      pop cx
      ret    
code ends
end start

上述程序结束后,没有恢复系统int9在中断向量表中的地址,用以下程序来恢复其值:

;1 编写一个程序实现如下功能
;  将从物理地址200h开始处的4个字节复制到9*4物理地址处。
;注:此程序是9号中断处理程序入口地址修正程序。
;若新的9号中断处理程序不在200h处,则该程序要做相应更改。(原来的int9中断向量地址保存在200h处)
assume cs:code
code segment
start:mov ax,0
      mov es,ax
     
      mov ax,es:[200h]             
      mov es:[9*4],ax

      mov ax,es:[202h]
      mov es:[9*4+2],ax
     
      mov ah,4ch
      int 21h
code ends
end start