主题:8255 PPI 延迟有问题
下面是一个驱动扬声器发声的程序,感觉延迟的时间不对,
有三个循环层
BX是入口参数,最外层
CX是让WAIT_10MS 产生10MS时间延迟的倍数
wait_10ms子程序是产生15.08毫秒的过程
假如:BX=25
一个音符的延迟时间=25*663*15.08=0.25S
这里我试过几次,BX,CX参数放大后都能增加延迟时间,
问题应该在WAIT_10MS的子程序里
我也不知道是什么原因,还有我的MASM5.0编译出来的代码
在DEBUG里调试,IN和OUT指令老是抹去他本身指令的下一条指令的显示
但程序应该正常,还有有时候查看修改的I/O端口数据也不对
往高手指点:代码如下
DATA SEGMENT ; ;定义声音频率数据块
MUS_FREQ DW 330,294,262,294,3 DUP(330)
DW 294,294,294,330,392,392
DW 330,294,262,294,4 DUP(330)
DW 294,294,330,294,262,0FFFFH
MUS_TIME DW 6 DUP(25),50 ; ;定义对应声音延迟数据块
DW 2 DUP(25,25,50)
DW 12 DUP(25),100
DATA ENDS
CODE SEGMENT
MAIN PROC FAR
ASSUME CS:CODE,DS:DATA
START:
MOV AX,DATA
MOV DS,AX
LEA SI,MUS_FREQ
LEA BP,DS:MUS_TIME
BEGIN1:
MOV DI,[SI] ; ;DI为频率
MOV BX,DS:[BP] ; ;BX为延迟,BX中的每一次调用延迟10MS的子程序
CALL SOUNDF
INC SI
INC SI
INC BP
INC BP
CMP [SI],0FFFFH
JZ OVER
JMP BEGIN1
OVER: MOV AH,4CH
INT 21H
MAIN ENDP
;______________________________
;DI = sound frequency
;BX = delay time
SOUNDF PROC NEAR
PUSH DI
PUSH BX
PUSH AX
;initializing the counter2
MOV DX,12H
MOV AX,348CH ;12348CH=1.1931817MHz
DIV DI ;the result in AX is outer frequency
PUSH AX ;save it
MOV AL,10110110B ;set controll word
OUT 43H,AL
POP AX ;restore outer frequency
OUT 42H,AL ;send it to PORT 42H
MOV AL,AH
OUT 42H,AL ;first write LSB, write MSB next
;turn the speaker on
IN AL,61H ;get the setting of PROT B
MOV AH,AL ;save it
OR AL,00000011B ;set PB0 and PB1 to bit 1
OUT 61H,AL ;out it to PROT 61H
;WAIT 时间延迟代码段********************************
WAIT1: MOV CX,663 ;633*15US=10MS CX为663倍15.08us = 10ms(此处如果放大,延迟有效果)
CALL WAIT_10MS
DEC BX ;BX为延迟时间的入口参数(此处放大,延迟也有效果)
JZ EXIT
JMP WAIT1
EXIT:
MOV AL,AH ;restore out PORT of PPI
OUT 61H,AL
POP AX
POP BX
POP DI
RET
SOUNDF ENDP
;____________________________
WAIT_10MS PROC NEAR
PUSH AX
WAIT3:
IN AL,61H ; ;获取61H端口数据
AND AL,10H ; ;测试61H端口的BP4
CMP AL,AH ; ;与以前的比较,看是否改变(此位每15.08US刷新一次)
JE WAIT3
MOV AH,AL
LOOP WAIT3
POP AX
RET
WAIT_10MS ENDP
;**********
CODE ENDS
END START
有三个循环层
BX是入口参数,最外层
CX是让WAIT_10MS 产生10MS时间延迟的倍数
wait_10ms子程序是产生15.08毫秒的过程
假如:BX=25
一个音符的延迟时间=25*663*15.08=0.25S
这里我试过几次,BX,CX参数放大后都能增加延迟时间,
问题应该在WAIT_10MS的子程序里
我也不知道是什么原因,还有我的MASM5.0编译出来的代码
在DEBUG里调试,IN和OUT指令老是抹去他本身指令的下一条指令的显示
但程序应该正常,还有有时候查看修改的I/O端口数据也不对
往高手指点:代码如下
DATA SEGMENT ; ;定义声音频率数据块
MUS_FREQ DW 330,294,262,294,3 DUP(330)
DW 294,294,294,330,392,392
DW 330,294,262,294,4 DUP(330)
DW 294,294,330,294,262,0FFFFH
MUS_TIME DW 6 DUP(25),50 ; ;定义对应声音延迟数据块
DW 2 DUP(25,25,50)
DW 12 DUP(25),100
DATA ENDS
CODE SEGMENT
MAIN PROC FAR
ASSUME CS:CODE,DS:DATA
START:
MOV AX,DATA
MOV DS,AX
LEA SI,MUS_FREQ
LEA BP,DS:MUS_TIME
BEGIN1:
MOV DI,[SI] ; ;DI为频率
MOV BX,DS:[BP] ; ;BX为延迟,BX中的每一次调用延迟10MS的子程序
CALL SOUNDF
INC SI
INC SI
INC BP
INC BP
CMP [SI],0FFFFH
JZ OVER
JMP BEGIN1
OVER: MOV AH,4CH
INT 21H
MAIN ENDP
;______________________________
;DI = sound frequency
;BX = delay time
SOUNDF PROC NEAR
PUSH DI
PUSH BX
PUSH AX
;initializing the counter2
MOV DX,12H
MOV AX,348CH ;12348CH=1.1931817MHz
DIV DI ;the result in AX is outer frequency
PUSH AX ;save it
MOV AL,10110110B ;set controll word
OUT 43H,AL
POP AX ;restore outer frequency
OUT 42H,AL ;send it to PORT 42H
MOV AL,AH
OUT 42H,AL ;first write LSB, write MSB next
;turn the speaker on
IN AL,61H ;get the setting of PROT B
MOV AH,AL ;save it
OR AL,00000011B ;set PB0 and PB1 to bit 1
OUT 61H,AL ;out it to PROT 61H
;WAIT 时间延迟代码段********************************
WAIT1: MOV CX,663 ;633*15US=10MS CX为663倍15.08us = 10ms(此处如果放大,延迟有效果)
CALL WAIT_10MS
DEC BX ;BX为延迟时间的入口参数(此处放大,延迟也有效果)
JZ EXIT
JMP WAIT1
EXIT:
MOV AL,AH ;restore out PORT of PPI
OUT 61H,AL
POP AX
POP BX
POP DI
RET
SOUNDF ENDP
;____________________________
WAIT_10MS PROC NEAR
PUSH AX
WAIT3:
IN AL,61H ; ;获取61H端口数据
AND AL,10H ; ;测试61H端口的BP4
CMP AL,AH ; ;与以前的比较,看是否改变(此位每15.08US刷新一次)
JE WAIT3
MOV AH,AL
LOOP WAIT3
POP AX
RET
WAIT_10MS ENDP
;**********
CODE ENDS
END START