ESP32

ESP32, Arduino and Timer/Alerts

Because of completely different architecture, ISR and Timer solutions known from other Arduino compatible platforms, especially AVR/ATmega does not work on ESP32. They don't. At all. If you would like to port any code that uses timers from AVR Arduino to ESP32 Arduino, you would have to rewrite them completely.

However, timers and alarms with espressif ESP32 Arduino core are simple. Much simpler than AVR equivalents! No more writing registers with magical numbers.

The basic code for Arduino ESP32 Timer looks like this:

hw_timer_t * timer = NULL;

void IRAM_ATTR onTimerHandler() {
    //This code will be executed every 1000 ticks, 1ms
}

void setup()
{
    // Prescaler 80 is for 80MHz clock. One tick of the timer is 1us
    timer = timerBegin(0, 80, true); 

    //Set the handler for the timer
    timerAttachInterrupt(timer, &onTimerHandler, true); 

    // How often handler should be triggered? 1000 means every 1000 ticks, 1ms
    timerAlarmWrite(timer, 1000, true); 

    //And enable the timer
    timerAlarmEnable(timer); 
}

void loop() {
    //Here you can do whatever you want
}

You have to bear in mind that:

  1. timer = timerBegin(0, 80, true); If you run ESP32 with a different clock, you have to modify the prescaler. 80 is valid for 80MHz clock
  2. timerAlarmWrite(timer, 1000, true); the last true sets alarm to autorepeat. If you set it false, handler will be triggered only once and you will have to manually set it to enabled inside of the handler
  3. If you want to synchronize data/variable between the ISR/timer handler and the main loop, variable has to be declared as volatile
  4. To make it better, you should also use semaphores for data synchronization. Then, the code would look like this:
portMUX_TYPE mux = portMUX_INITIALIZER_UNLOCKED;
volatile int counter = 0;

void IRAM_ATTR onTimerHandler() {
    portENTER_CRITICAL(&mux);
    //This code will be executed every 1000 ticks, 1ms
    counter++;
    portEXIT_CRITICAL(&mux);
}

void loop() {
    portENTER_CRITICAL(&mux);
    counter = counter + 5;
    portEXIT_CRITICAL(&mux);
}

For more information refer to Espressif ESP32 documentation.

One thought to “ESP32, Arduino and Timer/Alerts”

Leave a Reply

Your email address will not be published.

This site uses Akismet to reduce spam. Learn how your comment data is processed.