Continue to Site

Welcome to our site!

Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

  • Welcome to our site! Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

Period calculation with PIC18 using C18

Status
Not open for further replies.

Anthony_87

New Member
Dear all,

I'm using a PICDEM USB mounted with PIC18F4550 and I'm using the C18 compiler. I
want to measure a certain period of time at one of the PIC's inputs, lets say between a falling edge and a rising edge. so what i need to do is to store the value of a "timer" at the falling edge moment and store it again at the rising edge moment and do the comparison, but how to write it in C18 with all timer configuration and stuff !??

Thanks in advance

Best Regards
 
The PIC 18F4550 has a CCP (capture/compare/pwm) module which could probably do this. It also has the enhanced CCP module. See sections 15 and 16 in the datasheet.

Alternatively try either of the following for less accuracy:

- put your input signal on an interrupt pin, start a counter when it changes and stop the counter when it changes again
- continuously poll the pin, counting between changes

All of the 18F series PICs have known execution times, so you can calculate by working out how many instruction cycles pass between pin changes. That piece would be better done in inline ASM, so that you have the knowledge of how many cycles it takes. However, a timer will make this easier and the CCP module probably even easier still.

Which bit of the code do you need help with?
 
Hello "edeca", thanks for your help.

my application consists of using a bidirectional pin with internal pull ups, so I'm not sure if using the CCP module will work!! what i need is, for example to measure the "logic low" period within a single bit and compare it to a certain value (using if/else statement), this duration is between a falling edge and a rising edge, it could be around 0.9ms so its a long duration.
so how can I use the "counter" method, after all its 16bit, so the total counting time is (65535 x 200ns = 0.013ms) (if working on 20MHz)

thanks again
 
Do not forget that the internal timers have pre-scalers, which allow them to be configured with different counting rates. For example a 1:2 pre-scale will mean that the counter only increments once every two instruction cycles (so you are right to divide by four). 1:256 would provide a much larger range.

Consider also that just because the counter overflows, doesn't mean you have to stop timing. It might be easier to make the counter overflow every 100ns/1ms/10ms (find a sensible value that gives you enough accuracy) and count the number of times it overflows with a local variable.

It all depends how accurate you need it to be. If you want super accuracy, really consider the CCP module. If not, play with the timers.
 
it could be around 0.9ms so its a long duration.
so how can I use the "counter" method, after all its 16bit, so the total counting time is (65535 x 200ns = 0.013ms) (if working on 20MHz)

You goofed a little in your math. 65535 x 200ns = .013s = 13ms. But like edeca said, Timer1 has a prescaler if you should need it.
 
Dear all,

I'm using a PICDEM USB mounted with PIC18F4550 and I'm using the C18 compiler. I
want to measure a certain period of time at one of the PIC's inputs, lets say between a falling edge and a rising edge. so what i need to do is to store the value of a "timer" at the falling edge moment and store it again at the rising edge moment and do the comparison, but how to write it in C18 with all timer configuration and stuff !??

Thanks in advance

Best Regards

Hi Anthony, if you want to calculate the High Time/Low time/ Total time of a pulse, then check out my blog, it has got an example doing that with a 18F1320. The simulation is in Proteus VSM.

Capture_Func_Example.c - File Shared from Box.net - Free Online File Storage

**broken link removed**
 
Hello "Wond3rboy", thanks for ur help, one question if u may. I wrote the following code, nothing fancy ...

OpenTimer0( TIMER_INT_OFF &
T0_16BIT &
T0_SOURCE_INT &
T0_SOURCE_INT &
T0_PS_1_256);
while(1)
{
WriteTimer0( 0 );
LED = 1;
while(ReadTimer0() <= 488);
LED = 0;
WriteTimer0( 0 );
while(ReadTimer0() <= 488);
}
}

where i went wrong in my calculations ?:
using 20MHz crystal -> 1increment of timer0 = 200ns, choosing 1:256 prescaler -> 1increment = 51.2us, desired delay 25000us ... 25000/51.2=488 !! I tried to put this value, i ran simulation on Proteus, i scoped the output and i detected a 6.2ms delay and not 25ms, what might be the problem?
thanks again
 
