LORAWAN_APP_DATA_BUFF_SIZE limit?

Is there a limit for the numer of bytes that can be sent at once? whenever I try a number bigger than 10, there will be some kind of error. Either there will be an error with the TTS server o I will receive the lmh_send fail count message at the terminal. Could you help me please? I’m using the Rak4630 board and the tts server with a whitebelt webhook.
#include <Arduino.h>

#include <bluefruit.h>

#include <LoRaWan-RAK4630.h> //http://librarymanager/All#SX126x

#include <SPI.h>

//Aquí viene la parte de LoRa

// RAK4630 supply two LED

#ifndef LED_BUILTIN

#define LED_BUILTIN 35

#endif

#ifndef LED_BUILTIN2

#define LED_BUILTIN2 36

#endif

// TODO: Set this to your LoRaWAN Region

LoRaMacRegion_t g_CurrentRegion = LORAMAC_REGION_US915;

// Set to true to select Over-The-Air Activation (OTAA), false for Activation By Personalisation (ABP)

bool doOTAA = true;

//OTAA keys !!! KEYS ARE MSB !!!

uint8_t nodeDeviceEUI[8] = {XXXXX};

uint8_t nodeAppEUI[8] = {XXXXXX};

uint8_t nodeAppKey[16] = {XXXXXX};

// ABP keys

uint32_t nodeDevAddr = XXXX;

uint8_t nodeNwsKey[16] = {XXXXXX};

uint8_t nodeAppsKey[16] = {XXXXXX};

#define SCHED_MAX_EVENT_DATA_SIZE APP_TIMER_SCHED_EVENT_DATA_SIZE /**< Maximum size of scheduler events. */

#define SCHED_QUEUE_SIZE 60 /**< Maximum number of events in the scheduler queue. */

#define LORAWAN_DATERATE DR_0 /LoRaMac datarates definition, from DR_0 to DR_5/

#define LORAWAN_TX_POWER TX_POWER_5 /LoRaMac tx power definition, from TX_POWER_0 to TX_POWER_15/

#define JOINREQ_NBTRIALS 3 /**< Number of trials for the join request. */

DeviceClass_t g_CurrentClass = CLASS_A; /* class definition*/

lmh_confirm g_CurrentConfirm = LMH_UNCONFIRMED_MSG; /* confirm/unconfirm packet definition*/

uint8_t gAppPort = LORAWAN_APP_PORT; /* data port*/

/**@brief Structure containing LoRaWan parameters, needed for lmh_init()

*/

static lmh_param_t g_lora_param_init = {

LORAWAN_ADR_ON,

LORAWAN_DATERATE,

LORAWAN_PUBLIC_NETWORK,

JOINREQ_NBTRIALS,

LORAWAN_TX_POWER,

LORAWAN_DUTYCYCLE_OFF

};

// Foward declaration

static void lorawan_has_joined_handler(void);

static void lorawan_join_failed_handler(void);

static void lorawan_rx_handler(lmh_app_data_t *app_data);

static void lorawan_confirm_class_handler(DeviceClass_t Class);

static void send_lora_frame(void);

/**@brief Structure containing LoRaWan callback functions, needed for lmh_init()

*/

static lmh_callback_t g_lora_callbacks = {

BoardGetBatteryLevel,

BoardGetUniqueId,

BoardGetRandomSeed,

lorawan_rx_handler,

lorawan_has_joined_handler,

lorawan_confirm_class_handler,

lorawan_join_failed_handler

};

// Private defination

#define LORAWAN_APP_DATA_BUFF_SIZE 64 /**< buffer size of the data to be transmitted. */

#define LORAWAN_APP_INTERVAL 20000 /**< Defines for user timer, the application data transmission interval. .5s, value in [ms]. */

static uint8_t m_lora_app_data_buffer[LORAWAN_APP_DATA_BUFF_SIZE]; //< Lora user application data buffer.

static lmh_app_data_t m_lora_app_data = {m_lora_app_data_buffer, 0, 0, 0, 0}; //< Lora user application data structure.

TimerEvent_t appTimer;

static uint32_t timers_init(void);

static uint32_t count = 0;

static uint32_t count_fail = 0;

//variables globales

int i;//contador para ciclos for, principalmente el que recorre el arreglo de dispositivos

int j;//variable para los índices del arreglo de bytes que es el mensaje

int largo_mensaje;//esta variable sirve para decirle al send_message cuando detenerse

byte mensaje[12];//Aquí es donde guardamos el contenido del packet que vamos a mandar por LoRa

//Es necesario guardar varios datos de los dispositivos, así que se guardan en esta estructura

int no_dispositivos=2;//El número de dispositivos que vamos a usar

lmh_app_data_t *datitos;/estructura necesaria para recoger los downlinks/

