I am trying to generate a 1 s delay using Timer0
of PIC18F2520
. I am using the internal 8 MHz oscillator. The timer works with FOSC/4 so I have :
8 Mhz/4 = 2 Mhz
T = 1/2 MHz = 0.5 µs
Now the number of counts for rollover is 0xFFFF (65536)
so according to the delay I want I need to set the values of TMR0L
and TMR0H
. Now let's say I want a delay of 1000 ms, so:
65536 - 64536 = 1000 ms
64536 (0xFC18) is the value which I need to put in TMR0L and TMR0H.
If the above calculations are correct then the following code should work properly (using the C18 compiler):
#include <p18F2520>
#pragma config WDT = OFF //Disable watchdog timer
#pragma config OSC = INTIO67 //Internal oscillator
#pragma config LVP = OFF
void main()
{
//8Mhz oscillator
OSCCONbits.IRCF0 = 1;
OSCCONbits.IRCF1 = 1;
OSCCONbits.IRCF2 = 1;
OSCCONbits.SCS = 1;
TRISCbits.TRISC2 = 0; //output led
while(1)
{
LATCbits.LATC2 = 1;
DelayMs();
LATCbits.LATC2 = 0;
DelayMs();
}
}
void DelayMs()
{
T0CONbits.PSA = 0; //Prescaler assignment bits
T0CONbits.T0CS=0; //clock source select bit
T0CONbits.T0PS = 0x01; //1:4 prescaler
TMR0H= 0xFC;
TMR0L=0x18;
T0CONbits.TMR0ON = 1; //enable timer1
while(INTCONbits.TMR0IF==0);
T0CONbits.TMR0ON = 0;
INTCONbits.TMR0IF=0;
}
When I programmed the device with the code above, the LED was on. It didn't turn off even after 4-5 minutes.
Best Answer
According to what you described the timer clocks at 2MHz. That is equivalent to 500nsec per tick of the timer.
When you program the timer to 64536 you are specifying that the timer should count for 1000 cycles before timing out.
1000 cycles at 500 nsec per cycle = 500,000 nsec = 500 usec
So in your while loop where you are trying to toggle the port pin to flash the LED the DelayMs() call is giving your LED a cycle time of 1 msec (500 usec off + 500 usec on).
With the LED flashing at 1msec rate (a.k.a 1kHz) the LED will appear to be on all the time!!
If your real goal was to have the LED on for 0.5 second and off for 0.5 second then you will need to increase your delays by 1000. So put each of the calls to DelayMs() within your while loop inside a for loop that would iterate the delay 1000 times.