Clock project with PIC16F873

Thread Starter

ecka333

Joined Oct 1, 2009
76
I am doing dual channel timer with pic16f873 microcontroller. Compiler - mikroc from Mikroelektronika. Timer schematic and pcb is ready, now i am programming microcontroller. Now clock programming is made, but code is not working. Microcontroller now must count minutes and hours and display time in four seven segments displays. But all, that these displays shows, is lighting three segments: a, d and g. Three buttons is not programmed yet. Mybe someone could help me with the code? Schematics is in .doc file. Part I of the code:


Rich (BB code):
//Quartz crystal=2.097152Mhz, ucontroller - PIC16F873
/*Configuration:
oscilator XT; code protection off; WDT disabled; power-up timer enabled;
brown-out reset enabled; low voltage programming disabled;
code protection data disabled; flash program memory write enabled;
debugger mode disabled.
*/
//variable declaration
unsigned int Clock, T1on, T1off, T2on, T2off, Display;
unsigned short int Hours, Minutes, Seconds,
Segment1, Segment2, Segment3, Segment4, WhatShow;
bit SA1Press, SA2Press, SA3Press, SA2SA3Press, HG2DpToggle, EditMode, Blackout;
void zero(){PORTC=0b00111111;}         //show number 0 in display
void one(){PORTC=0b00000110;}          //show number 1 in display
void two(){PORTC=0b01011011;}          //show number 2 in display
void three (){PORTC=0b01001111;}       //show number 3 in display
void four (){PORTC=0b01100110;}        //show number 4 in display
void five (){PORTC=0b01101101;}        //show number 5 in display
void six (){PORTC=0b01111101;}         //show number 8 in display
void seven (){PORTC=0b00000111;}       //show number 7 in display
void eight (){PORTC=0b01111111;}       //show number 8 in display
void nine (){PORTC=0b01101111;}        //show number 9 in display
void blank (){PORTC=0b00000000;}        //show nothing in display
void Delay(){Delay_ms(5);}             //delay
void InitTimer0 ()
    {
    // Timer0 initialisation (led blinker in Edit mode) Period = 0.125 sec (8Hz)
    TMR0 = 0;                // preset for timer register
    OPTION_REG.PSA = 0;      // prescaler is assigned to the Timer0
    OPTION_REG.PS2 = 1;      // Prescaler= 256
    OPTION_REG.PS1 = 1;
    OPTION_REG.PS0 = 1;
    OPTION_REG.T0CS = 0;     // TMR0 Clock Source Select bit - Internal Clock
    INTCON.T0IF=0;              //clear TMR0 interrupt flag
    INTCON.T0IE=0;           //TMR0 interrupt enable
    }
    void InitTimer1 ()
    {
    // Timer1 initialisation (Seconds counter) Period = 1 sec
    T1CON.T1CKPS1 = 1;       // Prescaler= 8
    T1CON.T1CKPS0 = 1;
    T1CON.T1OSCEN = 0;       // Timer1 Oscillator disable
    T1CON.TMR1CS = 0;        // Timer1 Clock Source Select bit - internal clock
    T1CON.TMR1ON = 1;        // enable timer
    TMR1H = 0;               // preset for timer1 MSB register
    TMR1L = 0;               // preset for timer1 LSB register
    PIR1.TMR1IF = 0;         //clear TMR1 interrupt flag
    PIE1.TMR1IE=1;           //TMR1 interrupt enable
    }
void InitTimer2 ()
    {
    //Timer2 initialisation (Display multiplexing) Period = 0.00341797 seconds
    PR2 = 7;                 // PR2 (Timer2 Match value)
    T2CON = 120;             // Postscaler=16
    T2CON.T2CKPS1 = 1;      // Prescaler=16
    T2CON.T2CKPS0 = 0;
    T2CON.TMR2ON = 1;       // turn timer2 on;
    PIR1.TMR2IF = 0;        // clear timer2 interupt flag
    PIE1.TMR2IE = 1;        // enable Timer2 interrupts
    }
 

Attachments

Last edited:

Thread Starter

ecka333