struct BLE_device{

byte MAC[6]; //Aquí se guarda la dirección MAC

unsigned long previous_millis=0UL;

unsigned long interval=1000UL;

byte clave[2]; /* Esta variable es para asignarle una clave que nos ayude a identificar

                    los diferentes dispositivos que estamos usando*/

bool current_bandera=false;

bool previous_bandera=false;

};

void lorawan_has_joined_handler(void)

{

// When we have joined the LoRaWAN network, start a 20-second timer

Serial.println(“OTAA Mode, Network Joined!”);

lmh_error_status ret = lmh_class_request(g_CurrentClass);

if (ret == LMH_SUCCESS)

{

delay(1000);

TimerSetValue(&appTimer, LORAWAN_APP_INTERVAL);

TimerStart(&appTimer);

}

}

/**@brief LoRa function for handling OTAA join failed

*/

static void lorawan_join_failed_handler(void)

{

// If we can’t join the LoRaWAN network, show the error

Serial.println(“OTAA join failed!”);

Serial.println(“Check your EUI’s and Keys’s!”);

Serial.println(“Check if a Gateway is in range!”);

}

/**@brief Function for handling LoRaWan received data from Gateway

  • @param[in] app_data Pointer to rx data

*/

bool compara(byte trama_1[], byte trama_2[], uint8_t ind_1, uint8_t ind_2)

{

bool coincide = true;

for (int i = 0; i < 6 && coincide; i++)

{

if (trama_1[i + ind_1] != trama_2[ind_2 + i])

{

  coincide = false;

}

}

return coincide;

}

void lorawan_rx_handler(lmh_app_data_t *app_data)

{

// When we receive a LoRaWAN Packet from the LoRaWAN Gateway, display it.

// TODO: Ensure that app_data->buffer is null-terminated.

/*se supone que esta función void forma parte de una estructura formada por

todos los callbacks que hay para este código. Están en un arreglo que sirve

como parámetro para el lora_init.

*/

byte down_packet[] = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,

                  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x72, 0x01,

                   0x00, 0x00,0x30, 0x14, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00,

                   0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};



      if(compara(down_packet,app_data->buffer,0,0)==false)

      {Serial.printf("LoRa Packet received on port %d, size:%d, rssi:%d, snr:%d, data:%s\n",

      app_data->port, app_data->buffsize, app_data->rssi, app_data->snr, app_data->buffer);

        Serial.printBuffer(app_data->buffer,'-');

        Serial.println();

      }

}

// Callback Function that is called when the LoRaWAN Class has been changed

void lorawan_confirm_class_handler(DeviceClass_t Class)

{

Serial.printf(“switch to class %c done\n”, “ABC”[Class]);

// Informs the server that switch has occurred ASAP

m_lora_app_data.buffsize = 0;

m_lora_app_data.port = gAppPort;

lmh_send(&m_lora_app_data, g_CurrentConfirm);

}

// This is called when the 20-second timer expires. We send a LoRaWAN Packet.

void send_lora_frame(void)

{

if (lmh_join_status_get() != LMH_SET)

{

// Not joined, try again later

return;

}

m_lora_app_data.port = gAppPort;

memset(m_lora_app_data.buffer, 0, LORAWAN_APP_DATA_BUFF_SIZE);

for(i=0;i<largo_mensaje;i++){

m_lora_app_data.buffer[i]=mensaje[i];

}

m_lora_app_data.buffsize = largo_mensaje;

// Transmit the LoRaWAN Packet

lmh_error_status error = lmh_send(&m_lora_app_data, g_CurrentConfirm);

if (error == LMH_SUCCESS)

{

count++;

Serial.printf("lmh_send ok count %d\n", count);

}

else

{

count_fail++;

Serial.printf("lmh_send fail count %d\n", count_fail);

}

}

/**@brief Function for handling user timerout event.

*/

void tx_lora_periodic_handler(void)

{

// When the 20-second timer has expired, send a LoRaWAN Packet and restart the timer

TimerSetValue(&appTimer, LORAWAN_APP_INTERVAL);

TimerStart(&appTimer);

Serial.println(“Sending frame now…”);

send_lora_frame();

}

/**@brief Function for the Timer initialization.

  • @details Initializes the timer module. This creates and starts application timers.

*/

uint32_t timers_init(void)

{

TimerInit(&appTimer, tx_lora_periodic_handler);

return 0;

}

// At startup, we join the LoRaWAN network, in either OTAA or ABP mode

//Aquí viene la parte del BLE

void cargar_direccion(byte destino[6],byte sexto, byte quinto,byte cuarto,byte tercero, byte segundo,byte primero)

{

     destino[0]=  sexto;

     destino[1]=  quinto;

     destino[2]=  cuarto;

     destino[3]=  tercero;

     destino[4]=  segundo;

     destino[5]=  primero;

}

