espressif / esp-idf

Espressif IoT Development Framework. Official development framework for Espressif SoCs.
Apache License 2.0
13.6k stars 7.27k forks source link

ULP RISC-V Interrupts/Timers (IDFGH-13930) #14768

Open michaelboeding opened 19 hours ago

michaelboeding commented 19 hours ago

Answers checklist.

General issue report

I’m working on using the ESP32's ULP (Ultra-Low Power) mode for activity tracking with an accelerometer, and I’m trying to figure out the best way to implement this.

Here’s what I want to achieve:

Mark Activity as Active/Inactive: I need to monitor each minute. If a wake-up interrupt occurs from the accelerometer, I mark that minute as "active." If no interrupt occurs, it should be marked as "inactive."

Timer for Inactive Periods: I want a timer running in the ULP that resets every minute, marking the period as "inactive" if there’s no wake-up interrupt.

Main Application Sync: When the main app wakes up, I want to back-calculate activity based on the ULP's runtime and sync it with a Unix timestamp to create accurate time-stamped data.

Question:

How can I set up the ULP to trigger at regular intervals (like every minute) for marking inactivity, while still allowing GPIO interrupts for activity detection? What’s the best way to handle the timing and interrupts together in this scenario? I would rather not be constantly polling but just have it act like a RTC timer to wake up the ULP if possible. And if a wake up interrupt occurs reset the timer.

Another option may just be a way to have the interrupts setup and then have a software interrupt fired from the ULP at a set interval that I can track but it doesn't seem consistent when I tried to do this. I was never able to get the software interrupt in the ULP to say fire every 60 seconds. So is there a way to get the run time clock in the ULP?

sudeep-mohanty commented 14 hours ago

Hi @michaelboeding, May I know which target are you using? Is it the ESP32 or the ESP32-S2/S3, which support the ULP RISC-V core in addition to the ULP FSM core?

The ULP cores do not have a free-running timer like an RTC timer to keep track of time. However, the ULP can be programmed to wakeup every minute (or fractions of a minute) to check on the active/inactive status. If you are using a target with the ULP RISC-V core, you could also use the ulp_riscv_delay_cycles() to create a 60 second wait period where the ULP does nothing but waits either for the accelerometer IO interrupt or a timeout to happen.

michaelboeding commented 10 hours ago

Hey @sudeep-mohanty first off thanks for the response I really appreciate it.

I'm currently using the ESP32-S3 and the RISC-V ULP core. I had attempted to setup the gpio interrupts and then created a while loop with a delay using ulp_riscv_delay_cycles (and have that trigger a software interrupt) but the timing was all off it didn't seem to be happening at the interval I wanted.

Also in addition to the above is there a way to keep the current system time or read it in the ULP? I need to know the Unix timestamp in order to back calculate when I wake up fully from deep sleep? An example of something like this where it's time based on a set interval like a minute would really be helpful.

Just to summarize:

  1. Need GPIO interrupts
  2. Need a timer wakeup (the delay works) on a set interval in the ULP
  3. Need a way to keep track of the system time so I know when the events occurred and can back calculate once my esp is woken from deep sleep.

Thanks!