Go Down

Topic: Strange behavior of Timer2 interrupt (Read 638 times) previous topic - next topic


Hi everybody,

I am new to this forum so I take the occasion to say my greetings to all of you.
I am spending some time to play with Arduino and I have my first issue to understand a strange way of working of my code.
Here is the code

Code: [Select]

#include <avr/io.h>
#include <avr/interrupt.h>
#include <WProgram.h>

volatile unsigned char tic_counter = 0;
volatile unsigned char led_toggle = 1;

// interrupt service routine that wraps a user defined function supplied by attachInterrupt
    if (tic_counter++ == 61)
        tic_counter = 0;
        PORTB = led_toggle ? 0xFF : 0x00;
        led_toggle = !led_toggle;


// Cofiguration for Timer2
// 16 MHz / 1024 = 15625 Hz (prescaler 1024)
// 15625 Hz / 256 = 61.035 Hz (timer2 resolution)
void tic_setup(void)
    // Disable interrupts while setting registers

    // Use internal clock - external clock not used in Arduino
    ASSR &= ~(1<<AS2);

    // 17.11.1 TCCR2A - Timer/Counter Control Register A
    //   Bit    7      6      5      4      3      2      1      0
    // (0xB0) COM2A1 COM2A0 COM2B1 COM2B0   -      -    WGM21 WGM20
    //          0      0      0      0      0      0      0      0
    // Compare output mode (OC2A): normal port operation
    // Compare output mode (OC2B): normal port operation
    // Waveform generation mode: normal
    TCCR2A = 0x00;
    // TCCR2B - Timer/Counter Control Register B
    //   Bit    7     6     5     4     3     2     1    0
    // (0xB1) FOC2A FOC2B   -     -   WGM22  CS22  CS21 CS20
    //          0     0     0     0     0     1     1    1
    // Output compare A & B: 0
    // Prescaler: clkT2S/1024 (From prescaler)
    TCCR2B = 0x07;
    // TCNT2 - Timer/Counter Register
    // When normal mode is selected int TCCR2A and TCCR2B, Timer2 counts
    // upwards
    TCNT2 = 0x00;
    // TIMSK2 - Timer/Counter2 Interrupt Mask Register
    // Bit      7     6     5     4     3     2     1     0
    // (0x70)   -     -     -     -     -  OCIE2B OCIE2A TOIE2
    //          0     0     0     0     0     0     0     1
    // Output Compare A & B Interr. Enable: 0
    // Overflow Interrupt Enable: 1
    TIMSK2 = 0x01;
    // Enable global interrupts
int main()
    DDRB = 0xFF; // set PORTB for output
    PORTB = 0xFF;

    Serial.println("Initializing Timer Interrupt");
    while(1) ;   // <=== HERE IS THE PROBLEM!

Basically I configure Timer2 to trigger an interrupt with the frequency of ~61Hz.

The strange thing is on the infinite loop at the end of the file: if it is present, everything works fine, if not, then the interrupts are not triggered.
I would have expected that the ints were triggered even without the infinite loop.

I am using Linux and I am building using the command line.

Thanks in advance for any possible feedback.




Feb 20, 2011, 11:51 pm Last Edit: Feb 21, 2011, 12:54 am by shelleycat Reason: 1
The code starts main, and it runs through main.  Then it returns from main to ????

You don't want it to exit main, its got to stay under execution control there.  There is no operating system, the processor is executing what instructions you gave it.

Edit:  I've loaded your sketch in the ide, then run avr-objdump -d on the .elf file.
main gets called, and at the end of main it transfers control to exit, where it disables interrupts then goes into a continuous loop. However, I cannot see how it gets out of main - it looks like it should stay the end of main forever.


Thank you very much!!!
You are completely right, if you do not put an infinite loop at the end of main() the execution terminates. I should not code by night...
BTW, I wonder about the power consumption when the infinite loop is executing, it should be a kind of 'busy form of waiting'.
Is there any instruction in this case to, let's say, put the execution to 'sleep', without consuming any cpu resources, hence running the code only when the interrupts are triggered?

Thanks again.



Yes, but you are way out of arduino sketches then.  See the Atmegs spec and sleep mode, and various ways to wake up.  It might be simpler to run at a slower clock rate/lower voltage if you are worried about  power.

Go Up

Please enter a valid email to subscribe

Confirm your email address

We need to confirm your email address.
To complete the subscription, please click the link in the email we just sent you.

Thank you for subscribing!

via Egeo 16
Torino, 10131