Hi Anthony,

First i would say that do not rely on Proteus for timing accuracy. I have not found it very accurate in this regard. Second, the way that you are going about with your program is wrong. Here is a correct version:

#include<p18f4620.h>
#include<timers.h>
#pragma config OSC=HS,WDT=OFF,DEBUG=ON,LVP=OFF,IESO=OFF,WRTD=OFF
#define LED LATBbits.LATB0 // arbitary
void main(void)
{
ADCON1=0x0f;
CMCON=0x07;
TRISB=0x00;
OpenTimer0( TIMER_INT_OFF &
T0_16BIT &
T0_SOURCE_INT &
T0_PS_1_256);
while(1)
{
WriteTimer0( 65048 );
LED = 1;
while(INTCONbits.TMR0IF==0);// Wait here till timer0 overflows
LED = 0;
WriteTimer0( 65048 );
while(INTCONbits.TMR0IF==0);// Wait here till timer0 overflows
}
}

Before starting you should know that delay generation using timers depend on 3 things,

1. The timer register value
2. The Crystal Frequency
3. The prescaler

And a fourth, the compiler, if you are using a language other than assembly.

Continuing from your calculation of 488. This is how you generate a delay:

Max Timer0 count is 65535 for 16 bits. You need to make 488 cycles so,

65535-488=56047

you add one for the overflow it takes to become 0 again, so

65047+1=65048.

So for 488 cycles your TMR0 value is 65048.

Now also as you can see that our approximation of 488 when it was actually 25000/51.2=488.28125,
gives us an error of 51.2*488=24985.6 i-e we are short by around 14 cycles. Don't forget you will also get extra code that will effect the frequency too.

Check on a scope, increase or decrease the timer register value depending on what you get.

Enough for now.

PS: you can always call me by my last name, Syed.
 
Last edited:
Hello!!I´m from Spain and my english is not very good but...I will try to explain my problem in the best possible way...

I want to measure a period of time of my signal...because I need the signal's frequency.
I want to use CCP on capture mode, with timer3.
I use the PIC18f4620.
My problem is that...when I read the timer..it is different with the same signal..and I don´t know why??

This is my code:

#include <p18f4620.h>
#include <delays.h>
#include <capture.h>
#include <stdio.h>
#include <timers.h>
#include <stdlib.h>

#pragma config DEBUG=OFF
#pragma config OSC=XT
#pragma config WDT=OFF
#pragma config LVP=OFF
#pragma config PWRT=OFF
#pragma config MCLRE=OFF
#pragma config CCP2MX = PORTBE

#define LED LATEbits.LATE0

void main(){

unsigned int cambio;
unsigned int tiempo;
float uSxTick = 1.0;
float f=0.00;
float st=0.0;


ADCON1=0XFF;
TRISBbits.TRISB3=1;
TRISEbits.TRISE0=0;



// Configure Timer1
OpenTimer3( TIMER_INT_OFF &
T3_SOURCE_INT);

// Configure Capture2
OpenCapture2( C2_EVERY_RISE_EDGE &
CAPTURE_INT_OFF );

while(PIR2bits.CCP2IF==1){
WriteTimer3(0);
//LED=1;
PIR2bits.CCP2IF=0;
cambio=1;
}
while(cambio==1){
while(PIR2bits.CCP2IF==1){
tiempo=ReadTimer3();
st = uSxTick * tiempo;
f = 1 / (st/1000000);
//LED=0;
PIR2bits.CCP2IF=0;
cambio=0;
}

}

}

Do you have any suggestions??

Thank you very much!!
 
Hello!!I´m from Spain and my english is not very good but...I will try to explain my problem in the best possible way...

I want to measure a period of time of my signal...because I need the signal's frequency.
I want to use CCP on capture mode, with timer3.
I use the PIC18f4620.
My problem is that...when I read the timer..it is different with the same signal..and I don´t know why??

This is my code:

