PIC极限应用

2020-02-09 09:30发布

在一个小项目里面,用PIC16F913来主控,用来记录N个脉冲的时间,时间精确到10us,看了下资料,晶振可以最高20M     20M/4分频可以到5M。但是看了下第定时器的中断,软件模拟了下,进中断和出中断就要3.XX个US,如果加上脉冲捕获进中断的时间,一起的误差会不会超出10US的范畴???(思路是:一边捕获脉冲。一边开个5US的定时器片,一直累加。当脉冲捕获到N值时,关定时器。看定时了多少个5US)  刚接错PIC,不知道这样可行不?高手路过,喵喵。。。
友情提示: 此问题已得到解决,问题已经关闭,关闭后问题禁止继续编辑,回答。
26条回答
adszmc
2020-02-12 15:40
谢谢各位的帮助   
现在根据上面思路设计了下程序:
装载 CCPR1L,CCPR1H
时钟为外部引脚时钟(实际用信号发生器输入100hz)当TMR1H,TMR1L和CCPR1L,CCPR1H匹配时,产生中断关闭定时器TMR0。获取TMR0的值
TMR0从00-FF,溢出中断加一。

定时器1程序:

/*********************************************************************************************************
** Function name:                Timer1_Init()
** Descriptions:                定时器1初始化
** input parameters:    无
** output parameters:   无
** Returned value:      无
*********************************************************************************************************/
void Timer1_Init() //定时器1初始化
{
   
   TMR1CS =1; //定时器1时钟来源选择,此处设置为1,选着T1CKL1引脚,作为计数器,上升沿促发
   T1SYNC =0 ; //定时器1外部时钟同部位,在计数定模式下,于系统时钟同步
   T1OSCEN=0; //定时器1震荡有效位此处为1,即此处设置为有效
   
   T1CKPS1=0; //T1CKPS0都是0,则分频比为0
   T1CKPS0=0;
   T1GE=0;   //不使用门控位
    LCDEN=0;
    SE10=0;

    TMR1H = 0x00;        
    TMR1L = 0x00;
    TMR1ON=0;//关闭定时器1

  //设置 比较 模块下
   CCP1M3=1;//设置在比较模式下 及00001010
   CCP1M2=0;
   CCP1M1=1;
   CCP1M0=0;
   CCP1IF=0;//中断源复位
}


中断处理程序
void interrupt ISR(void)                         //中断服务程序
{
        if ( T0IF )         //2.5us//判TMR0 中断 =2.5us
        {
                T0IF = 0;         //清除TMR0 中断标志
        TIME_CONT++;
        //在此加入TMR0 中断服务
        }
        else if ( CCP1IF ) //=1us //判CCPX 中断
        {   
         TMR1ON=0;//0.5us //关闭
                 CCP1IF= 0; //0.5us //清除TMR1 中断标志
        if(START_FLAG==0xAA ) //2.5 //N个脉冲计算时间
          {   
             T0IE = 0;//0.5us //关闭定时器
             Copy_TMER0=TMR0;//备份TMR0值
             Copy_TIME_CONT=TIME_CONT;//备份
             TMR1ON=0;//关闭定时器1
             CCP1IE=0;//关闭
             nop();
          }
          else//开始计数器计数以及记录时间
           {
             TMR0 = 0x00;                // 256us
             T0IF = 0;         //清除TMR0 中断标志
             T0IE = 1;//打开定时器0
             TIME_CONT=0;
             START_FLAG=0xAA;//标志位置位
            
             CCPR1L=0xFF;//装载脉冲个数 <65536
             CCPR1H=0x00;//
             TMR1L = 0x00;
             TMR1H = 0x00;   //计数器复位
             TMR1ON=1;//开启计数器
            }
          //在此加入TMR1 中断服务
           }


}        



主函数:
/*********************************************************************************************************
** Function name:                mainS
** Descriptions:                系统主函数
** input parameters:   
** output parameters:   
** Returned value:      无
*********************************************************************************************************/
void main()               
{
    uchar i,j;
    Sys_initial();    //MCU参数初始化
    TMR1ON=0;//关闭定时器1
    TMR1H = 0x00;   //计数器复位
    TMR1L = 0x00;
    TMR0=0;
    T0IE = 0;//关闭定时器
        T0IF = 0; //清除TMR0 中断标志
    CCP1IF= 0;             //清除TMR1 中断标志
    TIME_CONT=0; //复位记录器
    START_FLAG=0;//复位转换开始标志位
    Copy_TMER0=0;
    Timer0_Init(); //定时器0初始化
        Timer1_Init();
    CCPR1L=0x1E;//装载脉冲个数 30
    CCPR1H=0x00;//
    TMR1H = 0x00;         //0。25S
    TMR1L = 0x00;
    TMR1ON=1;//开启定时器1
    CCP1IE=1;//开启比较

   while(1)
    {
      delay10ms(100);
    }   
}                //end main



说明下  
主函数中第一次装载  
     CCPR1L=0x1E;//装载脉冲个数 <65536
    CCPR1H=0x00;//
是为了脉冲和定时器0开始同步,同步处理程序在中断的

else//开始计数器计数以及记录时间
           {
             TMR0 = 0x00;                // 256us
             T0IF = 0;         //清除TMR0 中断标志
             T0IE = 1;//打开定时器0
             TIME_CONT=0;
             START_FLAG=0xAA;//标志位置位
            
             CCPR1L=0xFF;//装载脉冲个数 需要计数的真实脉冲个数
             CCPR1H=0x00;//
             TMR1L = 0x00;
             TMR1H = 0x00;   //计数器复位
             TMR1ON=1;//开启计数器
         }





出现问题:   发现随着 CCPR1L CCPR1H装载的值不同,测出时间会不稳定,测定方法为((256*N+ TTimer0模块寄存器值)*FOSC/4)N为定时器溢出次数) 随着CCPR1L CCPR1H装载值的增大,计算出来的时间也随着增大,如装载的值为10个脉冲,有可能误差为+12us,但装载的值为1000个脉冲,有可能误差为+60us   误差都是超一个方向递增。 调了一个早上,理了理思路,就是找不出来误差产生的原因?PIC用的不多,DX路过看下,我是用ICD2+MPLAB-IDE+HI-TECH PICC .

一周热门 更多>