void configurar_dipositivo(BLE_device dispositivo,byte sexto, byte quinto,byte cuarto,byte tercero, byte segundo,byte primero,byte unidad, char tipo);

void scan_callback(ble_gap_evt_adv_report_t* report)

//variables de la función del callback

{

BLE_device dispositivo;/arreglo de dispositivos BLE integrados/

/*configurar los dispositivos

cargar las direcciones*/

cargar_direccion(dispositivo.MAC,0xDD,0xDD,0xE7,0x3F,0x23,0xAC);//MBM01 unidad 01

// configurar las claves.

//MBM01

//unidad 01

dispositivo.clave[0]=0xA7;

dispositivo.clave[1]=0x01;

//Scouteamos para encontrar payloads de las MAC que están en el arreglo

  if(compara( report->peer_addr.addr,dispositivo.MAC,0,0)==true)

    {

        Serial.printBufferReverse(report->peer_addr.addr, 6, ':');

        Serial.println(" ");

        for(j=0;j<10;j++)

          {

            mensaje[j]=0x00;

          }

        mensaje[j++]=dispositivo.clave[0];

        mensaje[j++]=dispositivo.clave[1];

        largo_mensaje=j;

    }

Bluefruit.Scanner.resume();

}

void setup()

{//setup de Lora

pinMode(LED_BUILTIN, OUTPUT);

digitalWrite(LED_BUILTIN, LOW);

// Initialize LoRa chip.

lora_rak4630_init();

Serial.begin(115200);

while ( !Serial ) delay(10); // for nrf52840 with native usb

Serial.println("=====================================");

Serial.println(“Welcome to RAK4630 LoRaWan!!!”);

if (doOTAA)

{

Serial.println("Type: OTAA");

}

else

{

Serial.println("Type: ABP");

}

switch (g_CurrentRegion)

{

case LORAMAC_REGION_AS923:

  Serial.println("Region: AS923");

  break;

case LORAMAC_REGION_AU915:

  Serial.println("Region: AU915");

  break;

case LORAMAC_REGION_CN470:

  Serial.println("Region: CN470");

  break;

case LORAMAC_REGION_EU433:

  Serial.println("Region: EU433");

  break;

case LORAMAC_REGION_IN865:

  Serial.println("Region: IN865");

  break;

case LORAMAC_REGION_EU868:

  Serial.println("Region: EU868");

  break;

case LORAMAC_REGION_KR920:

  Serial.println("Region: KR920");

  break;

case LORAMAC_REGION_US915:

  Serial.println("Region: US915");

  break;

}

Serial.println("=====================================");

//creat a user timer to send data to server period

uint32_t err_code;

err_code = timers_init();

if (err_code != 0)

{

Serial.printf("timers_init failed - %d\n", err_code);

return;

}

// Setup the EUIs and Keys

if (doOTAA)

{

lmh_setDevEui(nodeDeviceEUI);

lmh_setAppEui(nodeAppEUI);

lmh_setAppKey(nodeAppKey);

}

else

{

lmh_setNwkSKey(nodeNwsKey);

lmh_setAppSKey(nodeAppsKey);

lmh_setDevAddr(nodeDevAddr);

}

// Initialize LoRaWaN

err_code = lmh_init( // lmh_init now takes 3 parameters instead of 5

&g_lora_callbacks,  //  Callbacks

g_lora_param_init,  //  Functions

doOTAA,             //  Set to true for OTAA

g_CurrentClass,     //  Class

g_CurrentRegion     //  Region

);

if (err_code != 0)

{

Serial.printf("lmh_init failed - %d\n", err_code);

return;

}

// Start Join procedure

Serial.println(“Joining LoRaWAN network…”);

lmh_join();

//Setup de BLE

Serial.println(“Bluefruit52 Central Scan Example”);

Serial.println("--------------------------------\n");

// Initialize Bluefruit with maximum connections as Peripheral = 0, Central = 1

// SRAM usage required by SoftDevice will increase dramatically with number of connections

Bluefruit.begin(0, 1);

Bluefruit.setTxPower(4); // Check bluefruit.h for supported values

Bluefruit.setName(“Bluefruit52”);

// Start Central Scan

Bluefruit.setConnLedInterval(250);

Bluefruit.Scanner.setRxCallback(scan_callback);

Bluefruit.Scanner.start(0);

Serial.println(“Scanning …”);

}

void loop()

{

lorawan_rx_handler(datitos);

}

Hi @Jacob_Ortiz_IOTF ,

You can try to increase your DR. In your code, it is zero as shown in this line #define LORAWAN_DATERATE DR_0

DR=0 at US915 will give you best payload length at 11 bytes. That can be lower depending on other possible MAC commands attached to the payload.

Here’s some notes from LoRa Alliance Regional Parameter specification.

1 Like