#include <p18f4620.h>
#include <delays.h>
#include <capture.h>
#include <stdio.h>
#include <timers.h>
#include <stdlib.h>

#pragma config DEBUG=OFF
#pragma config OSC=XT
#pragma config WDT=OFF
#pragma config LVP=OFF
#pragma config PWRT=OFF
#pragma config MCLRE=OFF
#pragma config CCP2MX = PORTBE

#define LED LATEbits.LATE0

void main(){

unsigned int cambio;
unsigned int tiempo;
float uSxTick = 1.0;
float f=0.00;
float st=0.0;


ADCON1=0XFF;
TRISBbits.TRISB3=1;
TRISEbits.TRISE0=0;



// Configure Timer1
OpenTimer3( TIMER_INT_OFF &
T3_SOURCE_INT &
T3_SOURCE_CCP
);

// Configure Capture2
OpenCapture2( C2_EVERY_RISE_EDGE &
CAPTURE_INT_OFF );
PIR2bits.CCP2IF=0;
while(PIR2bits.CCP2IF==1)// this should be while(PIR2bits.CCP2IF===0);
//so that it waits here until CCP generates a flag condition marking the start of the wave


{// delete this
WriteTimer3(0);
//LED=1;
PIR2bits.CCP2IF=0;
cambio=1;// delete this
}// delete this
while(cambio==1)// delete this
{// delete this
while(PIR2bits.CCP2IF==1)// this should be while(PIR2bits.CCP2IF===0);
//So that it stays here until CCP generates a flag condition and marks the end of a full period


{// delete this
tiempo=ReadTimer3();
st = uSxTick * tiempo;
f = 1 / (st/1000000);
//LED=0;
PIR2bits.CCP2IF=0;
cambio=0;// delete this
}

}// delete this

}// delete this

Do you have any suggestions??

Thank you very much!!

Hi, you were missing a bracket in your code. This is what you need to do to measure the full period of a square wave(max is 65536* your clock).
 
Last edited:
If you are going to tie up the processor by polling then you may as well take the simple approach,
Code:
    while(RB3==1);      //Wait for end of previous pulse
    while(RB3==0);      //Wait for start of new pulse
    WriteTimer3(0);     //Clear Timer
    while(RB3==1);      //Wait for end of new pulse
    While(RB3==0);      //Wait for start of next pulse
    Time=ReadTimer3();  //read timer

Or, use the capture hardware correctly,
Code:
    WriteTimer3(0);
    OldTime=0;
    while(1){
        if(PIR2bite.CCP2IF==1){         //do we have new time?
            NewTime=CCPR1L+256*CCPR1H;  //get captured time
            PulseTime=NewTime-OldTime;  //calculate cycle time
            OldTime=NewTime;            //keep copy for next time
            PIR2bits.CCP2IF=0;          //clear flag
        }
        //do whatever here
    }

Both of the above examples will find the time between successive rising edges.

Mike.
 
Thanks for yours answers.I got measure the frequency of my signal..but only if the frequency is less than 20KHz...It is because I use a crystal os 4MHZ??

I write this code:

#include <p18f4620.h>
#include <delays.h>
#include <capture.h>
#include <stdio.h>
#include <timers.h>
#include <stdlib.h>

#pragma config DEBUG=OFF
#pragma config OSC=XT
#pragma config WDT=OFF
#pragma config LVP=OFF
#pragma config PWRT=OFF
#pragma config MCLRE=ON
#pragma config CCP2MX = PORTBE

#define LED LATEbits.LATE0

void main(){

unsigned int tiempo;
unsigned float uSxTick = 1.0;
unsigned float f;
unsigned float st=0.0;


ADCON1=0XFF;
TRISBbits.TRISB3=1;
TRISEbits.TRISE0=0;


// Configure Timer1
OpenTimer3( TIMER_INT_OFF &
T3_SOURCE_INT &
T3_SOURCE_CCP &
T3_PS_1_8);

// Configure Capture2
OpenCapture2( C2_EVERY_RISE_EDGE &
CAPTURE_INT_OFF );

PIR2bits.CCP2IF=0;

while(PIR2bits.CCP2IF==0);
WriteTimer3(0);
//LED=1;
PIR2bits.CCP2IF=0;

while(PIR2bits.CCP2IF==0);
tiempo=ReadTimer3();
st = uSxTick * tiempo;
f = 1 / (st/1000000);
//LED=0;
PIR2bits.CCP2IF=0;

CloseCapture2;

}

