Other Parts Discussed in Thread: ENERGIA,
Hi
//in energia lora.h is not working with tm4c123 in energia
//but I develop lora tm4c123 energia code as follows
//it is fully working
//Sender
#include <SPI.h>
#define chipSelectPin PA_3
#define RDID 0x42
SPIClass mySPI(0); // 5 is SSI3 on port Q, see SPI.cpp for others
/* SSI0
PA2_CLK
PA3_FSS); NSS
PA4_RX); MISO
PA5_TX); MOSI
*/
#define REG_FIFO 0x00
#define MODE_SLEEP 0x00
#define MODE_STDBY 0x01
#define MODE_TX 0x03
#define MODE_RX_CONTINUOUS 0x05
#define MODE_RX_SINGLE 0x06
#define REG_OP_MODE 0x01
#define REG_FRF_MSB 0x06
#define REG_FRF_MID 0x07
#define REG_FRF_LSB 0x08
#define REG_PA_CONFIG 0x09
#define REG_OCP 0x0b
#define REG_LNA 0x0c
#define REG_FIFO_ADDR_PTR 0x0d
#define REG_FIFO_TX_BASE_ADDR 0x0e
#define REG_FIFO_RX_BASE_ADDR 0x0f
#define REG_FIFO_RX_CURRENT_ADDR 0x10
#define REG_IRQ_FLAGS 0x12
#define REG_RX_NB_BYTES 0x13
#define REG_PKT_SNR_VALUE 0x19
#define REG_PKT_RSSI_VALUE 0x1a
#define REG_RSSI_VALUE 0x1b
#define REG_MODEM_CONFIG_1 0x1d
#define REG_MODEM_CONFIG_2 0x1e
#define REG_PREAMBLE_MSB 0x20
#define REG_PREAMBLE_LSB 0x21
#define REG_PAYLOAD_LENGTH 0x22
#define REG_MODEM_CONFIG_3 0x26
#define REG_FREQ_ERROR_MSB 0x28
#define REG_FREQ_ERROR_MID 0x29
#define REG_FREQ_ERROR_LSB 0x2a
#define REG_RSSI_WIDEBAND 0x2c
#define REG_DETECTION_OPTIMIZE 0x31
#define REG_INVERTIQ 0x33
#define REG_DETECTION_THRESHOLD 0x37
#define REG_SYNC_WORD 0x39
#define REG_INVERTIQ2 0x3b
#define REG_DIO_MAPPING_1 0x40
#define REG_VERSION 0x42
#define REG_PA_DAC 0x4d
// modes
#define MODE_LONG_RANGE_MODE 0x80
#define PA_OUTPUT_RFO_PIN 0
#define PA_OUTPUT_PA_BOOST_PIN 1
// PA config
#define PA_BOOST 0x80
// IRQ masks
#define IRQ_TX_DONE_MASK 0x08
#define IRQ_PAYLOAD_CRC_ERROR_MASK 0x20
#define IRQ_RX_DONE_MASK 0x40
#define RF_MID_BAND_THRESHOLD 525E6
#define RSSI_OFFSET_HF_PORT 157
#define RSSI_OFFSET_LF_PORT 164
#define MAX_PKT_LENGTH 255
void setTxPower(int level, int outputPin = PA_OUTPUT_PA_BOOST_PIN);
int beginPacket(int implicitHeader = false);
int _implicitHeaderMode;
long _frequency;
#define ss 5
#define rst PF_2
#define dio0 2
int count;
uint8_t rv;
void setup()
{
Serial.begin(115200);
delay(1000); // wait a bit serial monitor to open
Serial.println("start");
if(!LoRabegin(866E6))
{
Serial.println("Starting LoRa failed!");
while (1);
}
setSyncWord(0xF3);
Serial.println("done");
}
void loop()
{
beginPacket();
Serial.println("sending ");
lora_send("Abcd");
delay(1000);
lora_send("Wxyz ");
delay(1000);
lora_send("Mnop ");
Serial.println(" done");
Serial.println(" ");
delay(5000);
}
void lora_send(char *a)
{
Serial.println(a);
int b=strlen(a); //string length
writeRegister(REG_OP_MODE, MODE_STDBY);
writeRegister(REG_FIFO_ADDR_PTR, 0x00);
for(int i=0;a[i];i++)
writeRegister(REG_FIFO, a[i] ); //massage you want to send
writeRegister(REG_PAYLOAD_LENGTH, b); //length of massage
writeRegister(MODE_STDBY, MODE_TX);
writeRegister(REG_FIFO_ADDR_PTR, 0x00);
writeRegister(REG_IRQ_FLAGS, 0x00);
}
int beginPacket(int implicitHeader)
{
if (isTransmitting())
{
return 0;
}
// put in standby mode
idle();
if (implicitHeader)
{
implicitHeaderMode();
}
else
{
explicitHeaderMode();
}
// reset FIFO address and paload length
writeRegister(REG_FIFO_ADDR_PTR, 0);
writeRegister(REG_PAYLOAD_LENGTH, 0);
return 1;
}
void explicitHeaderMode()
{
_implicitHeaderMode = 0;
writeRegister(REG_MODEM_CONFIG_1, readRegister(REG_MODEM_CONFIG_1) & 0xfe);
}
void implicitHeaderMode()
{
_implicitHeaderMode = 1;
writeRegister(REG_MODEM_CONFIG_1, readRegister(REG_MODEM_CONFIG_1) | 0x01);
}
bool isTransmitting()
{
if ((readRegister(REG_OP_MODE) & MODE_TX) == MODE_TX)
{
return true;
}
if (readRegister(REG_IRQ_FLAGS) & IRQ_TX_DONE_MASK)
{
// clear IRQ's
writeRegister(REG_IRQ_FLAGS, IRQ_TX_DONE_MASK);
}
return false;
}
void setSyncWord(int sw)
{
writeRegister(REG_SYNC_WORD, sw);
}
int LoRabegin(long frequency)
{
pinMode(chipSelectPin, OUTPUT);
digitalWrite(chipSelectPin, HIGH);
if (rst != -1)
{
pinMode(rst, OUTPUT);
digitalWrite(rst, LOW);
delay(100);
digitalWrite(rst, HIGH);
delay(100);
}
mySPI.begin();
rv=readRegister(REG_VERSION);
if (rv != 0x12)
{
return 0;
}
sleep();
setFrequency(frequency);
// set base addresses
writeRegister(REG_FIFO_TX_BASE_ADDR, 0);
writeRegister(REG_FIFO_RX_BASE_ADDR, 0);
// set LNA boost
writeRegister(REG_LNA, readRegister(REG_LNA) | 0x03);
// set auto AGC
writeRegister(REG_MODEM_CONFIG_3, 0x04);
// set output power to 17 dBm
setTxPower(17);
// put in standby mode
idle();
return 1;
}
void setTxPower(int level, int outputPin)
{
if (PA_OUTPUT_RFO_PIN == outputPin) {
// RFO
if (level < 0)
{
level = 0;
}
else if (level > 14)
{
level = 14;
}
writeRegister(REG_PA_CONFIG, 0x70 | level);
}
else
{
// PA BOOST
if (level > 17)
{
if (level > 20)
{
level = 20;
}
// subtract 3 from level, so 18 - 20 maps to 15 - 17
level -= 3;
// High Power +20 dBm Operation (Semtech SX1276/77/78/79 5.4.3.)
writeRegister(REG_PA_DAC, 0x87);
setOCP(140);
}
else
{
if (level < 2)
{
level = 2;
}
//Default value PA_HF/LF or +17dBm
writeRegister(REG_PA_DAC, 0x84);
setOCP(100);
}
writeRegister(REG_PA_CONFIG, PA_BOOST | (level - 2));
}
}
void setOCP(uint8_t mA)
{
uint8_t ocpTrim = 27;
if (mA <= 120)
{
ocpTrim = (mA - 45) / 5;
}
else if (mA <=240)
{
ocpTrim = (mA + 30) / 10;
}
writeRegister(REG_OCP, 0x20 | (0x1F & ocpTrim));
}
void idle()
{
writeRegister(REG_OP_MODE, MODE_LONG_RANGE_MODE | MODE_STDBY);
}
void sleep()
{
writeRegister(REG_OP_MODE, MODE_LONG_RANGE_MODE | MODE_SLEEP);
}
void setFrequency(long frequency)
{
_frequency = frequency;
uint64_t frf = ((uint64_t)frequency << 19) / 32000000;
writeRegister(REG_FRF_MSB, (uint8_t)(frf >> 16));
writeRegister(REG_FRF_MID, (uint8_t)(frf >> 8));
writeRegister(REG_FRF_LSB, (uint8_t)(frf >> 0));
}
uint8_t readRegister(uint8_t address)
{
return singleTransfer(address & 0x7f, 0x00);
}
void writeRegister(uint8_t address, uint8_t value)
{
singleTransfer(address | 0x80, value);
}
uint8_t singleTransfer(uint8_t address, uint8_t value)
{
uint8_t rv;
mySPI.begin();
pinMode(chipSelectPin,OUTPUT);
digitalWrite(chipSelectPin,LOW);
mySPI.transfer(address);
rv = mySPI.transfer(value);
digitalWrite(chipSelectPin,HIGH);
return rv;
}
//*******************************************************************************************************************************************************************************//
//Receiver
#include <SPI.h>
#define chipSelectPin PA_3
#define RDID 0x42
SPIClass mySPI(0); // 5 is SSI3 on port Q, see SPI.cpp for others
/* SSI0
PA2_CLK
PA3_FSS); NSS
PA4_RX); MISO
PA5_TX); MOSI
*/
#define REG_FIFO 0x00
#define REG_OP_MODE 0x01
#define REG_FRF_MSB 0x06
#define REG_FRF_MID 0x07
#define REG_FRF_LSB 0x08
#define REG_PA_CONFIG 0x09
#define REG_OCP 0x0b
#define REG_LNA 0x0c
#define REG_FIFO_ADDR_PTR 0x0d
#define REG_FIFO_TX_BASE_ADDR 0x0e
#define REG_FIFO_RX_BASE_ADDR 0x0f
#define REG_FIFO_RX_CURRENT_ADDR 0x10
#define REG_IRQ_FLAGS 0x12
#define REG_RX_NB_BYTES 0x13
#define REG_PKT_SNR_VALUE 0x19
#define REG_PKT_RSSI_VALUE 0x1a
#define REG_RSSI_VALUE 0x1b
#define REG_MODEM_CONFIG_1 0x1d
#define REG_MODEM_CONFIG_2 0x1e
#define REG_PREAMBLE_MSB 0x20
#define REG_PREAMBLE_LSB 0x21
#define REG_PAYLOAD_LENGTH 0x22
#define REG_MODEM_CONFIG_3 0x26
#define REG_FREQ_ERROR_MSB 0x28
#define REG_FREQ_ERROR_MID 0x29
#define REG_FREQ_ERROR_LSB 0x2a
#define REG_RSSI_WIDEBAND 0x2c
#define REG_DETECTION_OPTIMIZE 0x31
#define REG_INVERTIQ 0x33
#define REG_DETECTION_THRESHOLD 0x37
#define REG_SYNC_WORD 0x39
#define REG_INVERTIQ2 0x3b
#define REG_DIO_MAPPING_1 0x40
#define REG_VERSION 0x42
#define REG_PA_DAC 0x4d
// modes
#define MODE_LONG_RANGE_MODE 0x80
#define MODE_SLEEP 0x00
#define MODE_STDBY 0x01
#define MODE_TX 0x03
#define MODE_RX_CONTINUOUS 0x05
#define MODE_RX_SINGLE 0x06
#define PA_OUTPUT_RFO_PIN 0
#define PA_OUTPUT_PA_BOOST_PIN 1
// PA config
#define PA_BOOST 0x80
// IRQ masks
#define IRQ_TX_DONE_MASK 0x08
#define IRQ_PAYLOAD_CRC_ERROR_MASK 0x20
#define IRQ_RX_DONE_MASK 0x40
#define RF_MID_BAND_THRESHOLD 525E6
#define RSSI_OFFSET_HF_PORT 157
#define RSSI_OFFSET_LF_PORT 164
#define led PF_1
#define RH_RF95_HEADER_LEN 4
#define MAX_PKT_LENGTH 255
#define RH_RF95_MAX_PAYLOAD_LEN MAX_PKT_LENGTH
void setTxPower(int level, int outputPin = PA_OUTPUT_PA_BOOST_PIN);
int beginPacket(int implicitHeader = false);
int parsePacket(int size = 0);
int _implicitHeaderMode;
int _packetIndex;
long _frequency;
#define ss 5
#define rst PF_2
#define dio0 2
int count;
uint8_t rv;
volatile uint8_t _bufLen;
uint8_t _buf[RH_RF95_MAX_PAYLOAD_LEN];
int i1=0;
/// True when there is a valid message in the buffer
volatile bool _rxBufValid;
void setup()
{
Serial.begin(115200);
Serial.println("RECEVER ");
while (!LoRabegin(866E6))
{
Serial.println(".");
delay(500);
}
setSyncWord(0xF3);
Serial.println("Start");
}
void loop()
{
int packetSize = parsePacket();
if (packetSize)
{
Serial.print("Received packet ");
for(i1=0;i1<packetSize;i1++)
{
char i=readRegister(REG_FIFO);
Serial.print(i);
}
Serial.println("");
}
}
int available()
{
return (readRegister(REG_RX_NB_BYTES) - _packetIndex);
}
int parsePacket(int size)
{
int packetLength = 0;
int irqFlags = readRegister(REG_IRQ_FLAGS);
if (size > 0)
{
implicitHeaderMode();
writeRegister(REG_PAYLOAD_LENGTH, size & 0xff);
}
else
{
explicitHeaderMode();
}
// clear IRQ's
writeRegister(REG_IRQ_FLAGS, irqFlags);
if ((irqFlags & IRQ_RX_DONE_MASK) && (irqFlags & IRQ_PAYLOAD_CRC_ERROR_MASK) == 0)
{
// received a packet
_packetIndex = 0;
// read packet length
if (_implicitHeaderMode)
{
packetLength = readRegister(REG_PAYLOAD_LENGTH);
}
else
{
packetLength = readRegister(REG_RX_NB_BYTES);
}
// set FIFO address to current RX address
writeRegister(REG_FIFO_ADDR_PTR, readRegister(REG_FIFO_RX_CURRENT_ADDR));
// put in standby mode
idle();
}
else if (readRegister(REG_OP_MODE) != (MODE_LONG_RANGE_MODE | MODE_RX_SINGLE))
{
// reset FIFO address
writeRegister(REG_FIFO_ADDR_PTR, 0);
// put in single RX mode
writeRegister(REG_OP_MODE, MODE_LONG_RANGE_MODE | MODE_RX_SINGLE);
}
return packetLength;
}
int beginPacket(int implicitHeader)
{
if (isTransmitting())
{
return 0;
}
// put in standby mode
idle();
if (implicitHeader)
{
implicitHeaderMode();
}
else
{
explicitHeaderMode();
}
// reset FIFO address and paload length
writeRegister(REG_FIFO_ADDR_PTR, 0);
writeRegister(REG_PAYLOAD_LENGTH, 0);
return 1;
}
void explicitHeaderMode()
{
_implicitHeaderMode = 0;
writeRegister(REG_MODEM_CONFIG_1, readRegister(REG_MODEM_CONFIG_1) & 0xfe);
}
void implicitHeaderMode()
{
_implicitHeaderMode = 1;
writeRegister(REG_MODEM_CONFIG_1, readRegister(REG_MODEM_CONFIG_1) | REG_OP_MODE);
}
bool isTransmitting()
{
if ((readRegister(REG_OP_MODE) & MODE_TX) == MODE_TX)
{
return true;
}
if (readRegister(REG_IRQ_FLAGS) & IRQ_TX_DONE_MASK)
{
// clear IRQ's
writeRegister(REG_IRQ_FLAGS, IRQ_TX_DONE_MASK);
}
return false;
}
void setSyncWord(int sw)
{
writeRegister(REG_SYNC_WORD, sw);
}
int LoRabegin(long frequency)
{
pinMode(chipSelectPin, OUTPUT);
digitalWrite(chipSelectPin, HIGH);
if (rst != -1)
{
pinMode(rst, OUTPUT);
digitalWrite(rst, LOW);
delay(100);
digitalWrite(rst, HIGH);
delay(100);
}
mySPI.begin();
rv=readRegister(REG_VERSION);
if (rv != 0x12)
{
return 0;
}
sleep();
setFrequency(frequency);
// set base addresses
writeRegister(REG_FIFO_TX_BASE_ADDR, 0);
writeRegister(REG_FIFO_RX_BASE_ADDR, 0);
// set LNA boost
writeRegister(REG_LNA, readRegister(REG_LNA) | 0x03);
// set auto AGC
writeRegister(REG_MODEM_CONFIG_3, 0x04);
// set output power to 17 dBm
setTxPower(17);
// put in standby mode
idle();
return 1;
}
void setTxPower(int level, int outputPin)
{
if (PA_OUTPUT_RFO_PIN == outputPin)
{
// RFO
if (level < 0)
{
level = 0;
}
else if (level > 14)
{
level = 14;
}
writeRegister(REG_PA_CONFIG, 0x70 | level);
}
else
{
// PA BOOST
if (level > 17)
{
if (level > 20)
{
level = 20;
}
// subtract 3 from level, so 18 - 20 maps to 15 - 17
level -= 3;
// High Power +20 dBm Operation (Semtech SX1276/77/78/79 5.4.3.)
writeRegister(REG_PA_DAC, 0x87);
setOCP(140);
}
else
{
if (level < 2)
{
level = 2;
}
//Default value PA_HF/LF or +17dBm
writeRegister(REG_PA_DAC, 0x84);
setOCP(100);
}
writeRegister(REG_PA_CONFIG, PA_BOOST | (level - 2));
}
}
void setOCP(uint8_t mA)
{
uint8_t ocpTrim = 27;
if (mA <= 120)
{
ocpTrim = (mA - 45) / 5;
}
else if (mA <=240)
{
ocpTrim = (mA + 30) / 10;
}
writeRegister(REG_OCP, 0x20 | (0x1F & ocpTrim));
}
void idle()
{
writeRegister(REG_OP_MODE, MODE_LONG_RANGE_MODE | MODE_STDBY);
}
void sleep()
{
writeRegister(REG_OP_MODE, MODE_LONG_RANGE_MODE | MODE_SLEEP);
}
void setFrequency(long frequency)
{
_frequency = frequency;
uint64_t frf = ((uint64_t)frequency << 19) / 32000000;
writeRegister(REG_FRF_MSB, (uint8_t)(frf >> 16));
writeRegister(REG_FRF_MID, (uint8_t)(frf >> 8));
writeRegister(REG_FRF_LSB, (uint8_t)(frf >> 0));
}
uint8_t readRegister(uint8_t address)
{
return singleTransfer(address & 0x7f, 0x00);
}
void writeRegister(uint8_t address, uint8_t value)
{
singleTransfer(address | 0x80, value);
}
uint8_t singleTransfer(uint8_t address, uint8_t value)
{
uint8_t rv;
mySPI.begin();
pinMode(chipSelectPin,OUTPUT);
digitalWrite(chipSelectPin,LOW);
mySPI.transfer(address);
rv = mySPI.transfer(value);
digitalWrite(chipSelectPin,HIGH);
return rv;
}