LoRaWAN not transmitting after deep sleep

Hey
I am trying to build a Lorawan based weather station using a heltec wireless stick lite v3.
Transmitting the sensor values is no problem, but as soon as I try to put the ESP32 into deep sleep, it will not transmit data after waking up once. I do get “unconfirmed uplink sending … Deep sleeping for 10 seconds” in the serial monitor, but i does not transmit anything after deep sleep.
Please note I’m a beginner with LoRa stuff like this. I would really appreciate, if someone would look at my code:

#include “LoRaWan_APP.h”
#include <Wire.h>
#include <Adafruit_Sensor.h>
#include “Adafruit_BME680.h”

/* OTAA para*/
uint8_t devEui[] = {};
uint8_t appEui[] = {};
uint8_t appKey[] = {};

/* ABP para*/
uint8_t nwkSKey[] = {};
uint8_t appSKey[] = {};
uint32_t devAddr = ( uint32_t );

Adafruit_BME680 bme;

#define TIME_TO_SLEEP 10 /* Duration ESP32 will go to sleep (seconds) /

/LoraWan channelsmask, default channels 0-7/
uint16_t userChannelsMask[6]={ 0x00FF,0x0000,0x0000,0x0000,0x0000,0x0000 };

/LoraWan region, select in arduino IDE tools/
LoRaMacRegion_t loraWanRegion = ACTIVE_REGION;

/LoraWan Class, Class A and Class C are supported/
DeviceClass_t loraWanClass = CLASS_A;

/the application data transmission duty cycle. value in [ms]./
uint32_t appTxDutyCycle = 10*1000;

#define LORA_SPREADING_FACTOR 12// [SF7…SF12]

/OTAA or ABP/
bool overTheAirActivation = false;

/ADR enable/
bool loraWanAdr = true;

/* Indicates if the node is sending confirmed or unconfirmed messages */
bool isTxConfirmed = false;

/* Application port */
uint8_t appPort = 2;

/*!

  • Number of trials to transmit the frame, if the LoRaMAC layer did not
  • receive an acknowledgment. The MAC performs a datarate adaptation,
  • according to the LoRaWAN Specification V1.0.2, chapter 18.4, according
  • to the following table:
  • Transmission nb | Data Rate
  • ----------------|-----------
  • 1 (first) | DR
  • 2 | DR
  • 3 | max(DR-1,0)
  • 4 | max(DR-1,0)
  • 5 | max(DR-2,0)
  • 6 | max(DR-2,0)
  • 7 | max(DR-3,0)
  • 8 | max(DR-3,0)
  • Note, that if NbTrials is set to 1 or 2, the MAC will not decrease
  • the datarate, in case the LoRaMAC layer did not receive an acknowledgment
    */
    uint8_t confirmedNbTrials = 10;

float temperature;
float humidity;
float pressure;
float gasResistance;

/* Prepares the payload of the frame */
static void prepareTxFrame( uint8_t port )
{
/*appData size is LORAWAN_APP_DATA_MAX_SIZE which is defined in “commissioning.h”.
*appDataSize max value is LORAWAN_APP_DATA_MAX_SIZE.
*if enabled AT, don’t modify LORAWAN_APP_DATA_MAX_SIZE, it may cause system hanging or failure.
*if disabled AT, LORAWAN_APP_DATA_MAX_SIZE can be modified, the max value is reference to lorawan region and SF.
*for example, if use REGION_CN470,
*the max value for different DR can be found in MaxPayloadOfDatarateCN470 refer to DataratesCN470 and BandwidthsCN470 in “RegionCN470.h”.
*/

/* Read sensor data */

getBME680Readings();

/* Convert float values to integers for payload */
int int_temp = temperature * 100; // remove decimal point
int int_hum = humidity * 10; // remove decimal point
int int_pressure = pressure ;
int int_gas_resistance = gasResistance; // gas resistance is already an integer

/* Update appData with sensor data */
appDataSize = 8;
appData[0] = int_temp >> 8; // Store the high byte of int_temp in appData[0]
appData[1] = int_temp; // Store the low byte of int_temp in appData[1]
appData[2] = int_hum >> 8; // Store the high byte of int_hum in appData[2]
appData[3] = int_hum; // Store the low byte of int_hum in appData[3]
appData[4] = int_pressure >> 8; // Store the high byte of int_pressure in appData[4]
appData[5] = int_pressure; // Store the low byte of int_pressure in appData[5]
appData[6] = int_gas_resistance >> 8; // Store the high byte of int_gas in appData[6]
appData[7] = int_gas_resistance; // Store the low byte of int_gas in appData[7]
}
//if true, next uplink will add MOTE_MAC_DEVICE_TIME_REQ

void setup() {
Serial.begin(115200);
Mcu.begin();
Serial.print(“setup”);

Wire.begin(46,45);

if (!bme.begin()) {
Serial.println(F(“Could not find a valid BME680 sensor, check wiring!”));
while (1);
}

bme.setTemperatureOversampling(BME680_OS_8X);
bme.setHumidityOversampling(BME680_OS_2X);
bme.setPressureOversampling(BME680_OS_4X);
bme.setIIRFilterSize(BME680_FILTER_SIZE_3);
bme.setGasHeater(320, 150); // 320*C for 150 ms

deviceState = DEVICE_STATE_INIT;
}