I´m going to write another code with PORTRB3...

Thanks for all!!
 
If you are going to tie up the processor by polling then you may as well take the simple approach,
Code:
    while(RB3==1);      //Wait for end of previous pulse
    while(RB3==0);      //Wait for start of new pulse
    WriteTimer3(0);     //Clear Timer
    while(RB3==1);      //Wait for end of new pulse
    While(RB3==0);      //Wait for start of next pulse
    Time=ReadTimer3();  //read timer

I also use this code...and it works fine...but it measures a frequency a little different...and it only works until 20KHZ...

#include <p18f4620.h>
#include <delays.h>
#include <capture.h>
#include <stdio.h>
#include <timers.h>
#include <stdlib.h>

#pragma config DEBUG=OFF
#pragma config OSC=XT
#pragma config WDT=OFF
#pragma config LVP=OFF
#pragma config PWRT=OFF
#pragma config MCLRE=ON
#pragma config CCP2MX = PORTBE

#define LED LATEbits.LATE0

void main(){

unsigned int time;
unsigned float uSxTick = 1.0;
unsigned float f;
unsigned float st=0.0;


ADCON1=0XFF;
TRISBbits.TRISB3=1;
TRISEbits.TRISE0=0;


// Configure Timer1
OpenTimer3( TIMER_INT_OFF &
T3_SOURCE_INT &
T3_PS_1_8);

while(PORTBbits.RB3==1); //Wait for end of previous pulse
while(PORTBbits.RB3==0); //Wait for start of new pulse
WriteTimer3(0); //Clear Timer
while(PORTBbits.RB3==1); //Wait for end of new pulse
while(PORTBbits.RB3==0); //Wait for start of next pulse
time=ReadTimer3(); //read timer
st = uSxTick * time;
f = 1 / (st/1000000);


}

I don´t know why..

Thanks!! ;)
 
I don´t know why..

Thanks!! ;)

You have the prescaler set to 8 and the polling code takes some time to execute and so this limits your resolution. I'm guessing it still works above 20kHz but is inaccurate.

You could improve it a few ways, increase the processor speed by using the PLL to make it 4 times faster or reduce the prescaler to give better resolution of timer 3. I would try the PLL first.

You should also try the capture hardware as that will be even more accurate and allow you to do other things as well.

Mike.
 
Hi Mike, and adreaymaria,

@ andreaymaria
If it is accuracy you want than using a higher resolution would give you significant improvement. Also another thing you can do is use the CCP with interrupts. More over, you can omit using C18 libraries and use interrupts manually so that there will be less overhead of code(a bit complex though). If you want to use CCP with interrupts and use the libraries, than there is such an example in my blog, which measures the pulse time of a wave. Its written for a 18F1320 but would do your task with some editing.

If you want to measure higher frequencies than you will have to use a higher prescaler and subsequently end up with the measurement being slightly in accurate.
 
If you want to use CCP with interrupts and use the libraries, than there is such an example in my blog, which measures the pulse time of a wave. Its written for a 18F1320 but would do your task with some editing.

I have seen your code...and I have used it to measure my signal´s frequency...but...It doesn´t working very good...
I think that I don´t use the interrupts correctly. The frequency is different in each case with the same signal.

This is the code...it´s practically the same that yours...

Thanks for all!!

//This is a program that displays the use of the CCP feature with
//Microchips Libraries documented on page 21.It measures the High and the Total Time
//and sends it to the serial port.
//The maximum Pulse Time is 16.38ms
//The Timer Section is documented on P#57 of C18 Libraries
//Use 181320capture.DSN
//In this simulation a switch has been used, for hardware use a function generator since the debounce time for the //switch will exceed the highest possible time measurement.
#include <p18f4620.h>
#include <delays.h>
#include <capture.h>
#include <stdio.h>
#include <timers.h>
#include <stdlib.h>

