| 网站首页 | 业界新闻 | 小组 | 威客 | 人才 | 下载频道 | 博客 | 代码贴 | 在线编程 | 编程论坛
欢迎加入我们,一同切磋技术
用户名:   
 
密 码:  
共有 669 人关注过本帖
标题:3楼的错误改了,程序还是有其他问题。求帮助,现在1CH中断的时候同时获取键 ...
只看楼主 加入收藏
cdangjia
Rank: 1
等 级:新手上路
帖 子:7
专家分:0
注 册:2012-2-13
结帖率:50%
收藏
已结贴  问题点数:20 回复次数:5 
3楼的错误改了,程序还是有其他问题。求帮助,现在1CH中断的时候同时获取键盘输入,程序不能返回。
现在是新写了一个1CH时钟中断,用来刷新1行屏幕。
然后住程序里面获取键盘的输入控制。

坏境是在虚拟机dos 6.22下
masm 5.0编译

如果在1CH里面只有一句iret,程序就没事。运行程序直接按q可以返回。
但是按了其他键之后 再按Q就程序返回不了,好像是卡主了   死机的样子

程序代码:
assume cs:code,ds:data,ss:stack

stack segment stack
db 128 dup(0)
stack ends

data segment
ww db 160 dup('W')
aa db 39 dup(' '),'A',40 dup(' ')
data ends

code segment
start:
        call setbullet
        call install
        call getkey
        
        mov ax,0
        mov es,ax
        push es:[200h]
        pop es:[1ch*4]
        push es:[202h]
        pop es:[1ch*4+2]
        
        mov ax,4c00h
        int 21h

install:    ;install 1ch to refresh screen
        push ax
        push es
        push di
        push ds
        push si
        push cx
        
        mov ax,0
        mov es,ax
        mov di,210h
        mov ax,cs
        mov ds,ax
        mov si,offset refresh
        mov cx,offset refreshend-offset refresh
        cld 
        rep movsb
        
        mov ax,0
        mov es,ax
        push es:[1ch*4]
        pop es:[200h]
        push es:[1ch*4+2]
        pop es:[202h]
        
        cli
        mov word ptr es:[1ch*4],210h
        mov word ptr es:[1ch*4+2],0
        sti
        
        pop cx
        pop si
        pop ds
        pop di
        pop es
        pop ax
        ret
        
        
getkey:        ;get a key
        push ax
        
        mov ah,0
        int 16h
        
        cmp ah,4bh
        je leftkey
        cmp ah,4dh
        je rightkey
        cmp ah,39h
        je spacekey
        cmp ah,10h
        je quit
        jmp getkey
        
leftkey:
        jmp getkey
rightkey:
        jmp getkey
spacekey:
        jmp getkey
quit:
        pop ax
        ret
        
setbullet:    ;set bullets
        push ax
        push es
        push si
        push cx
        
        mov ax,0
        mov es,ax
        mov si,2a0h
        mov cx,80
        
ssetbul:    
        mov al,'.'
        mov es:[si],al
        inc si
        loop ssetbul
        
        pop cx
        pop si
        pop es
        pop ax
        ret
        
refresh:    ;sub refresh screen, new 1ch int
        push ax
        push es
        push si
        push bx
        push cx
        push ds
        
        mov ax,0b800h
        mov es,ax
        mov ax,0
        mov ds,ax
        mov si,2a0h
        mov bx,160*2
        mov cx,80
        
sref:
        mov al,ds:[si]
        mov es:[bx],al
        inc si
        add bx,2
        loop sref
        
        pop ds
        pop cx
        pop bx
        pop si
        pop es
        pop ax
        iret
refreshend:
        nop
        
code ends
end start




