View previous topic :: View next topic |
Author |
Message |
hayee
Joined: 05 Sep 2007 Posts: 252
|
Timer1 for 1 sec interrupt |
Posted: Mon Feb 22, 2010 5:54 am |
|
|
Hi,
I want interrupt after every 1 sec using timer1
I am doing the following calculations but not successful,Can anybody tell me where is the problem?
fclk=20Mhz
prescaler=1
Timer=1
Tout=1 sec, so Fout=1 Hz
using formula
Fout=fclk/(4*prescaler*(65536-TMR1)*count)
count=fclk/(4*1*65536*1)
I got the value of count
count~77
Here is my code
Code: |
#include <18f452.h>
#fuses HS,NOWDT,NOLVP,PUT,NOBROWNOUT
#use delay(clock=20000000)
#use rs232(xmit=PIN_C6, rcv=PIN_C7, baud=9600)
#int_TIMER1
TIMER1_isr()
{
output_toggle(PIN_D0);
//delay_ms(1);
}
void main()
{
setup_timer_1(T1_INTERNAL | T1_DIV_BY_1);
set_timer1(77);//value which come from the formula
//set_timer1(65459);
clear_interrupt(INT_TIMER1);
enable_interrupts(INT_TIMER1);
enable_interrupts(GLOBAL);
while(1)
{
output_toggle(PIN_D1);
delay_ms(300);
}
}
|
I also tried different prescaler but does't work. |
|
|
jaimechacoff
Joined: 14 Feb 2010 Posts: 24 Location: Santiago, Chile
|
|
Posted: Mon Feb 22, 2010 9:15 am |
|
|
there is a good example in the file EX_STWT.C using timer0
you need to set the division of your clock.
In the example they used:
Code: |
set_timer0(0);
setup_counters( RTCC_INTERNAL, RTCC_DIV_256 | RTCC_8_BIT);
|
and a clock of 20Mhz
that means:
Quote: |
20Mhz / 4 * 256 * 256 = ~76.2
|
so, each 76 interrupts by timer0 overflow you have one second.
PS: check your datasheet, I think in chip18 Timer0 also can be of 16bit. |
|
|
bkamen
Joined: 07 Jan 2004 Posts: 1615 Location: Central Illinois, USA
|
|
Posted: Mon Feb 22, 2010 9:47 am |
|
|
jaimechacoff wrote: |
Quote: |
20Mhz / 4 * 256 * 256 = ~76.2
|
so, each 76 interrupts by timer0 overflow you have one second.
|
Keeping in mind that every 5 interrupts, you'd want to consider adding 1 tick to make up for the .2 shortfall. (unless it doesn't matter -- but if you're timekeeping, it does.)
LEAP TICKS!
:D
-Ben _________________ Dazed and confused? I don't think so. Just "plain lost" will do. :D |
|
|
hayee
Joined: 05 Sep 2007 Posts: 252
|
|
Posted: Mon Feb 22, 2010 10:46 pm |
|
|
Hi, thanks for your replies.
I am already using Timer0 interrupt. That's why I am going to use Timer1.
The values you have shown using Timer0 is same as mine using Timer1.
That is 76.2. Then why it is not creating 1 sec pulses? Is there anything
wrong in my code? |
|
|
jaimechacoff
Joined: 14 Feb 2010 Posts: 24 Location: Santiago, Chile
|
|
Posted: Mon Feb 22, 2010 11:23 pm |
|
|
You are not counting how many Timer1 interrupts you are getting, furthermore, I believe there are some problems with your math, notwithstanding I left something for you:
Code: |
setup_timer_1(T1_INTERNAL | T1_DIV_BY_4);
set_timer1(0);
|
Quote: |
Interrupts per second = 20Mhz / 4 * 4 * 65536 = ~19.1
|
and your interrupt function will be called 19 times each second, and each one is for Timer1 overflows (65535 to 0).
Code: |
#INT_TIMER1
void second() {
if(--interrupts==0) {
output_low(PIN_B4); // for example, you can do what you want here
interrupts = 19;
}
}
|
"interrupts" is your interrupts counter, you need it to know how many times Timer1 got overflow, and you already know that 19 overflows are a second.
Good luck |
|
|
hayee
Joined: 05 Sep 2007 Posts: 252
|
|
Posted: Tue Feb 23, 2010 3:25 am |
|
|
Thanks everyone.
What I have done is that I simply replaced my timer0 function with timer1.
Now the timer0 is generating 1sec interrupt.
Both are working. |
|
|
thedrizzle Guest
|
timer1 interrupt |
Posted: Wed Feb 24, 2010 9:41 pm |
|
|
Code: |
#define int_per_sec 19 // How many times it takes timer1 to interrupt in one sec
#include "utilityALE.c" // !!! (20000000/4)=5000000 actual osc speed (5Mhz)
// (5000000/4)=1.25Mhz is with 1/4 prescaler
// 1.25Mhz/65536=19.07348633
// 0xFFFF is the highest that timer1_high and
// timer1_low with go and that with 1/4 prescaler
// the osc speed is now at 1.25Mhz which then
// gives us 1.25/(0xfff+1) and this gives us
// approx 19. Divide 1 second by 19 (1/19) and
// allakhazam we have that every 59.632ms the timer
// interrupts thus giving us approx 19 interrupts in a sec!!!!
int sec,sec2,min1,min2,counter;
int all_led[]={LED0,LED1,LED2,LED3,LED4,LED5,LED6,LED7};
#INT_TIMER1
void timer1_isr(){ // interrupt routine
counter--; // decrements counter which is set to it_per_sec
if(counter==0){ // will only do the following code if t1 has interrupted
sec++; // 19 times
counter=int_per_sec; // resets counter
}
if(sec==10){
sec=0; // clear sec
sec2++; // increment sec2 or the 10's side of 2
}
if(sec2==6){
min1++; // the rest is self explanatory same as before
sec2=0;
}
if(min1==10) {
min1=0;
min2++;
}
}
void main(){
setup_timer_1(T1_INTERNAL | T1_DIV_BY_4); // setting t1 to internal
enable_interrupts(INT_TIMER1); // enabling T1
enable_interrupts(GLOBAL); // enabling global interrupts
set_timer1(0); // clearing TMR1H & TMR1L
sec=0;
sec2=0; // making sure all variables are
min1=0; // at zero
min2=0;
counter=int_per_sec;
while(TRUE){
|
|
|
|
|