#pragma config DEBUG=OFF
#pragma config OSC=XT
#pragma config WDT=OFF
#pragma config LVP=OFF
#pragma config PWRT=OFF
#pragma config MCLRE=ON
#pragma config CCP2MX = PORTBE

unsigned int result,hightime,totaltime,dutycycle;//Variables used
unsigned char start=1;
unsigned char highlow,end;
unsigned float uSxTick = 1.0;
unsigned float f;
unsigned float st=0.0;

/*******************************************************************************************************
/* Interrupcion con direccion 0x08
/***************************************************************************************************** */
void InterruptServiceHigh(void);
#pragma code InterruptVectorHigh = 0x08
void InterruptVectorHigh (void)
{
_asm
goto InterruptServiceHigh //Salta a la direccion de interrupcion ALTA
_endasm
}
/*******************************************************************************************************
/* Interrupcion con direccion 0x18
/***************************************************************************************************** */
void InterruptServiceLow(void);
#pragma code InterruptVectorLow = 0x18
void InterruptVectorLow (void)
{
_asm
goto InterruptServiceLow //Salta a la direccion de interrupcion BAJA
_endasm
}


#pragma interrupt InterruptServiceHigh // Directiva pragma "interrupt" para interrupcion de alta prioridad
void InterruptServiceHigh(void)
{
if(PIR2bits.CCP2IF==1)
{
if(start==1)
{
WriteTimer1(0);//Start timer 1 for maximum count
OpenCapture2( CAPTURE_INT_ON & //Initialize CCP for HtoL
C2_EVERY_FALL_EDGE );
start=0;
highlow=1;
PIR2bits.CCP2IF=0;// Enable interrupt again
}
else
{
if(highlow==1)
{
hightime = ReadTimer1();// Read contents of capture registers
OpenCapture2( CAPTURE_INT_ON & //Initialize CCP for LtoH
C2_EVERY_RISE_EDGE );
highlow=0;
end=1;
PIR2bits.CCP2IF=0;
}
else
if(end==1)
{
totaltime=ReadTimer1();// Read contents of Capture registers
st = uSxTick * totaltime;
f = 1 / (st/1000000);
CloseTimer1();// Close timer 1
CloseCapture2();// Close CCP Module
INTCONbits.GIE=0;//Disbale interrupts
//while(1);// wait here
}
}
}
}
void main(void)
{
OSCCON=0x60;//Internal 4MHz oscillator
ADCON1=0x7f;//Make all pins Digital
TRISE=0x00;//Only for test
LATE=0;
TRISBbits.TRISB3=1;//Make CCP1 pin an input for the pulse

//Initiazlize the capture moudule(ccp) for LtoH
OpenCapture2( C2_EVERY_RISE_EDGE
& CAPTURE_INT_ON );

OpenTimer1( TIMER_INT_OFF &//configure Timer1 for ccp
T1_16BIT_RW &// Can also use Timer3
T1_SOURCE_INT & // Timer1 clock source is internal
T1_SOURCE_CCP &// Make Timer1 source for CCP module
T1_PS_1_1);// No prescaler for timer1

INTCONbits.PEIE=1;// Enable peripheral interrupts
INTCONbits.GIEH=1;// Enable all interrupts

}

/*******************************************************************************************************
********************************************************************************************************
/* Interrupcion con direccion 0x18
/***************************************************************************************************** */
#pragma interruptlow InterruptServiceLow// Directiva pragma "interruptlow" para interrupcion de baja prioridad
void InterruptServiceLow(void)
{
/**********************
/* aqui va el programa que corresponde a la interrupcion de baja prioridad
***********************/
}
 
Hi adndreaymaria,

This measures the hightime and the total time, what you need is the pulse time so only the first part of the ISR needs to be kept intact and the rest of it removed. A little change in the if statement in the first ISR part will give you the total time(you can do you calculation in that part). Ofcourse you need to be vary of my earlier post in which i said you will get some overhead. I do not have access to my computer. I will give you a working model of the changes tomorrow.
 