Joined Oct 1, 2009
76
Now my project is near the end, all programming work is done. But now i noticed, that microcontrollers clock is running too fast. The innacurracy is different: one day it reaches 1 minute in every 10 minutes, the other day it is 4 seconds in 10 hours. I can't understant, why the difference is so big. I am using pic16f873 microcontroller, 2,097152MHz crystal oscilator (XTAL configuration) with 15pF ceramic capacitors. Maybe inacurracy comes from environment temperature? And how i can correct this clock inacurracy?
PART II of the code:
Rich (BB code):
void interrupt ()
    {
     if(PORTB.B7==0){Blackout=0;} else {Blackout=1;}
     if(Blackout==1)
         {PORTC=0b00000000;//turn off HG1-HG4 indicators on blackout
         PORTA.B3=0; PORTB.B3=0; PORTA.B4=1; TRISA.B5=1; //turn off all five diode indicators on blackout
         PORTA.B1=0; PORTA.B2=0;//turn off outputs of timers on Blackout
         EditMode=0;
        }
    //interrupt from Timer0 -  0.125sec(led blinker in Edit mode)
    if(INTCON.T0IF==1&&INTCON.T0IE==1&&Blackout==0)
        {if(WhatShow==0){PORTA.B3=~PORTA.B3;}
        if(WhatShow==1){PORTB.B3=~PORTB.B3;}
        if(WhatShow==2){PORTA.B4=~PORTA.B4;}
        if(WhatShow==3){PORTA.B5=0; TRISA.B5=~TRISA.B5;}
        if(WhatShow==4){PORTA.B5=1; TRISA.B5=~TRISA.B5;}
        INTCON.T0IF=0;
        }
     //interrupt from Timer1 - 1 sec (Seconds counter)
     if(PIR1.TMR1IF==1&&PIE1.TMR1IE==1){
     HG2DpToggle=~HG2DpToggle;//togle auxiliary HG2 decimal point's bit
     if (Seconds<=58) {Seconds=Seconds+1;}
     else if (Seconds==59&&Clock<=1438) {Seconds=0; Clock=Clock+1;}
     else if (Seconds==59&&Clock==1439) {Seconds=0; Clock=0;};
     PIR1.TMR1IF=0;}                    //clear TMR1 flag
     //interrupt from Timer2 - 0.00341797 sec (Display multiplexing)
     if(Blackout==0&&PIR1.TMR2IF==1){
         if (PORTB.B2==1) {PORTB.B2=0;
         switch (Segment2){
         case 0: zero(); break;
         case 1: one (); break;
         case 2: two(); break;
         case 3: three (); break;
         case 4: four(); break;
         case 5: five (); break;
         case 6: six(); break;
         case 7: seven (); break;
         case 8: eight(); break;
         case 9: nine (); break;};
         PORTB.B1=1; PORTB.B0=0; PORTA.B0=0;
         PORTC.B7=HG2DpToggle;               //blink indicator's HG2 decimal point
                           }
 
         else if (PORTA.B0==1) {PORTA.B0=0;
         switch (Segment1){
         case 0: blank(); break;
         case 1: one (); break;
         case 2: two(); break;
                        };
         PORTB.B2=1; PORTB.B1=0; PORTB.B0=0; PORTC.B7=0;
                               }
 
         else if (PORTB.B0==1) {PORTB.B0=0;
         switch (Segment4){
         case 0: zero(); break;
         case 1: one (); break;
         case 2: two(); break;
         case 3: three (); break;
         case 4: four(); break;
         case 5: five (); break;
         case 6: six(); break;
         case 7: seven (); break;
         case 8: eight(); break;
         case 9: nine (); break;};
         PORTA.B0=1; PORTB.B1=0; PORTB.B2=0; PORTC.B7=0;
                          }
         else if (PORTB.B1==1) {PORTB.B1=0;
         switch (Segment3){
         case 0: zero(); break;
         case 1: one (); break;
         case 2: two(); break;
         case 3: three (); break;
         case 4: four(); break;
         case 5: five (); break;
         case 6: six(); break;
         case 7: seven (); break;
         case 8: eight(); break;
         case 9: nine (); break;};
         PORTB.B0=1; PORTA.B0=0; PORTB.B2=0; PORTC.B7=0;
                        }
     PIR1.TMR2IF=0;}     //clear TMR2 flag
     }
