Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
main.cpp
- Committer:
- amolkulk
- Date:
- 2020-07-02
- Revision:
- 20:d29e04f0a066
- Parent:
- 19:29a983e47ef3
File content as of revision 20:d29e04f0a066:
#include "mbed.h"
#include "main.h"
#include "sx1276-hal.h"
/* Set this flag to '1' to display debug messages on the console */
#define DEBUG_MESSAGE 1
/* Set this flag to '1' to use the LoRa modulation or to '0' to use FSK modulation */
#define USE_MODEM_LORA 1
#define USE_MODEM_FSK !USE_MODEM_LORA
#define RF_FREQUENCY 868000000 // Hz
#define TX_OUTPUT_POWER 14 // 14 dBm
#if USE_MODEM_LORA == 1
#define LORA_BANDWIDTH 2 // [0: 125 kHz,
// 1: 250 kHz,
// 2: 500 kHz,
// 3: Reserved]
#define LORA_SPREADING_FACTOR 7 // [SF7..SF12]
#define LORA_CODINGRATE 1 // [1: 4/5,
// 2: 4/6,
// 3: 4/7,
// 4: 4/8]
#define LORA_PREAMBLE_LENGTH 8 // Same for Tx and Rx
#define LORA_SYMBOL_TIMEOUT 5 // Symbols
#define LORA_FIX_LENGTH_PAYLOAD_ON false
#define LORA_FHSS_ENABLED false
#define LORA_NB_SYMB_HOP 4
#define LORA_IQ_INVERSION_ON false
#define LORA_CRC_ENABLED true
#elif USE_MODEM_FSK == 1
#define FSK_FDEV 25000 // Hz
#define FSK_DATARATE 19200 // bps
#define FSK_BANDWIDTH 50000 // Hz
#define FSK_AFC_BANDWIDTH 83333 // Hz
#define FSK_PREAMBLE_LENGTH 5 // Same for Tx and Rx
#define FSK_FIX_LENGTH_PAYLOAD_ON false
#define FSK_CRC_ENABLED true
#else
#error "Please define a modem in the compiler options."
#endif
#define RX_TIMEOUT_VALUE 3500 // in ms
#define BUFFER_SIZE 32 // Define the payload size here
#define SEC_TO_MSEC (1000)
#if( defined ( TARGET_KL25Z ) || defined ( TARGET_LPC11U6X ) )
DigitalOut led( LED2 );
#else
DigitalOut led( LED1 );
#endif
/*
* Global variables declarations
*/
typedef enum
{
LOWPOWER = 0,
IDLE,
RX,
RX_TIMEOUT,
RX_ERROR,
TX,
TX_TIMEOUT,
CAD,
CAD_DONE
}AppStates_t;
volatile AppStates_t State = LOWPOWER;
/*!
* Radio events function pointer
*/
static RadioEvents_t RadioEvents;
RawSerial pc(USBTX, USBRX);
/*
* Global variables declarations
*/
SX1276MB1xAS Radio( NULL );
const uint8_t PingMsg[] = "PING";
const uint8_t PongMsg[] = "PONG";
uint16_t BufferSize = BUFFER_SIZE;
uint8_t Buffer[BUFFER_SIZE];
int16_t RssiValue = 0.0;
int8_t SnrValue = 0.0;
int main( void )
{
uint8_t i;
bool isMaster = true;
uint32_t rx_count = 0;
uint32_t tx_count = 0;
while(1){
debug("Press 1 to start, isMaster(%d)\r\n", isMaster);
char c = pc.getc();
if(c == '1'){
break;
}
}
debug( "\n\n\r SX1276 Ping Pong Demo Application \n\n\r" );
// Initialize Radio driver
RadioEvents.TxDone = OnTxDone;
RadioEvents.RxDone = OnRxDone;
RadioEvents.RxError = OnRxError;
RadioEvents.TxTimeout = OnTxTimeout;
RadioEvents.RxTimeout = OnRxTimeout;
Radio.Init( &RadioEvents );
// verify the connection with the board
while( Radio.Read( REG_VERSION ) == 0x00 )
{
debug( "Radio could not be detected!\n\r", NULL );
wait( 1 );
}
debug_if( ( DEBUG_MESSAGE & ( Radio.DetectBoardType( ) == SX1276MB1LAS ) ), "\n\r > Board Type: SX1276MB1LAS < \n\r" );
debug_if( ( DEBUG_MESSAGE & ( Radio.DetectBoardType( ) == SX1276MB1MAS ) ), "\n\r > Board Type: SX1276MB1MAS < \n\r" );
Radio.SetChannel( RF_FREQUENCY );
#if USE_MODEM_LORA == 1
debug_if( LORA_FHSS_ENABLED, "\n\n\r > LORA FHSS Mode < \n\n\r" );
debug_if( !LORA_FHSS_ENABLED, "\n\n\r > LORA Mode < \n\n\r" );
Radio.SetTxConfig( MODEM_LORA, TX_OUTPUT_POWER, 0, LORA_BANDWIDTH,
LORA_SPREADING_FACTOR, LORA_CODINGRATE,
LORA_PREAMBLE_LENGTH, LORA_FIX_LENGTH_PAYLOAD_ON,
LORA_CRC_ENABLED, LORA_FHSS_ENABLED, LORA_NB_SYMB_HOP,
LORA_IQ_INVERSION_ON, 2000 );
Radio.SetRxConfig( MODEM_LORA, LORA_BANDWIDTH, LORA_SPREADING_FACTOR,
LORA_CODINGRATE, 0, LORA_PREAMBLE_LENGTH,
LORA_SYMBOL_TIMEOUT, LORA_FIX_LENGTH_PAYLOAD_ON, 0,
LORA_CRC_ENABLED, LORA_FHSS_ENABLED, LORA_NB_SYMB_HOP,
LORA_IQ_INVERSION_ON, true );
#elif USE_MODEM_FSK == 1
debug("\n\n\r > FSK Mode < \n\n\r" );
Radio.SetTxConfig( MODEM_FSK, TX_OUTPUT_POWER, FSK_FDEV, 0,
FSK_DATARATE, 0,
FSK_PREAMBLE_LENGTH, FSK_FIX_LENGTH_PAYLOAD_ON,
FSK_CRC_ENABLED, 0, 0, 0, 2000 );
Radio.SetRxConfig( MODEM_FSK, FSK_BANDWIDTH, FSK_DATARATE,
0, FSK_AFC_BANDWIDTH, FSK_PREAMBLE_LENGTH,
0, FSK_FIX_LENGTH_PAYLOAD_ON, 0, FSK_CRC_ENABLED,
0, 0, false, true );
#else
#error "Please define a modem in the compiler options."
#endif
debug_if( DEBUG_MESSAGE, "Starting Ping-Pong loop\r\n" );
led = 0;
Radio.Rx( RX_TIMEOUT_VALUE );
while( 1 )
{
debug("Is master %d, app state %d, radio state %d \r\n", isMaster, State, Radio.GetStatus());
if(tx_count >= 100 && isMaster){
debug("Sent 10 packets\r\n");
debug("Got %d replies\r\n", rx_count);
//Radio.Sleep();
wait_ms(10 * SEC_TO_MSEC);
tx_count = 0;
rx_count = 0;
//break;
}
switch( State )
{
case RX:
rx_count++;
if( isMaster == true )
{
if( BufferSize > 0 )
{
if( strncmp( ( const char* )Buffer, ( const char* )PongMsg, 4 ) == 0 )
{
led = !led;
debug( "...Pong received \r\n" );
// Send the next PING frame
strcpy( ( char* )Buffer, ( char* )PingMsg );
// We fill the buffer with numbers for the payload
for( i = 4; i < BufferSize; i++ )
{
Buffer[i] = i - 4;
}
wait_ms( 10 );
Radio.Send( Buffer, BufferSize );
tx_count++;
}
else if( strncmp( ( const char* )Buffer, ( const char* )PingMsg, 4 ) == 0 )
{ // A master already exists then become a slave
debug( "...Ping received\r\n" );
led = !led;
isMaster = false;
// Send the next PONG frame
strcpy( ( char* )Buffer, ( char* )PongMsg );
// We fill the buffer with numbers for the payload
for( i = 4; i < BufferSize; i++ )
{
Buffer[i] = i - 4;
}
wait_ms( 10 );
Radio.Send( Buffer, BufferSize );
tx_count++;
}
else // valid reception but neither a PING or a PONG message
{ // Set device as master ans start again
isMaster = true;
Radio.Rx( RX_TIMEOUT_VALUE );
}
}
}
else //slave
{
if( BufferSize > 0 )
{
if( strncmp( ( const char* )Buffer, ( const char* )PingMsg, 4 ) == 0 )
{
led = !led;
debug( "...Ping\r\n" );
// Send the reply to the PING string
strcpy( ( char* )Buffer, ( char* )PongMsg );
// We fill the buffer with numbers for the payload
for( i = 4; i < BufferSize; i++ )
{
Buffer[i] = i - 4;
}
wait_ms( 10 );
Radio.Send( Buffer, BufferSize );
debug("sent pong messages\r\n");
Radio.Rx( RX_TIMEOUT_VALUE );
tx_count++;
}
else // valid reception but not a PING as expected
{ // Set device as master and start again
isMaster = true;
Radio.Rx( RX_TIMEOUT_VALUE );
}
}
}
State = LOWPOWER;
break;
case TX:
led = !led;
if( isMaster == true )
{
//debug( "Ping...\r\n" );
}
else
{
//debug( "Pong...\r\n" );
}
Radio.Rx( RX_TIMEOUT_VALUE );
State = LOWPOWER;
break;
case RX_TIMEOUT:
if( isMaster == true )
{
debug("RA_TImout... sending ping\r\n");
// Send the next PING frame
strcpy( ( char* )Buffer, ( char* )PingMsg );
for( i = 4; i < BufferSize; i++ )
{
Buffer[i] = i - 4;
}
wait_ms( 10 );
Radio.Send( Buffer, BufferSize );
tx_count++;
}
else
{
debug("Master(%d): waiting for a ping\r\n", isMaster);
Radio.Rx( RX_TIMEOUT_VALUE );
}
State = LOWPOWER;
break;
case RX_ERROR:
debug("RX_ERROR\r\n");
// We have received a Packet with a CRC error, send reply as if packet was correct
if( isMaster == true )
{
// Send the next PING frame
strcpy( ( char* )Buffer, ( char* )PingMsg );
for( i = 4; i < BufferSize; i++ )
{
Buffer[i] = i - 4;
}
wait_ms( 10 );
Radio.Send( Buffer, BufferSize );
}
else
{
// Send the next PONG frame
strcpy( ( char* )Buffer, ( char* )PongMsg );
for( i = 4; i < BufferSize; i++ )
{
Buffer[i] = i - 4;
}
wait_ms( 10 );
Radio.Send( Buffer, BufferSize );
}
State = LOWPOWER;
break;
case TX_TIMEOUT:
Radio.Rx( RX_TIMEOUT_VALUE );
State = LOWPOWER;
break;
case LOWPOWER:
wait_ms(1000);
break;
default:
State = LOWPOWER;
break;
}
}
}
void OnTxDone( void )
{
Radio.Sleep( );
State = TX;
//debug_if( DEBUG_MESSAGE, "> OnTxDone\n\r" );
}
void OnRxDone( uint8_t *payload, uint16_t size, int16_t rssi, int8_t snr )
{
Radio.Sleep( );
BufferSize = size;
memcpy( Buffer, payload, BufferSize );
RssiValue = rssi;
SnrValue = snr;
State = RX;
//debug_if( DEBUG_MESSAGE, "> OnRxDone\n\r" );
}
void OnTxTimeout( void )
{
Radio.Sleep( );
State = TX_TIMEOUT;
//debug_if( DEBUG_MESSAGE, "> OnTxTimeout\n\r" );
}
void OnRxTimeout( void )
{
Radio.Sleep( );
Buffer[BufferSize] = 0;
State = RX_TIMEOUT;
//debug_if( DEBUG_MESSAGE, "> OnRxTimeout\n\r" );
}
void OnRxError( void )
{
Radio.Sleep( );
State = RX_ERROR;
//debug_if( DEBUG_MESSAGE, "> OnRxError\n\r" );
}