Welcome to EDAboard.com

Welcome to our site! EDAboard.com is an international Electronics Discussion Forum focused on EDA software, circuits, schematics, books, theory, papers, asic, pld, 8051, DSP, Network, RF, Analog Design, PCB, Service Manuals... and a whole lot more! To participate you need to register. Registration is free. Click here to register now.

16f877a interrupt issue

Status
Not open for further replies.

sysysy

Member level 3
Joined
Nov 11, 2010
Messages
56
Helped
2
Reputation
4
Reaction score
1
Trophy points
1,288
Activity points
1,801
Hi,

i am going to use the interrupt in PIC16f877a.
But anyone can explain methods to use timer and few register that will be used to me?

i am using 20Mhz crystal, but i dun know the pre-scaler is what for?

from what i know is put a number inside the register, then when the register count to 0xff, then the interrupt flag will be set. is it indicates when the flag be set, then the instruction will go to do the interrupt work???

For example,
if i want my program every 10 seconds go to do the interrupt service routine. that what should i set and how i calculate?

*note: i really do not understand the datasheet. :-( :-( :-(
 

Tahmid

Advanced Member level 5
Joined
Jun 17, 2008
Messages
4,758
Helped
1,792
Reputation
3,576
Reaction score
1,651
Trophy points
1,393
Location
Silicon Valley, California, USA (from Dhaka, Bangl
Activity points
30,543
Hi,
To start off with, the timer increases its value from 0 upwards every clock cycle. At 20MHz, the clock cycle is 0.2us. So every 200ns the timer increments its value by 1. When the value reaches 0xff it rolls over to 0 and sets the interrupt flag. If interrupt and global interrupt are enabled, then by going to the interrupt vector, you can carry out the functions you want done every time the timer rolls over.
So, at 20MHz, your timer rolls over at 51.2us. That means, every 51.2us, you can have an interrupt. The prescaler simply elongates the time of each tick. When you have prescaler set to 256, instead of 0.2us, each increment will occur at 0.2 * 256 = 51.2us. Therefore, the timer rolls over at 51.2 * 256 = 13.1ms.
In the interrupt routine, increment the value of a register every 13.1ms and in turn increment another register, keeping track as to when 10sec occurs.

For explanation, if you don't get the datasheet, look for the mid-range PIC Reference Manual. It explains everything fairly well.

Hope I could make you understand. Hope this helps.
Tahmid.
 

sysysy

Member level 3
Joined
Nov 11, 2010
Messages
56
Helped
2
Reputation
4
Reaction score
1
Trophy points
1,288
Activity points
1,801
Thanks alot for the information :)

Hmm, i read a datasheet and see some timer will have postscaler. What is that? and what is different between it and the prescale?

and i also find the equation on other forum ,
example,
20000000/(4*4*250*10) = 50 // 50 ticks per second

ok, i know 20M is the crystal value. then what is the remain one? (the equation is use for calculate 10s in timer2)
can you explain abit?

* it #define TicksPerEvent (500) before, after that use 500/50, then get 10seconds.
 

sysysy

Member level 3
Joined
Nov 11, 2010
Messages
56
Helped
2
Reputation
4
Reaction score
1
Trophy points
1,288
Activity points
1,801
Below is the source code for the equation.

Code:
#define TicksPerEvent (500) 
int1 do_operation=FALSE; 

#int_timer2 
void tick(void) { 
   static int16 counts=TicksPerEvent; 
   //Arrive here 50*/second 
   if (--counts==0) { 
       //500/50 = 10 so here every ten seconds 
       counts=TicksPerEvent; 
       do_operation=TRUE; 
   } 
} 

//Then in your main 

    //Early on 
    setup_timer2(T2_DIV_BY_14,249,10); /(4*4*250*10) 
    enable_interrupts(INT_TIMER2); 
    enable_interrupts(GLOBAL); 

    //Then in your main 'loop' 
    while (TRUE) { 
         if (do_operation) { 
             do_operation=FALSE; 
             //Code here that you want to execute every ten seconds 
         } 
         //Your other code 

    }
 
Last edited:

Tahmid

Advanced Member level 5
Joined
Jun 17, 2008
Messages
4,758
Helped
1,792
Reputation
3,576
Reaction score
1,651
Trophy points
1,393
Location
Silicon Valley, California, USA (from Dhaka, Bangl
Activity points
30,543
Hi,
I think it should be:
Code:
setup_timer2(T2_DIV_BY_4,249,10); /(4*4*250*10)
This means that you've set up timer2 for prescale by 4, postcale by 10, period 249
That means the timer will overflow when it reaches 249, ie 250 ticks, which is 50us
Now you have it prescaled and postscaled elongating the time from 50us to 50us * prescale unit * postscale unit
That means you have an overflow every 50 * 4 * 10 = 2000us = 2ms

In the ISR, you are checking if the interrupt occured 500 times. The interrupt occurs each 2ms. So if interrupt occurs 500 times, you know that it's been 500 * 2 = 1000ms. So you serve the routine every 1s. I think tick counter should be 5000 not 500.

Code:
20000000/(4*4*250*10) = 50 // 50 ticks per second
Above you made this mistake.
Code:
20000000/(4*4*250*10) = 500 // 500 ticks per second

That's what should be done.

Hope this helps.
Tahmid.
 
  • Like
Reactions: sysysy

    sysysy

    Points: 2
    Helpful Answer Positive Rating
Status
Not open for further replies.

Similar threads

Part and Inventory Search

Welcome to EDABoard.com

Sponsor

Top