真心请教,我的PIC定时器中断为啥只能进去1次
小弟最近开始使用PIC单片机,使用的是PIC18F45K80,使用PICKIT3作为调试工具,遇到以下难题:系统时钟内部的16M,定时器前置4分频,也就是定时器时钟1M,定时10ms,现在调试发现定时器中断只能进去1次,到底是哪里出现了问题?恳请大家不吝赐教,谢谢!
我的程序如下:工程文件在附件中
/** C O N F I G U R A T I O N B I T S ******************************/
#pragma config XINST = OFF,SOSCSEL=DIG,INTOSCSEL=LOW,RETEN=ON //Config 1L
#pragma config IESO = OFF,FCMEN=OFF,PLLCFG=OFF,FOSC=INTIO2 //Config 1H
#pragma config BORPWR = LOW,BORV=3,BOREN=OFF,PWRTEN=OFF //Config 2L
#pragma config WDTPS = 1,WDTEN=OFF //Config 2H
#pragma config MCLRE = ON //Config 3H
/** I N C L U D E S **************************************************/
#include "p18f45k80.h"
/** D E C L A R A T I O N S ******************************************/
/* ***********************************************************************************
** 函 数 名: void main (void)
** 功能描述: 主函数
**
**************************************************************************************/
void main (void)
{
//OSCCON = 0x60; //选择8M内部时钟
OSCCON = 0x70; //选择16M内部时钟
OSCTUNEbits.PLLEN = 0; // *4 PLL 禁能
//OSCTUNEbits.PLLEN = 1; // *4 PLL 使能
T0CON=0b00000001;//前置4分频定时器1M的时钟
TMR0H=0xD8;
TMR0L=0xEF; //0xFFFF-0xD8EF= 10000定时10ms
T0CONbits.TMR0ON=1;
RCONbits.IPEN=1;
INTCONbits.TMR0IF=0; /* 清除TMR0的中断标志 */
INTCON2bits.TMR0IP=1; /* TMR0中断高优先级 */
INTCONbits.TMR0IE=1; /* TMR0中断允许 */
INTCONbits.PEIE_GIEL=1;
INTCONbits.GIE_GIEH=1;
while (1);
}
void InterruptServiceHigh ()
{
if(INTCONbits.TMR0IF==1)
{
TMR0H=0xD8;
TMR0L=0xEF; //0xFFFF-0xD8EF= 10000定时10ms
INTCONbits.TMR0IF=0;
INTCONbits.TMR0IE=1;
}
}
#pragma code InterruptVectorHigh = 0x08
void InterruptVectorHigh (void)
{
_asm
goto InterruptServiceHigh //jump to interrupt routine
_endasm
}
看看标志位是不是写1清零 楼主看资料不细致
void InterruptServiceHigh ()应该需要声明为中断函数,不然系统只当普通函数来处理对待;
解决办法如下所示:
1、方法1
#pragma code
#pragma interrupt InterruptServiceHigh
void InterruptServiceHigh(void)
{
if(INTCONbits.TMR0IF)
{
TMR0H = 0xD8;
TMR0L = 0xEF; //0xFFFF-0xD8EF= 10000 定时10ms
INTCONbits.TMR0IF = 0;
INTCONbits.TMR0IE = 1;
}
}
2、方法2
分析void InterruptServiceHigh(void)为普通函数时,系统进中断后,
最高级中断允许标志位清零;当中断处理完退出后,最高级中断允许标志位没有置1;
导致下次没法再进入高级中断。
个人感觉可以人为在函数最后加上如下一句:
void InterruptServiceHigh(void)
{
if(INTCONbits.TMR0IF)
{
TMR0H = 0xD8;
TMR0L = 0xEF; //0xFFFF-0xD8EF= 10000 定时10ms
INTCONbits.TMR0IF = 0;
INTCONbits.TMR0IE = 1;
}
INTCONbits.GIE_GIEH = 1;
}
初步测试可以再次进入中断,但没分析会不会有其它不良影响。 yklstudent 发表于 2014-9-10 10:45
楼主看资料不细致
void InterruptServiceHigh ()应该需要声明为中断函数,不然系统只当普通函数来处理对待 ...
首先非常感谢你专业的回答,问题就在“void InterruptServiceHigh ()应该需要声明为中断函数”,谢谢!
页:
[1]