LowPower does not work for me in Lora

Hi.
I want to use only the LoRa layer to send temperature data to an ESP32-Lora that receives and publishes it in my local MQTT broker.
I have adapted the LoRaSender sketch (https://github.com/HelTecAutomation/ASR650x-Arduino/tree/master/libraries/LoRa/examples/LoRaBasic/LoRaSender) and it works perfectly.
My problem is that I cannot operate the lowPower. I have included the sample sketch code LowPower_WakeUpByTimer (https://github.com/HelTecAutomation/ASR650x-Arduino/tree/master/libraries/Basics/examples/LowPower_WakeUpByTimer)
but it does not work. LowPowerHandler () is not running.
Can you help me?.
Thank you

“not running”. Please elaborate. It will run multiple (6) times before it finally sleeps, by design. It keeps running beyond six times?

Before trying to implement the lowPower mode, the time between transmissions was managed with delay () and works perfectly, but with a high consumption of 12 mA continuous.
When using the code of “LowPower_WakeUpByTimer” and commenting on the delay () line in my sketch, the call to function “LowPowerHandler ()” has no effect and the node transmits continuously every second approximately, never enters in deepsleep.
I have tried the sketch “LowPower_WakeUpByTimer” and it works perfectly, it goes into deep sleep and I measure a consumption of only 3.5uA. The problem arises when mixing the LowPower code with the LoRaSender code.
Thanks for your help and sorry for the google translate english.

I can’t get the lowpower mode to work. I put the test sketch I’ve tried. Where this error?
#include “LoRaWan_APP.h”
#include “Arduino.h”
#ifndef LoraWan_RGB
#define LoraWan_RGB 0
#endif
#define RF_FREQUENCY 868000000 // Hz
#define TX_OUTPUT_POWER 14 // dBm
#define LORA_BANDWIDTH 0
#define LORA_SPREADING_FACTOR 7 // [SF7…SF12]
#define LORA_CODINGRATE 1 // [1: 4/5
#define LORA_PREAMBLE_LENGTH 8 // Same for Tx and Rx
#define LORA_SYMBOL_TIMEOUT 0 // Symbols
#define LORA_FIX_LENGTH_PAYLOAD_ON false
#define LORA_IQ_INVERSION_ON false

#define RX_TIMEOUT_VALUE 1000
#define BUFFER_SIZE 30 // Define the payload size here
char txpacket[BUFFER_SIZE];
static RadioEvents_t RadioEvents;
int16_t txNumber;
int16_t rssi,rxSize;

#define timetosleep 25000 //tiempo durmiendo
#define timetowake 5000 //tiempo despierto
static TimerEvent_t sleep;
static TimerEvent_t wakeUp;
uint8_t lowpower=1;

void onSleep()
{
Serial.printf(“into lowpower mode, %d ms later wake up.\r\n”,timetowake);
lowpower=1;
//timetosleep ms later wake up;
TimerSetValue( &wakeUp, timetowake );
TimerStart( &wakeUp );
}
void onWakeUp()
{
Serial.printf(“wake up, %d ms later into lowpower mode.\r\n”,timetosleep);
lowpower=0;
//timetosleep ms later into lowpower mode;
TimerSetValue( &sleep, timetosleep );
TimerStart( &sleep );
}

void setup() {
Serial.begin(115200);
boardInitMcu();
txNumber=0;
rssi=0;

Radio.Init( &RadioEvents );
Radio.SetChannel( RF_FREQUENCY );
Radio.SetTxConfig( MODEM_LORA, TX_OUTPUT_POWER, 0, LORA_BANDWIDTH,
                               LORA_SPREADING_FACTOR, LORA_CODINGRATE,
                               LORA_PREAMBLE_LENGTH, LORA_FIX_LENGTH_PAYLOAD_ON,
                               true, 0, 0, LORA_IQ_INVERSION_ON, 3000 ); 

Radio.Sleep( );

TimerInit( &sleep, onSleep );
TimerInit( &wakeUp, onWakeUp );
onSleep();
}

void loop()
{
if(lowpower){
//note that lowPowerHandler() run six times the mcu into lowpower mode;
lowPowerHandler();
}

//delay(1000);
txNumber++;
sprintf(txpacket,"%s","Hello world number");  //start a package
sprintf(txpacket+strlen(txpacket),"%d",txNumber); //add to the end of package
	   
turnOnRGB(COLOR_SEND,0); //change rgb color

Serial.printf("\r\nsending packet \"%s\" , length %d\r\n",txpacket, strlen(txpacket));

Radio.Send( (uint8_t *)txpacket, strlen(txpacket) ); //send the package out	

}

I suspect you’re waking up out of LowPower due to the code after it – it does say it needs to run 6 times, but every loop you’re doing stuff that wakes it up. It was posited and proven in another thread (by @johnarnoldbrown ) that doing printf’s would prevent sleep.

Can you try an else clause on that if (lowpower) case and put the txNumber++ etc into that else clause so you only do that work if you’re not trying to sleep?

Other than that I’m not sure if the lowPowerHander() was part of the LoRaWAN stack e.g. not pure LoRa, but I’ll wait until you try the else clause first.

¡¡¡At last it WORKS!!!. The problem is what you indicate. Now it works as expected. Thank you very much bwooce.
But something happens with consumption in Lowpower. Let’s see if you can help me.
The loop () function of my sketch is this:

void loop()
{
if(lowpower){
digitalWrite(Vext,HIGH);//Corta alimentaciĂłn sensores por pin Vext
lowPowerHandler( );
}

else{
PreparaPayload();
turnOnRGB(COLOR_SEND,0);
Serial.printf("\r\nsending packet “%s” , length %d\r\n",txpacket, strlen(txpacket));
Radio.Send( (uint8_t *)txpacket, strlen(txpacket) ); //send the package out
turnOffRGB(); //led off
}
}

It works perfectly, but there are some differences in consumption. When the sketch starts, in the first pass through “if (lowpower)” i get a consumption of 3uA. To achieve this low consumption it was necessary to add the “digitalWrite (Vext, HIGH)” line before calling the lowPowerHandler () function, which alone only reduces consumption to 1.2mA.
After going through the first time “else{” and making the first transmission, the rest of calls to lowPowerHandler () leave a consumption of 70uA.
It seems that after the first broadcast of the radio something active remains and lowPowerHandler () fails to reduce consumption to the desired 3uA.
Any ideas?
Once again, thank you very much.

Maybe a bit late but would a Radio.Sleep() after sending help?

Hi.
Try this instruction, but the radio appears to be disabled as the LoRa gateway is not receiving transmissions.

I continue to be unable to maintain lowpoweer mode at 3.5uA throughout my sketch. My node has run on 2 alkaline AA batteries for 4 months, with periods of deep sleep (timetowake) of 5 minutes and 1 second awake (timetosleep). It is a short time, due to the “phantom” consumption after the first pass after startup by the lowPowerHandler () function. In this first step through this function, I achieve the desired consumption of around 3 uA throughout the time (timetowake) of deep sleep, but after the first Lora transmission, the following states of deep sleep have a consumption that varies between 51uA and 1.2mA.

My sketch finally has this structure:

……
void loop()
{
if(lowpower){
digitalWrite(Vext,HIGH);//Corta alimentaciĂłn sensores por pin Vext
lowPowerHandler( );
}
}

void onSleep()
{
lowpower=1;
//timetosleep ms later wake up;
TimerSetValue( &wakeUp, timetowake );
TimerStart( &wakeUp );
}
void onWakeUp()
{
lowpower=0;
//timetosleep ms later into lowpower mode;
digitalWrite(Vext,LOW);
PreparaPayload(); //sensor reading and payload (txpacket) preparation
turnOnRGB(COLOR_SEND,0);
Serial.printf("\r\nsending packet “%s” , length %d\r\n",txpacket, strlen(txpacket));
Radio.Send( (uint8_t *)txpacket, strlen(txpacket) ); //send the package out
turnOffRGB(); //led off
TimerSetValue( &sleep, timetosleep );
TimerStart( &sleep );
}

Any suggestion?. Thanks

Hey @JJ1 try removing (or #ifdef’ing with a macro) all the Serial stuff for a start. You don’t want to be doing that when embedded; but you want it for debugging I’m sure. I’ve not measured it, but it can’t help and it’s relatively easy to conditionally compile out.

Also, the two timers? One is for the wakeup after going to lowpower but why do you need one to send yourself to sleep? I’ll admit to not having used the CubeCell in Lora-only mode, so educate me :slight_smile: - is it to sleep after the Send completes?

Other than that…do you have any other pins connected? Parasitic draw from the signal pins after Vext gets turned off is a thing, so you can take them LOW (?) to prevent that from memory.

Hi @bwooce.
As I read in the forum the effect of series outputs on low power, I eliminated them in my tests and everything remained the same.

The reason for the two timers, I don’t know. I just took the example “LowPower_WakeUpByTimer” (https://github.com/HelTecAutomation/ASR650x-Arduino/tree/master/libraries/Basics/examples/LowPower_WakeUpByTimer ) which gave me a great low consumption of 3uA and I adapted it to my needs with LoRa (thanks to your help).

If I have other things connected, but I get the same behavior with them connected and not connected.

Hi I had the same issue.
I got it to work by putting in a delay before the Radio.Sleep()

all working now :slight_smile:

so
else{
PreparaPayload();
turnOnRGB(COLOR_SEND,0);
Serial.printf("\r\nsending packet “%s” , length %d\r\n",txpacket, strlen(txpacket));
Radio.Send( (uint8_t *)txpacket, strlen(txpacket) ); //send the package out
turnOffRGB(); //led off
delay(1000);
Radio.Sleep()

}
}

1 Like

Great :slightly_smiling_face: The key was the delay before Radio.Sleep ()
Now I have a true deep sleep of only 2.5uA and an estimated battery life of almost 3 years.
Thank you very much.

2 Likes

One question - do you send synch or asynch? if Asynch I would try to put the Radio.Sleep(); in both:
void OnTxDone( void );
void OnTxTimeout( void );

Just to be sure the radio is switched off AFTER the data had been send.

1 Like

I managed to get 11mA when awake and 1.5mA when sleeping. I’m trying to use you technique for my INA219 sensor but get some errors. Can you paste whole final version of the script please.