Hi andrea,

here you go, with the changes that require it to measure pulse time only. I also removed the WriteTimer instruction from the ISR and replaced it with a manual instruction. It still shows an error of 20-21% between the range of 1khz to 10khz (tested). But for higher frequencies, the error increases. Its because of the code overhead most likely, for the functions as well as C). If you want higher accuracy i advise you resort to using the Capture Function manually.
Code:
//This is a program that displays the use of the CCP feature with 
//Microchips Libraries documented on page 21.It measures the High and the Total Time
//and sends it to the serial port.
//The maximum Pulse Time is 16.38ms
//The Timer Section is documented on P#57 of C18 Libraries
//Use 181320capture.DSN
//In this simulation a switch has been used, for hardware use a function generator since the debounce time for the //switch will exceed the highest possible time measurement. 
#include<p18f1320.h>// Include files and definitions for the Processor
#include<capture.h>//Include function definitions for the Capture library
#include<timers.h>// Include function definitions for Timer Library
#include <usart.h>// Include function definitions for USART Library
#include<stdlib.h>// Include function definitions for string manupulation Library
#pragma config LVP=OFF,OSC=HSPLL,WDT=OFF// Configuration settings for 18f1320
unsigned int result,hightime,totaltime,dutycycle;//Variables used
unsigned char start=0;
unsigned char highlow,end;
char str[5];
void Send(void);// Function for sending data to serial port
void chk_isr(void);// ISR Handler
void hi_prioriint(void)// ISR Routine
{
	_asm
	GOTO chk_isr
	_endasm
}
#pragma interrupt chk_isr
void chk_isr(void)
{
	if(PIR1bits.CCP1IF)
		{
			T1CONbits.TMR1ON=1;
			start++;
			if(start==2)
			{			
			totaltime=(CCPR1H*256)+CCPR1L;// Read contents of Capture registers
			CloseTimer1();// Close timer 1
			Send();// Send the measured time values to the serial port
			INTCONbits.GIE=0;
			}
			PIR1bits.CCP1IF=0;// Enable interrupt again
			
		}
}
void main(void)
{
	OSCCON=0x60;//Internal 4MHz oscillator
	ADCON1=0x7f;//Make all  pins Digital
	TRISA=0x00;//Only for test
	LATA=0;
	TRISBbits.TRISB3=1;//Make CCP1 pin an input for the pulse
	TRISBbits.TRISB1=0;//Make TX pin an output
	//Initiazlize the capture moudule(ccp) for LtoH	
	OpenCapture1( C1_EVERY_RISE_EDGE
					& CAPTURE_INT_ON  );
	
	OpenTimer1( TIMER_INT_OFF &//configure Timer1 for ccp
				T1_16BIT_RW &// Can also use Timer3
				T1_SOURCE_INT & // Timer1 clock source is internal
				T1_SOURCE_CCP &// Make Timer1 source for CCP module
				T1_PS_1_1);// No prescaler for timer1
				T1CONbits.TMR1ON=0;
				TMR1H=0x00;//Start timer 1 for maximum count
				TMR1L=0x00;
	//Initialize USART for tx  high time,total time
	OpenUSART(USART_TX_INT_OFF &// Trasnmit interrupt off
			  USART_ASYNCH_MODE & // Use USART in asynchronous mode
			  USART_EIGHT_BIT &// Eight bits for data
			  USART_CONT_RX &// Enable continous receiving
			  USART_BRGH_LOW,// Dont use baud rate multiplier
			  12);// SPBRG value for a BR of 4800
			  INTCONbits.PEIE=1;// Enable peripheral interrupts
			  INTCONbits.GIEH=1;// Enable all interrupts
	while(1);// wait here
}

