这是使用 pic16f676 中的 TIMER0 中断使 LED 闪烁的 MPASM 代码。端口 A 的引脚 0 (RA0) 未切换至关闭位置。请帮忙...
我是图片组装新手,我想掌握图片。有没有图片神童请帮我学习一下...
我需要以 1 秒的间隔眨眼。 代码是:
#include "p16F676.inc"
__CONFIG _FOSC_INTRCIO & _WDTE_OFF & _PWRTE_OFF & _MCLRE_OFF & _BOREN_OFF & _CP_OFF & _CPD_OFF
MyCount EQU 0x20
RES_VECT CODE 0x0000
GOTO CODE_INIT
ISR CODE 0x0004
GOTO ISR_HANDLER
;MAIN_PROG CODE
CODE_INIT:
CALL PORT_INIT
CALL TIMER_INIT
GOTO IDLE_LOOP
ISR_HANDLER:
DECFSZ MyCount, 1
RETFIE
movlw 0x01
xorwf PORTA, F
BCF INTCON, TMR0IF
MOVLW d'10'
MOVWF TMR0
RETFIE
IDLE_LOOP:
NOP
NOP
NOP
NOP
GOTO IDLE_LOOP
PORT_INIT:
BSF STATUS, RP0
MOVLW b'00000000'
MOVWF ADCON1
MOVWF ANSEL
MOVWF TRISA
RETURN
TIMER_INIT:
CLRWDT
MOVLW b'00000110'
MOVWF OPTION_REG
BSF INTCON, GIE
BSF INTCON, TMR0IE
BCF STATUS, RP0
MOVLW d'18'
MOVWF MyCount
BCF INTCON, TMR0IF
MOVLW d'10'
MOVWF TMR0
RETURN
END
看来是赌延迟问题。但对预标量和计数器进行改组可以保持引导位置不变。我需要打开和关闭 LED。
以下是我在您的代码中检测到的一些问题...
正如我在这个答案中提到的,您的初始化代码缺少
CMCON
的代码,即控制模拟比较器模块的寄存器。以下是正确设置的方法:
BCF STATUS,RP0 ;Bank 0
CLRF PORTA ;Init PORTA
MOVLW 05h ;Set RA<2:0> to
MOVWF CMCON ;digital I/O
BSF STATUS,RP0 ;Bank 1
CLRF ANSEL ;digital I/O
CLRF TRISA ;set all pins as outputs
BCF STATUS,RP0 ;Bank 0
将预分频器设置为 1:128,意味着定时器将每 128us 递增一次。
您的计时器重载值为 10,这意味着它将计数 245 直到溢出。那么你的溢出率就是
128us * 245 = 31360us
。1000000 / 31360 = 31.8877
让我们将其四舍五入为十进制的 32。因此,您应该将 MyCount
变量加载为 32,以便总共生成 1 秒的延迟。18 * 31360 = 564.480ms
。
让我们先看看你的timer0中断处理程序代码。
ISR_HANDLER:
DECFSZ MyCount, 1
RETFIE
movlw 0x01
xorwf PORTA, F
BCF INTCON, TMR0IF
MOVLW d'10'
MOVWF TMR0
RETFIE
每次timer0 遇到中断时,您都应该清除timer0 标志。但只有当计数器减至零时才将其清除。但问题是:程序将陷入定时器中断,直到其标志被清除。因此,由于连续调用定时器中断,
DECFSZ MyCount, 1
指令将非常快速地执行,导致输出引脚非常快速地闪烁。因此没有人的眼睛会发现它在闪烁。MyCount
的值达到零后,您不会重新加载它。这将导致变量下溢到 255,并且在第一次之后它总是会从 255 开始倒计时。
因此,无论计数器的值如何,您应该做的是每次中断发生时清除标志并重新加载timer0值。您还应该重新加载
MyCount
值,以便它不断从计算值开始倒计时。最后,定时器中断的正确流程如下:
ISR_HANDLER
bcf INTCON, TMR0IF
movlw d'10'
BANKSEL TMR0 ; Make sure you're in correct data bank
decfsz MyCount, 1
retfie
movlw d'32'
BANKSEL MyCount ; Again make sure you're in correct bank
movwf MyCount
; PORTA and MyCount are in the same bank since MyCount's address is 0x20
movlw 1
xorwf PORTA, F ; Toggle output due to 1 sec time out
retfie
将上述修复应用到您的代码中,然后重试。让我知道结果。