void main()
     {
     /*SFR's and variables initialisation*/
     ADCON1=0b00000110;        //make PORTA pins digital
     TRISA=0b00100000;         //configure input/output pins, turn on Clock indication
     TRISB=0b11110000;
     TRISC=0b00000000;
     PORTA=0b00011000;         //clear data latches
     PORTB=0b11110100;
     PORTC=0b00000000;
     OPTION_REG.B7=0;          //turn on pullups for B port
     Seconds=0; Clock=0; T1on=0; T1off=0; T2on=0, T2off=0; //Set all variables to zero
     SA1Press=0; SA2Press=0; SA3Press=0; SA2SA3Press=0;
     WhatShow=0; EditMode=0;              //on turn-on show Clock time in display
     InitTimer0 ();
     InitTimer1 ();
     InitTimer2 ();
     INTCON.PEIE = 1;        //Peripheral Interrupt Enable
     INTCON.GIE = 1;         // global interrupt enable
 
      for (;;)
      {
      //turn timers on and off
      if(Blackout==0)
          {if(Clock>=T1on&&Clock<T1off){PORTA.B2=1;}
          else if(Clock>=T1off&&Clock<T1on){PORTA.B2=1;}
          else{PORTA.B2=0;};
          if(Clock>=T2on&&Clock<T2off){PORTA.B1=1;}
          else if(Clock>=T2off&&Clock<T2on){PORTA.B1=1;}
          else{PORTA.B1=0;}
          }
      //display modes initialization
      if (WhatShow==0){Display=Clock;}
      else if(WhatShow==1){Display=T1on;}
      else if(WhatShow==2){Display=T1off;}
      else if(WhatShow==3){Display=T2on;}
      else if(WhatShow==4){Display=T2off;}
      //display modes indication
      if(EditMode==0&&PORTB.B7==0)
          {if (WhatShow==0){PORTA.B3=1; PORTB.B3=0; PORTA.B4=1; TRISA.B5=1;}
          else if(WhatShow==1){PORTA.B3=0; PORTB.B3=1; PORTA.B4=1; TRISA.B5=1;}
          else if(WhatShow==2){PORTA.B3=0; PORTB.B3=0; PORTA.B4=0; TRISA.B5=1;}
          else if(WhatShow==3){PORTA.B3=0; PORTB.B3=0; PORTA.B4=1; TRISA.B5=0; PORTA.B5=0;}
          else if(WhatShow==4){PORTA.B3=0; PORTB.B3=0; PORTB.B4=1; TRISA.B5=0; PORTA.B5=1;}
          }
          //Time calculation
          Hours=Display/60;
          Segment1=Hours/10;         //calculate tens of hours
          Segment2=Hours%10;         //calculate ones of hours
          Minutes=Display%60;
          Segment3=Minutes/10;         //calculate tens of minutes
          Segment4=Minutes%10;         //calculate ones of minutes
 
         //check if button SA1 is pressed
         if(PORTB.B4==0&&SA1Press==0&&EditMode==0){SA1Press=1; Delay();};
         if(PORTB.B4==1&&SA1Press==1&&EditMode==0)
             {SA1Press=0; Delay();
             //button SA1 was pressed and released, so switch mode:
             if(Whatshow<4){Whatshow++;}else{Whatshow=0;}
             };
         //Check if SA2 & SA3 simultaneously pressed, if pressed, enter edit mode
         if(EditMode==0&&PORTB.B5==0&&PORTB.B6==0&&SA2SA3Press==0){SA2SA3Press=1; Delay();}
         if(PORTB.B5==1&&PORTB.B6==1&&SA2SA3Press==1){SA2SA3Press=0; Delay(); EditMode=1;}
         //Check if SA2 pressed, if pressed, edit hours
         if(EditMode==1&&PORTB.B5==0&&SA2Press==0){SA2Press=1; Delay();};
         if(EditMode==1&&PORTB.B5==1&&SA2Press==1)
             {SA2Press=0; Delay();
             if(WhatShow==0){if(Clock<1380){Clock=Clock+60;}else{Clock=Clock-1380;};}
             else if(WhatShow==1){if(T1on<1380){T1on=T1on+60;}else{T1on=T1on-1380;};}
             else if(WhatShow==2){if(T1off<1380){T1off=T1off+60;}else{T1off=T1off-1380;};}
             else if(WhatShow==3){if(T2on<1380){T2on=T2on+60;}else{T2on=T2on-1380;};}
             else if(WhatShow==4){if(T2off<1380){T2off=T2off+60;}else{T2off=T2off-1380;};}
             }
         //Check if SA3 pressed, if pressed, edit minutes
         if(EditMode==1&&PORTB.B6==0&&SA3Press==0){SA3Press=1; Delay();};
         if(EditMode==1&&PORTB.B6==1&&SA3Press==1)
             {SA3Press=0; Delay();
             if(WhatShow==0){if(Clock%60<59){Clock=Clock+1;}else{Clock=Clock-59;};}
             else if(WhatShow==1){if(T1on%60<59){T1on=T1on+1;}else{T1on=T1on-59;};}
             else if(WhatShow==2){if(T1off%60<59){T1off=T1off+1;}else{T1off=T1off-59;};}
             else if(WhatShow==3){if(T2on%60<59){T2on=T2on+1;}else{T2on=T2on-59;};}
             else if(WhatShow==4){if(T2off%60<59){T2off=T2off+1;}else{T2off=T2off-59;};}
             }
 
         //Check if SA1 pressed, if pressed, escape edit mode
         if(EditMode==1&&PORTB.B4==0&&SA1Press==0){SA1Press=1; Delay();};
         if(PORTB.B4==1&&SA1Press==1){SA1Press=0; Delay(); EditMode=0;}
 
         //enable edit mode
         if(EditMode==1){INTCON.T0IE=1;if(Whatshow==0){PIE1.TMR1IE=0;HG2DpToggle=1;}}
         //disable edit mode
         if(EditMode==0){PIE1.TMR1IE=1; INTCON.T0IE=0;}
        }
      }
 