void Send(void)// For sending the times
{
	putrsUSART ("\nThe High Time in us is");
	ultoa(hightime,str);// convert integer in to string
	putsUSART(str);// Send string to serial port
	putrsUSART ("\nThe total time in us is");
	ultoa(totaltime,str);// convert integer in to string
	putsUSART(str);// Send string to serial port
	CloseCapture1();// Close CCP Module
	INTCONbits.GIE=0;//Disbale interrupts
	while(1);// wait here
}
 
Last edited:
Hi guys ,
i take Wond3rboy code and i am trying to measures the period and the high time of rectangular waveform using capture mode and display them on a 2x16 lcd . I am using ccp1 as input .
But although the program is build succeeded the screen doesn’t display anything .

I am working with pic18f452 and pic18f4520 I use mplap ide v8.63 and c18 lite v3,36.
The period of the waveform can be adjusted between 1,5ms and 3ms and it is between 3 and 5 volts .
This is the code I’m working on .

Code:
#include "p18f452.h"// Include files and definitions for the Processor
#include<xlcd.h>// Include function definitions for the External LCD Library library
#include<delays.h>// Include function definitions for built in Delay routines
#include <stdio.h>
#include <timers.h>
//#include<stdlib.h>// Include function definitions for string manupulation Library
#include<capture.h>//Include function definitions for the Capture library
 
//#include <stdlib.h> /**********tin aferesa epeidi ekane problima sto itoa. Kanonika auti einai bibliothiki poy exei to idoa mesa tin ebala otan ebla ton ADC kodika Den ipirxe prin. Douleue sosta xvris ayti*/
 
 
 
#pragma config LVP=OFF
#pragma config OSC=HS
#pragma config WDT=OFF// Use internal Oscillator, Watchdog off, LVP off
#pragma config DEBUG = ON 
 
 
 
#define DATALCD PORTD
#define dirDATA TRISD
 
 
unsigned int result,hightime,totaltime,dutycycle;//Variables used
unsigned char start=1;
unsigned char highlow,end;
 
 
 unsigned char data[]="this is Thigh";
char str1[5];
char str2[5];
unsigned char newlineadd=0x40;
 
void DelaySTRING(void);
void LCDdata (unsigned char);
void LCDDelay( void );
void lcdcmd(unsigned char);
void lcdcmd(unsigned char);
void stringtoLCD(unsigned char *m);
unsigned char * itoa(unsigned int value  , unsigned char * string);//
unsigned char dataString[10];
unsigned char *biginin;
 
 
void Send(void);// Function for sending data to serial port
void chk_isr(void);// ISR Handler
void hi_prioriint(void)// ISR Routine
{
                _asm
                GOTO chk_isr
                _endasm
}
#pragma interrupt chk_isr
void chk_isr(void)
{
                if(PIR1bits.CCP1IF)
                                {
                                                if(start==1)
                                                {
                                                                WriteTimer1(00);//Start timer 1 for maximum count
                                                                OpenCapture1( CAPTURE_INT_ON & //Initialize CCP for HtoL
                                                                                                                  C1_EVERY_FALL_EDGE );
                                                                start=0;
                                                                highlow=1;
                                                                PIR1bits.CCP1IF=0;// Enable interrupt again
                                                }
                                                else
                                                {
                                                                if(highlow==1)
                                                                {
                                                                                hightime = ReadCapture1();// Read contents of capture registers
                                                                                OpenCapture1( CAPTURE_INT_ON & //Initialize CCP for LtoH
                                                                                                                                C1_EVERY_RISE_EDGE );
                                                                                highlow=0;
                                                                                end=1;
                                                                                PIR1bits.CCP1IF=0;
                                                                }
                                                                else
                                                                if(end==1)
                                                                {
                                                                                totaltime=ReadCapture1();// Read contents of Capture registers
                                                                                CloseTimer1();// Close timer 1
                                                                                Send();// Send the measured time values to the serial port
                                                                }
                                                }
                                }
}
void main(void)
{
               // OSCCON=0x60;//Internal 4MHz oscillator
                ADCON1=0x7f;//Make all  pins Digital
 
                //Initiazlize the capture moudule(ccp) for LtoH   
                OpenCapture1( C1_EVERY_RISE_EDGE
                                                                                & CAPTURE_INT_ON  );
 
                OpenTimer1( TIMER_INT_OFF &//configure Timer1 for ccp
                                                                T1_16BIT_RW &// Can also use Timer3
                                                                T1_SOURCE_INT & // Timer1 clock source is internal
                                                                T1_SOURCE_CCP &// Make Timer1 source for CCP module
                                                                T1_PS_1_1);// No prescaler for timer1
                  OpenXLCD( EIGHT_BIT & LINES_5X7 );// Use 8 bit Data, 5x7 pixel Matrix per character
              while( BusyXLCD());// Wait till LCD finishes executing command
              WriteCmdXLCD( CURSOR_ON);// Turn cursor ON
               while( BusyXLCD() );// Wait till LCD finishes executing command
 
                                                  INTCONbits.PEIE=1;// Enable peripheral interrupts
                                                   INTCONbits.GIEH=1;// Enable all interrupts
                while(1);// wait here
}
 
