先放代码… sy16.asm
assume cs:code
code segment
start:
mov ax,cs
mov ds,ax ;设置ds
mov si,offset int7c ;ds:si源地址
mov ax,0
mov es,ax
mov di,200h ;es:di目的地址
mov cx,offset int7cend-offset int7c ;cx为传输长度
cld ;传输方向为正
rep movsb ;开始传输
cli
mov ax,0
mov es,ax
mov word ptr es:[7ch*4],200h
mov word ptr es:[7ch*4+2],0 ;设置新的int7c中断例程地址
sti
mov ax,4c00h
int 21h
org 200h ; ←←←←←←←←←重点
int7c:
jmp short set
table dw sub1,sub2,sub3,sub4
set:
push bx
cmp ah,3
ja sret
mov bl,ah
mov bh,0
add bx,bx
call word ptr table[bx]
sret:
pop bx
iret
sub1:
push bx
push cx
push es
mov bx,0b800h
mov es,bx
mov bx,0
mov cx,2000
sub1s:
mov byte ptr es:[bx],' '
add bx,2
loop sub1s
pop es
pop cx
pop bx
ret
sub2:
push bx
push cx
push es
mov bx,0b800h
mov es,bx
mov bx,1
mov cx,2000
sub2s:
and byte ptr es:[bx],11111000b
or es:[bx],al
add bx,2
loop sub2s
pop es
pop cx
pop bx
ret
sub3:
push bx
push cx
push es
mov cl,4
shl al,cl
mov bx,0b800h
mov es,bx
mov bx,1
mov cx,2000
sub3s:
and byte ptr es:[bx],10001111b
or es:[bx],al
add bx,2
loop sub3s
pop es
pop cx
pop bx
ret
sub4:
push cx
push si
push di
push es
push ds
mov si,0b800h
mov es,si
mov ds,si
mov si,160
mov di,0
cld
mov cx,24
sub4s:
push cx
mov cx,160
rep movsb
pop cx
loop sub4s
mov cx,80
mov si,0
sub4s1:
mov byte ptr [160*24+si],' '
add si,2
loop sub4s1
pop ds
pop es
pop di
pop si
pop cx
ret
int7cend:nop
code ends
end start
tstsy16.asm
assume cs:code
code segment
start:
;set front color
mov ah,1
mov al,3
int 7ch
call delay
;set background color
mov ah,2
mov al,7
int 7ch
call delay
mov ah,3
int 7ch
call delay
;clean screen
mov ah,0
int 7ch
mov ax,4c00h
int 21h
delay:
push ax
push dx
mov dx,0h
mov ax,0ffffh
s1: sub ax,1
sbb,dx,0
cmp ax,0
jne s1
cmp dx,0
jne s1
pop dx
pop ax
ret
code ends
end start
代码写完之后发现结果不对,调试一下发现问题出在int7c的中断例程中 call word ptr table[bx] 这一句。 程序首先进行编译,这时候table实际上就被替换为了一个地址,然后再执行程序的时候,这个错误的地址和程序一块被拷贝到了0:200开始的内存中,所以执行程序的时候会出问题。 要解决这个问题需要在要拷贝的程序前添加一句 org 200h,告诉编译器,在编译的时候就把后面这段程序当做存在0:200处,这样一些标号的地址就是我们想要的正确地址。
欢迎与我分享你的看法。 转载请注明出处:http://taowusheng.cn/