Last edited:

Markd77

Joined Sep 7, 2009
2,806
Is it on breadboard? There are lots of stray capacitances and inductances which can wreck crystal accuaracy.
It's quite likely it will work properly when on a proper PCB.
 

Markd77

Joined Sep 7, 2009
2,806
Something to try would be to reduce the amount of code inside the interrupt. Unless C does something clever it can be possible to miss interrupts if you spend too much time in there.
However I would have guessed that would make the clock run slow not fast.......
 

Thread Starter

ecka333

Joined Oct 1, 2009
76
One interesting thing: clock is going normally until one minute. After one minute it starts run very fast, clock counts 60 seconds through 40-50 seconds interval of time, according good clock. Seems like Timer1 interrupt occurs not always exactly 1 second, sometimes less, sometimes exactly. Or interrupt flag is not cleared always after Timer1 interrupt. But when i look at the code, everything seems ok. Maybe this is problem with compiler?
 

t06afre

Joined May 11, 2009
5,934
Read the datasheet with care. It may be as you say. Some flag need to be cleared. If you have a free pin on the cpu, and a scope. Toggle this pin each time you enter and leave the Timer1 ISR(If this is used as second counter). That will give you some clues. You must use a scope as the pin may switch to fast to be seen on a LED
 

Markd77

Joined Sep 7, 2009
2,806
I don't know much about C (I should put that in my signature) so I can't really check the code well.
It's possible that both interrupt flags are set, as they become set when the condition is true, regardless of if you are already in the interrupt.
I find it's best to check for one type of interrupt, service it as quickly as possible, then exit the ISR. If the other interrupt is set then the ISR will immediately be triggered again. Checking for both kinds of interrupts can lead to ruin because you are servicing the event that caused the interrupt and also another one.
 

Potato Pudding

Joined Jun 11, 2010
688
The Timer1 module is a 16-bit timer/counter consisting
of two 8-bit registers (TMR1H and TMR1L), which are
readable and writable. The TMR1 Register pair
(TMR1H:TMR1L) increments from 0000h to FFFFh
and rolls over to 0000h. The TMR1 Interrupt, if enabled,
is generated on overflow, which is latched in interrupt
flag bit TMR1IF (PIR1<0>). This interrupt can be
enabled/disabled by setting/clearing TMR1 interrupt
enable bit TMR1IE (PIE1<0>).
Timer1 can operate in one of two modes:
• As a timer
• As a counter
from the Microchip 16f873 datasheet
What you want to do is let it run as a counter and just keep reading the timer as often as possible and decoding the timer counts into a real time value. Interrupts shouldn't be required but they are normally used.

I would suggest that you let a prescaler work for you and make the numbers smaller and easier to divide into seconds - and prevent the timer from overflowing more than you need to.

You only need one timer. For other timezone clocks you are just going to change their base.

Your clocks are normally all going to be running from a 32kilohertz crystal and that makes them theoretically accurate to less than a millisecond.