void Send(void)// For sending the times
{
 
 
int integer,i,k,t,z;//????
            biginin=&dataString[0];
              WriteCmdXLCD( 0x80);// Force curson to the begining of 2nd line
                  while( BusyXLCD() );
                WriteCmdXLCD( SHIFT_DISP_LEFT );//Shift Cursor Display Left
 
                while( BusyXLCD());// Wait till LCD finishes executing command
 
                  putsXLCD(data);// Write the String data to the LCD
                   while( BusyXLCD());// Wait till LCD finishes executing command
                  WriteCmdXLCD( 0xC0);// Force curson to the begining of 2nd line
                  while( BusyXLCD() );
 
 DelaySTRING();
					integer=hightime;
					DelaySTRING();
					LCDDelay();
					itoa (integer, biginin);
					WriteCmdXLCD( 0xC0);          //Emfanizontai sti 2 grammi
					stringtoLCD(dataString);
                  while( BusyXLCD());
DelaySTRING();
                  WriteCmdXLCD(0b00000001);// Clear Display
                  while( BusyXLCD() );
                   WriteCmdXLCD( SHIFT_DISP_LEFT );//Shift Cursor Display Left
                	while( BusyXLCD());// Wait till LCD finishes executing command
 
                   DelaySTRING();
					integer=totaltime;
					DelaySTRING();
					LCDDelay();
					ultoa (integer, biginin);
					WriteCmdXLCD( 0xCA);          //Emfanizontai sti 2 grammi
					stringtoLCD(dataString);
                   while( BusyXLCD() );
                   while( BusyXLCD() );
 
                CloseCapture1();// Close CCP Module
 
                INTCONbits.GIE=0;//Disbale interrupts
 
                while(1);// wait here
 
     }
void LCDdata (unsigned char value)
{
BusyXLCD();//busylcd();
TRISD = 0;
DATALCD = value;
RS_PIN=1;
RW_PIN=0;
E_PIN=1;
LCDDelay();
E_PIN=0;
 
}
 
void LCDDelay(void)
{
int i=0;
for (i=0;i<250;i++);
 
} 
 
 

 
void stringtoLCD(unsigned char *m)
{
unsigned char i;
i = 0;
while(m[i] != 0)
{
LCDdata(m[i]);
i++;
}
}
 
void DelayFor18TCY(void)
 
{
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
_asm NOP _endasm
 
}
void DelayPORXLCD(void)
 
{
 
Delay1KTCYx(15);
 
}
 
void DelayXLCD(void)
 
{
 
Delay1KTCYx(5);
 
}
void DelaySTRING(void)
{
//Delay1KTCYx(450);   // Stin pragmatikotita MONO 
	Delay1KTCYx(100);//Gia prosomoiosi MONO				
}

i think i have added all the source file that the c18 functions need to work.(cp1close,cp1open, cp1read,t1open,t1write) and for lcd ( wcmdxlcd,putsxlcd,openxlcd,busyxlcd)



please help me .

Thank you.
 
Last edited by a moderator:
Status
Not open for further replies.

Latest threads

Back
Top