[ 本帖最后由 cdangjia 于 2012-7-6 23:38 编辑 ]
搜索更多相关主题的帖子: 运行程序 虚拟机 color 
2012-07-06 00:29
zklhp
Rank: 20Rank: 20Rank: 20Rank: 20Rank: 20
来 自:china
等 级:贵宾
威 望:254
帖 子:11485
专家分:33241
注 册:2007-7-10
收藏
得分:10 
帮顶
2012-07-06 09:17
heliang6291
Rank: 2
等 级:论坛游民
威 望:3
帖 子:27
专家分:45
注 册:2012-6-28
收藏
得分:0 
我来指出你的错误:
第一:你的新1CH中断也错了,在保护现场与恢复现场中,PUSH 和 POP的顺序反了,压栈出栈应当是先进后出。你的为
refresh:    ;新的1CH中断程序,功能将内存0:2a0h处的内容输出到屏幕,如果直接调用这段子程序能够输出
        ;如果中断程序只有iret 按Q后也能返回,
        ;做子程序调用没问题
        push ax
        push es
        push si
        push bx
        push cx
        push ds
        
        mov ax,0b800h
        mov es,ax
        mov ax,0
        mov ds,ax
        mov si,2a0h
        mov bx,160*2
        mov cx,80*2
        
sref:
        mov al,ds:[si]
        mov es:[bx],al
        inc si
        add bx,2
        loop sref
        
        pop ax
        pop es
        pop si
        pop bx
        pop cx
        pop ds
        iret
应该为:
refresh:    ;新的1CH中断程序,功能将内存0:2a0h处的内容输出到屏幕,如果直接调用这段子程序能够输出
        ;如果中断程序只有iret 按Q后也能返回,
        ;做子程序调用没问题
        push ax
        push es
        push si
        push bx
        push cx
        push ds
        
        mov ax,0b800h
        mov es,ax
        mov ax,0
        mov ds,ax
        mov si,2a0h
        mov bx,160*2
        mov cx,80*2
        
sref:
        mov al,ds:[si]
        mov es:[bx],al
        inc si
        add bx,2
        loop sref
        
        pop ds
        pop cx
        pop bx
        pop si
        pop es
        pop ax
        iret
另外,我想问问你,你的2a0h这样的地址是怎么知道的?如何获得的?另外你的setbullet:    ;设置要输出的内容,把输出的内容放在内存0:2a0h处.新的1CH中断就可以把0:2A0H的输出到屏幕.
        push ax
        push es
        push si
        push cx
        
        mov ax,0
        mov es,ax
        mov si,2a0h
        mov cx,80*2
        
ssetbul:   
        mov al,'.'
        mov es:[si],al
        inc si
        loop ssetbul
        
        pop ax
        pop es
        pop si
        pop cx
        ret
这段子程序根本没用到,那你的新1ch中断还能显示那样的信息?

另外,记得开中断sti

记得给分。结题散分啊
2012-07-06 12:56
cdangjia
Rank: 1
等 级:新手上路
帖 子:7
专家分:0
注 册:2012-2-13
收藏
得分:0 
晚上回去试试,这个问题卡了一周了,一直没注意到恢复现场的时候出栈要反序。
setbullet这个子程序是在内存0:2a0h处设置1CH中断输出的内容。
我是用0:2a0h这段内存做为共享内存。
这里为了测试1CH所以只要了主要的部分,其他代码删除了。
谢谢。
2012-07-06 14:51
heliang6291
Rank: 2
等 级:论坛游民
威 望:3
帖 子:27
专家分:45
注 册:2012-6-28
收藏
得分:10 
记得给我分数啊!!!!
别吝啬哦
2012-07-07 13:39
cdangjia
Rank: 1
等 级:新手上路
帖 子:7
专家分:0
注 册:2012-2-13
收藏
得分:0 
以下是引用heliang6291在2012-7-7 13:39:59的发言:

记得给我分数啊!!!!
别吝啬哦



出栈顺序那个改了,但是程序还是有问题,直接按Q可以退出,按了其他键后再按Q不能退出,机子死机卡主,只能重启。帮忙再看看吧。分肯定是会给的。
2012-07-07 18:33
快速回复:3楼的错误改了,程序还是有其他问题。求帮助,现在1CH中断的时候同时获 ...
数据加载中...
 
   



关于我们 | 广告合作 | 编程中国 | 清除Cookies | TOP | 手机版

编程中国 版权所有,并保留所有权利。
Powered by Discuz, Processed in 0.140238 second(s), 8 queries.
Copyright©2004-2024, BCCN.NET, All Rights Reserved