[PIC] Frequency meter using CCP capture module

Status
Not open for further replies.

mnyama

Newbie level 4
Joined
Feb 23, 2013
Messages
5
Helped
0
Reputation
0
Reaction score
0
Trophy points
1,281
Visit site
Activity points
1,333

Code:
 //lcd configuration
sbit LCD_RS at RD4_bit;
sbit LCD_EN at RD5_bit;
sbit LCD_D4 at RD0_bit;
sbit LCD_D5 at RD1_bit;
sbit LCD_D6 at RD2_bit;
sbit LCD_D7 at RD3_bit;
sbit LCD_RS_Direction at TRISD4_bit;
sbit LCD_EN_Direction at TRISD5_bit;
sbit LCD_D4_Direction at TRISD0_bit;
sbit LCD_D5_Direction at TRISD1_bit;
sbit LCD_D6_Direction at TRISD2_bit;
sbit LCD_D7_Direction at TRISD3_bit;
//end of lcd configuration

 unsigned int t1,t2,T=0;
 float t3,tp=0;
 unsigned char cpf,cnt=0; //variables as count
 char txt[15];

void system_init()
{
// Configure AN pins as digital I/O
ANSEL = 0x00;
ANSELH = 0x00;

// Disable comparators
 C1ON_bit = 0;
 C2ON_bit = 0;
  //configuring  PORTD is output
 TRISD = 0;
 PORTD =0;
  //setting the RC2/CCP1 pin as input
 PORTC.F2=1;  //set the RC2/CCP1 pin as input
 INTCON = 0b11000000;  // Enable interrupt (bits GIE+peripheral)
PIE1=0b00000101; //except for the TMR1IE&CCP1IE bits
T1CON = 0b00000001; /*T1 on,sychronised,prescaler value 1:1 */
CCP1CON=0b00000111; //capture every 16th rising edge
Lcd_Init();                 // Initialize LCD
Lcd_Cmd(_LCD_CLEAR);        // CLEAR display
Lcd_Cmd(_LCD_CURSOR_OFF);   // Cursor off
TMR1H=0; //initialize the TMR1H&TMR1L
TMR1L=0;

CCPR1H=0; //clear the ccp register
CCPR1L=0;
}
 void interrupt()
 {
  if(PIR1.F2==1)   //ccp capture flag bit
  {
  PIR1.F2=0; //clear flag bit
  cpf++; //record the ccp flag bit
  }
  if(PIR1.F0==1)    //timer1 overflow flag bit
  {
   PIR1.F0=0; //clear the flag bit
   cnt++; //record the t1 overflows
  }
}


void main() {
system_init();  //configurin the system
Lcd_Out(1,1,"Freq meter");


for(;;)
{
 if(cpf==1)  //wait here untill the first captured rising edge
 {
  t1=CCPR1H*256+CCPR1L;   //copy the content of the ccp--->t1 variable
 }
 
if(cpf==2)//wait here until the 2nd captured value
{
 T1CON.F0=0; //stop the timer1
 INTCON = 0b00000000;//clear all interrupt
 t2=CCPR1H*256+CCPR1L+cnt*65536;
 T=t2-t1;  //find the difference between 2nd capture - 1st captured  value
 t3=T/16; //divide the difference in time by 16 due to ccp prescalar value 1:16
 tp=(1/t3)*1000000;
FloatToStr(tp,txt);// convert the t3 into string txt
 Lcd_Out(2,1,txt);//send the results to lcd
 Lcd_Out_Cp("Hz"); //units in microsecond because of 4Mhz crsystal, 4Mhz/4=1Mhz
                   //this is equevalent to 1microsecond internal timer period
 TMR1H,TMR1L=0; //clear the timer to zero for next round trip
cpf,cnt=0;  //reset the counter variables
CCPR1H,CCPR1L=0; //reset the ccp variable
T1CON.F0=1; //switch on the timer again
INTCON = 0b11000000;//Re-enabling the interrupt again
}
}

}


 

Status
Not open for further replies.

Similar threads

Cookies are required to use this site. You must accept them to continue using the site. Learn more…