You don't need that for only counting seconds. As long as you aren't going to introduce timing errors, slowing down the counter you actually read and convert to RTC so that it is closer to 1 Hz is a good start. Even better might have been to pick a device with native RTC hardware but if this is the learning exercise that it seems to be then that would be cheating. Using a Real Time Clock equipped device would make this much simpler.

For now have you looked at Microchips application note AN1303? Even Microchip suggests just having an outside device send a Real time clock signal to their PIC over I2C so don't feel bad about having so much trouble.
It could even be another PIC.

Also look at this Video which might help.

This can be done but it takes some work.
 
Last edited:

AlexR

Joined Jan 16, 2008
732
Your clock problems are obviously software related, crystals are simply not that erratic. The most probable cause would be a failure to clear one of the interrupt flags resulting in multiple interrupts for the same event but where the problem lies I've no idea. To put it brutally your code is very difficult to read, it has no structure, you need to make more use of functions and less use of nested "if" statements.
The ISR is particularly bad. The whole idea of servicing an interrupt is to do it as fast as you can then get out so the next interrupt can occur. If an event triggers an interrupt that requires extensive processing then set a flag in the ISR, exit the ISR and do the processing in the main loop.
Also when you are looking for the interrupt source don't over-specify. For example, in your ISR code you have statements such as
Rich (BB code):
//interrupt from Timer1 - 1 sec (Seconds counter)
      if(PIR1.TMR1IF==1&&PIE1.TMR1IE==1){.......
In other words is timer1 overflow interrupt flag is set and TMR1 interrupts are enabled do something. But why are you worried about TMR1 interrupts are enabled? If the an interrupt has occurred and the TMR1F flag is set then TMR1F flag must be cleared regardless of anything else.

The whole ISR could be re-written as
Rich (BB code):
void interrupt()
{
    //interrupt from Timer0 -  0.125sec(led blinker in Edit mode)
    if(INTCON.T0IF)
    {
        t0_isr();
        INTCON.T0IF=0;
    }
    
    //interrupt from Timer1 - 1 sec (Seconds counter)
     else if(PIR1.TMR1IF)
    {
        t1_isr();
        PIR1.TMR1IF=0;
    }
       
     //interrupt from Timer2 - 0.00341797 sec (Display multiplexing)
    else if(TMR2IF)
    {
        t2_isr();
        PIR1.TMR2IF=0;     
     }
}
Which is much easier to read and less likely to result in errors through failure to clear interrupt flags. All the real work will be done in the new functions t?_isr().

Your display routines are very cumbersome and needlessly complicated. Also none of the display work should be done inside the ISR. All that the ISR should do update time and display counters and set flags to tell the main loop that it's time for a display update. The actual selection of LED segments would be better done using an array rather than 10 functions all performing the same task (ie writing a byte to a portB). eg.
Rich (BB code):
char led_segment[] = {0x3F, 0x06, 0x5B, 0x4F, 0x66, 0x6D, 0x7D, 0x07, 0x7F, 0x6F};

//Then for example to bring up the pattern for Segment2 all you need write is

portB = led_segment[Segment2];
 

Markd77

Joined Sep 7, 2009
2,806
A possibly useful thing would be to turn timer1 off, rather than just disabing the interrupt. That way, any time TMR1IF is set you know it's needed. I don't think you can turn timer0 off unfortunately.
 

Thread Starter

ecka333

Joined Oct 1, 2009
76
Thank you all for answers. I found a clock inacurracy problem after some searching. My routine in the main function constantly was enabling TMR1 timer i.e. TMR1 enable bit was set to 1 time after time, even if this bit was set to 1 already. As i puzzled out, TMR1 enable bit setting to 1, if timer is already running, causes timer to restart at zero or similarly.
 

Potato Pudding

Joined Jun 11, 2010
688
Simple enough to put a config inside the main loop and cause resets like that. Amazing how often those types of things can pop up.

Let us know if you have any other problems - and how accurate your clock is. Your display is working now?

So many people are convinced that the interrupts need to shrink, but when you have put that much work into your code I would want you to test it and see if there are any more problems with the code as it is.

I expect there will be but they will probably be about 1% or less. So you might miss 15 minutes a day which is not bad for your first clock attempt.
 

Thread Starter

ecka333

Joined Oct 1, 2009
76
Now i connected 32,768kHz crystal to Timer1 module T1OSO and T1OSI pins. I tried to configure timer to get 1 sec interrupts, but insted o that i get exactly 2 sec interrupts. I suspect, that compiler cant write TMR1H and TMR1L registers. I tried to change these registers values, but interrupt occured exactly after 2 sec, regardless TMR1H and TMR1L values. Maybe something is wrong with the code? Microcontroller - PIC16F873.
Rich (BB code):
// Timer1 initialisation (Seconds counter) Period = 2 sec, Quartz 32768Hz
        T1CON.T1OSCEN = 1;       // Timer1 Oscillator enable
        T1CON.TMR1CS = 1;        // Timer1 Clock Source Select bit - external clock
        T1CON.T1SYNC = 1;        // Do not synchronize external clock input
        TMR1H = 0;               // preset for timer1 MSB register
        TMR1L = 0;               // preset for timer1 LSB register
        T1CON.T1CKPS1 = 0;       // Prescaler= 1
        T1CON.T1CKPS0 = 0;
        PIR1.TMR1IF = 0;         //clear TMR1 interrupt flag
        PIE1.TMR1IE=1;           //TMR1 interrupt enable
        T1CON.TMR1ON = 1;        // enable timer
 

t06afre

Joined May 11, 2009
5,934
Now i connected 32,768kHz crystal to Timer1 module T1OSO and T1OSI pins. I tried to configure timer to get 1 sec interrupts, but insted o that i get exactly 2 sec interrupts. I suspect, that compiler cant write TMR1H and TMR1L registers. I tried to change these registers values, but interrupt occured exactly after 2 sec, regardless TMR1H and TMR1L values. Maybe something is wrong with the code? Microcontroller - PIC16F873.
TMR1 with external osc. at 32.768KHz generates overflow interrupt every 2 seconds. If we set TMR1 to start at 0x8000 (32768), the TMR1 will overflow every 1 second. Setting TMR1 to 0x8000 requires only 0x80 to be written to TMR1H in your ISR. This Does not affect the clock accuracy. Given that TMR1H is set in about 7.7 msesond after TMR1 interrupt. 7.7 msecond is rough calculated about 7700 machine code instructions with a 4 MHz clock frequency. Any setting of TMR1L will affect the accuracy, as it will be updated during your time in the ISR. Also include this as it is good reference but perhaps not in this project
http://ww1.microchip.com/downloads/en/DeviceDoc/01146B.pdf
 
Last edited:

Thread Starter

ecka333

Joined Oct 1, 2009
76
Ok, i understand what you say, t06afre. But i said, that if write to TMR1h register any value 0 or 255 gives absolutely no result. So, if i write
Rich (BB code):
// Timer1 initialisation (Seconds counter) Period = 2 sec, Quartz 32768Hz
        T1CON.T1OSCEN = 1;       // Timer1 Oscillator enable
        T1CON.TMR1CS = 1;        // Timer1 Clock Source Select bit - external clock
        T1CON.T1SYNC = 1;        // Do not synchronize external clock input
        TMR1H = 0b10000000;               // preset for timer1 MSB register
        TMR1L = 0;               // preset for timer1 LSB register
        T1CON.T1CKPS1 = 0;       // Prescaler= 1
        T1CON.T1CKPS0 = 0;
        PIR1.TMR1IF = 0;         //clear TMR1 interrupt flag
        PIE1.TMR1IE=1;           //TMR1 interrupt enable
        T1CON.TMR1ON = 1;        // enable timer
i will get interrupt every second, am i right?
 
Last edited:

t06afre

Joined May 11, 2009
5,934
Timer1 do not have any preset value. The TMR1 Register pair (TMR1H:TMR1L) increments from 0000h to FFFFh and rolls over to 0000h. So whatever you write to the TMR1 Register pair in the Timer1 initialisation function will only have effect once. But if you update TMR1H in your ISR it should work.
 

Thread Starter

ecka333

Joined Oct 1, 2009
76
I dont understand: if i wrote something to TMR1H register, will this register resets on interrupt to 0b00000000? I thought, that if i once wrote particulal value to register, this value stays there till the POR or BOR?
 

Markd77

Joined Sep 7, 2009
2,806
Because it is a timer it is being incremented all the time. When it rolls over to zero that causes the interrupt, not the other way round.
 
Top