void loop()

{
switch( deviceState )
{
case DEVICE_STATE_INIT:
{
#if(LORAWAN_DEVEUI_AUTO)
LoRaWAN.generateDeveuiByChipID();
#endif
LoRaWAN.init(loraWanClass,loraWanRegion);
break;
}
case DEVICE_STATE_JOIN:
{
LoRaWAN.join();
break;
}
case DEVICE_STATE_SEND:
{
resetLoRaWAN();
prepareTxFrame( appPort );
LoRaWAN.send();
deviceState = DEVICE_STATE_CYCLE;

  break;
}
case DEVICE_STATE_CYCLE:
{
   //Schedule next packet transmission
  txDutyCycleTime = appTxDutyCycle + randr( -APP_TX_DUTYCYCLE_RND, APP_TX_DUTYCYCLE_RND );
  LoRaWAN.cycle(txDutyCycleTime);
  deviceState = DEVICE_STATE_SLEEP;
  break;
}
case DEVICE_STATE_SLEEP:
{
  LoRaWAN.sleep(loraWanClass);
  delay(3000);
  goToSleep(TIME_TO_SLEEP);
  break;
}
default:
{
  deviceState = DEVICE_STATE_INIT;
  break;
}

}
}
void getBME680Readings(){
// Tell BME680 to begin measurement.
unsigned long endTime = bme.beginReading();
if (endTime == 0) {
Serial.println(F(“Failed to begin reading :(”));
return;
}
if (!bme.endReading()) {
Serial.println(F(“Failed to complete reading :(”));
return;
}
temperature = bme.temperature;
pressure = bme.pressure/100;
humidity = bme.humidity;
gasResistance = bme.gas_resistance / 1000.0;
}

void goToSleep(int sleepSeconds) {
Radio.Sleep( );

delay(100);
VextOFF();

// // Heltec V2 // Heltec V3
pinMode(17, INPUT); // 4 SDA // 17 OLED SDA
pinMode( 9,INPUT); // 5 LORA SCK // 9 LORA
pinMode(14,INPUT); // 14 RST 1278 // 12 LORA RST
pinMode(18, INPUT); // 15 SCL // 18 OLED SCL
pinMode(21,INPUT); // 16 OLED RST // 21 OLED RST
//pinMode(17,INPUT); // 17 HS1_DATA5 //
pinMode( 8,INPUT); // 18 LORA NSS // 8 LORA NSS
pinMode(11,INPUT); // 19 MISO // 11 LORA MISO
pinMode(12,INPUT); // 26 DIO026 // 12 DIO1 (LORA)
pinMode(10,INPUT); // 27 MOSI // 10 LORA MOSI

Serial.printf(“Deep sleeping for %d seconds\n”, sleepSeconds);
esp_sleep_enable_timer_wakeup(sleepSeconds * 1000000);
Serial.flush();
esp_deep_sleep_start();

Serial.println(“This will never be printed”);
}

void VextON(void)
{
pinMode(Vext,OUTPUT);
digitalWrite(Vext, LOW);
}

void VextOFF(void) //Vext default OFF
{
pinMode(Vext,OUTPUT);
digitalWrite(Vext, HIGH);
}

void resetLoRaWAN() {
// Reset LoRaWAN parameters
LoRaWAN.init(loraWanClass, loraWanRegion);
if (overTheAirActivation) {
LoRaWAN.join();
}
// Other LoRaWAN configuration if needed
}

Please have a look at RadioLib. You should be able to copy-paste in your BME680 readings, but you will need to create an uint8_t appData[8]; - then you can also use the function prepareTxFrame().

Using RadioLib’s saveSession(), you should be able to safely go into deepsleep without any troubles!

@janiss0202 Have you solved the problem?

If not - some hints:

  1. check the library version you are using, latest is the 1.0.0 (NOT the 0.0.7 - as I have used before I have seen it… :smile:)

  2. take the LoRaWAN sample code from Heltec - it is working now fine with sleeping mode - no needs more to make additional steps with PIN settings and ESP32 sleep command…
    Do not use (even not for testing) too short TIME_TO_SLEEP , for testing no less 60 seconds
    (also check the TTN fair to use policy…)

  1. if this code is working as expected (as you can check in TTN console) - then add your sensor request code in “case DEVICE_STATE_SEND” block before prepareTxFrame()

WSL V3 Stick is now working fine (more or less - ESP32 limitations) - will send values and go after about 6 seconds into deep sleep. Then will wakeup and send new values again.

I had before also different problems with sleeping mode - but after changing to actual lib 1.0.0 all was working.

How did you install version 1.0.0?
Board manager only shows 0.0.7 as the latest version.

Hi,

yes, same issue I had here…

The Board Manager URL is a new now - for new version.
https://github.com/Heltec-Aaron-Lee/WiFi_Kit_series/releases/download/1.0.0/package_heltec_esp32_index.json

Replace it in preferences - and new library will be loaded.

I also do not understand why a new URL for new version is needed…:thinking: