I am programming a PIC18F4520 and I've set it to use a 32Mhz internal clock.
I need a counter to tick every second so I'm using TMR0
for this purpose.
To use TMR0
, I have set the following:
- Prescaler 1:256
- 16 Bit mode
- High level interrupt on
TMR0
overflow.
To set the timer to count every 1 second, I've calculated it as follows:
TMR0 = (Required time)/(4 * Timer clock * prescale value)
= 1 / (4 * (1/32000000) * 256)
= 31250
So, TMR0 = 0xFFFF - 31250
.
Is this correct? If not, what am I missing? The code is as follows:
#pragma code
void main(void)
{
//Set clock frequency
OSCCON |= 0x70; //8 Mhz clock, primary clock
OSCTUNEbits.PLLEN = 1; //4x Multiplier, thus we have 32 Mhz clock
while (!OSCCONbits.IOFS); //Wait until INTOSC is stable.
//Enable TRISA as analog input (For ADC)
TRISA = 0x2F;
//PIN Outputs
TRISB = 0; //Make PORTD as output
//Reset PORTB
PORTB = 0;
//Set ADC
OpenADC(ADC_FOSC_32 & //Fosc/32
ADC_RIGHT_JUST &
ADC_4_TAD, //4xTAD
ADC_CH0 &
ADC_REF_VDD_VSS &
ADC_INT_OFF, ADC_5ANA); //ADC CH0-CH4 Initialized
//Set Timer0
OpenTimer0( TIMER_INT_ON &
T0_16BIT &
T0_SOURCE_INT &
T0_PS_1_256);
//Write Timer
WriteTimer0(CLOCK_TICK);
INTCON2bits.TMR0IP = 1; //TMR0 has high overflow interrupt priority
RCONbits.IPEN = 1; //enable priority levels
INTCONbits.GIEH = 1; //enable high interrupts
//Begin
while (TRUE)
{
}
CloseADC(); //Closing ADC
CloseTimer0();
}
On my high level interrupt vector, I've done this:
#pragma code
#pragma interrupt high_priority_interrupt
void high_priority_interrupt()
{
if (INTCONbits.TMR0IF) //TIMER0 overflowed
{
//Stuff
second += 1;
if (second == 60)
{
minute += 1;
second = 0;
}
if (minute == 60)
{
measure_and_switch();
WriteTimer0(CLOCK_TICK);
minute = 0;
}
INTCONbits.TMR0IF = 0; //Clear TIMER0 overflow bit.
}
}
So, basically, every 2 minutes, I want the method measure_and_switch()
to be executed. Should I follow it with WriteTimer0()
?
Btw: CLOCK_TICK
is TMR0
(calculation from above).
Thanks