RAK4631 goes to deep sleep, but it doesn´t wake up

Please include the following information, in order for us to help you as effectively as possible.

  • What product do you wish to discuss? RAK4631

  • What firmware are you using? VSCode/PlatformIO/Arduino BSP

  • Computer OS? Windows

  • What Computer OS version? Windows 11

  • How often does the problem happen? Always

  • How can we replicate the problem? Yes

  • Provide source code if custom firmware is used or link to example if RAKwireless example code is used.

I have a code to make RAK4631 goes to “deep sleep mode”. The problem is that isn´t make the RAK4631 wakeup.

Could you help me?

Regards,

Claudio

#include <nrf.h>  // Direct access to nRF52840 hardware registers

#define WAKEUP_INTERVAL_SECONDS 10  // Time to wake up in seconds

void setup() {
  // Start the serial port for debugging
  Serial.begin(115200);
  while (!Serial);  // Wait for serial to be ready

  Serial.println("RAK4631 entering deep sleep for 10 seconds...");

  // Configure RTC to wake up after the specified time
  configureRTCWakeup(WAKEUP_INTERVAL_SECONDS);

  // Enter deep sleep (System OFF mode)
  enterDeepSleep();
}

void loop() {
  // This runs after waking up
  Serial.println("Woke up from deep sleep!");

  // Optional: delay to observe wake-up before going to sleep again
  delay(2000);

  // Enter deep sleep again
  Serial.println("Entering deep sleep again...");
  configureRTCWakeup(WAKEUP_INTERVAL_SECONDS);
  enterDeepSleep();
}

// Function to configure RTC for timed wakeup
void configureRTCWakeup(uint32_t seconds) {
  // Start the Low-Frequency Clock (LFCLK) required for RTC
  NRF_CLOCK->LFCLKSRC = CLOCK_LFCLKSRC_SRC_Synth;  // Use synthesized or external crystal oscillator
  NRF_CLOCK->TASKS_LFCLKSTART = 1;  // Start LFCLK
  while (NRF_CLOCK->EVENTS_LFCLKSTARTED == 0);  // Wait until LFCLK starts
  NRF_CLOCK->EVENTS_LFCLKSTARTED = 0;  // Clear the event

  // Set up RTC1 to count down to the specified number of seconds
  NRF_RTC1->PRESCALER = 0;  // Prescaler 0 gives 1 tick per 30.5 µs (32.768 kHz)
  NRF_RTC1->CC[0] = seconds * 32768;  // Set the compare register to the number of ticks (seconds * 32,768)
  NRF_RTC1->EVENTS_COMPARE[0] = 0;  // Clear the compare event
  NRF_RTC1->INTENSET = RTC_INTENSET_COMPARE0_Enabled << RTC_INTENSET_COMPARE0_Pos;  // Enable Compare 0 interrupt

  // Enable the RTC interrupt in the NVIC (Interrupt Controller)
  NVIC_EnableIRQ(RTC1_IRQn);

  // Start the RTC
  NRF_RTC1->TASKS_START = 1;
}

// Function to enter System OFF (deep sleep)
void enterDeepSleep() {
  // Enter System OFF mode (deep sleep mode)
  NRF_POWER->SYSTEMOFF = 1;

  // Code below won't execute until wake-up occurs
}

// RTC interrupt handler
extern "C" void RTC1_IRQHandler(void) {
  // Check if the compare event occurred
  if (NRF_RTC1->EVENTS_COMPARE[0]) {
    // Clear the compare event
    NRF_RTC1->EVENTS_COMPARE[0] = 0;
    // Stop the RTC
    NRF_RTC1->TASKS_STOP = 1;
  }
}

I am not sure if you can use these low level functions.
The Arduino BSP is built using FreeRTOS and I am sure somewhere inside there is the sleep and power saving modes handled.
You might create conflicts with FreeRTOS.

But not 100% sure, I never tried to use these functions.