RadioLib/examples/LoRaWAN/LoRaWAN_TS_Packages/LoRaWAN_TS009.h

239 wiersze
7.3 KiB
C

#include <Arduino.h>
#include <RadioLib.h>
// #include <RadioBoards.h>
#warning "The variables below must match your main code. Please check your radio type!"
extern SX1278 radio; // this can be any LoRaWAN-compatible type (e.g. SX1262)
extern LoRaWANNode node;
extern uint32_t periodicity;
extern bool isConfirmed;
extern bool reply;
extern uint8_t dataUp[255];
extern size_t lenUp;
extern uint8_t fPort;
#define RADIOLIB_LORAWAN_TS009_PACKAGE_VERSION (0x00)
#define RADIOLIB_LORAWAN_TS009_DUT_RESET (0x01)
#define RADIOLIB_LORAWAN_TS009_DUT_JOIN (0x02)
#define RADIOLIB_LORAWAN_TS009_SWITCH_CLASS (0x03)
#define RADIOLIB_LORAWAN_TS009_ADR_BIT_CHANGE (0x04)
#define RADIOLIB_LORAWAN_TS009_REGIONAL_DUTY_CYCLE (0x05)
#define RADIOLIB_LORAWAN_TS009_TX_PERIODICITY_CHANGE (0x06)
#define RADIOLIB_LORAWAN_TS009_TX_FRAMES_CTRL (0x07)
#define RADIOLIB_LORAWAN_TS009_ECHO_PAYLOAD (0x08)
#define RADIOLIB_LORAWAN_TS009_RX_APP_CNT (0x09)
#define RADIOLIB_LORAWAN_TS009_RX_APP_CNT_RESET (0x0A)
#define RADIOLIB_LORAWAN_TS009_LINK_CHECK (0x20)
#define RADIOLIB_LORAWAN_TS009_DEVICE_TIME (0x21)
#define RADIOLIB_LORAWAN_TS009_PING_SLOT_INFO (0x22)
#define RADIOLIB_LORAWAN_TS009_TX_CW (0x7D)
#define RADIOLIB_LORAWAN_TS009_DUT_FPORT224_DISABLE (0x7E)
#define RADIOLIB_LORAWAN_TS009_DUT_VERSIONS (0x7F)
/*!
\brief This function implements the TS009 specification.
To enable this package, add this to your setup:
`node.addAppPackage(RADIOLIB_LORAWAN_PACKAGE_TS009, handleTS009)`
Make sure that all `extern` variables are handled in your user code!
*/
void handleTS009(uint8_t* dataDown, size_t lenDown) {
if(lenDown == 0 || dataDown == NULL) {
return;
}
RADIOLIB_DEBUG_PRINTLN("CID = %02x, len = %d", dataDown[0], lenDown - 1);
switch(dataDown[0]) {
case(RADIOLIB_LORAWAN_TS009_PACKAGE_VERSION): {
lenUp = 3;
dataUp[1] = 5; // PackageIdentifier
dataUp[2] = 1; // PackageVersion
fPort = RADIOLIB_LORAWAN_FPORT_TS009;
RADIOLIB_DEBUG_PRINTLN("PackageIdentifier: %d, PackageVersion: %d", dataUp[1], dataUp[2]);
reply = true;
} break;
case(RADIOLIB_LORAWAN_TS009_DUT_RESET): {
RADIOLIB_DEBUG_PRINTLN("Restarting...");
#warning "Please implement this reset function yourself!"
// the function to reset the MCU is platform-dependent
// for ESP32 for example, this would be:
// ESP.restart();
reply = false;
} break;
case(RADIOLIB_LORAWAN_TS009_DUT_JOIN): {
RADIOLIB_DEBUG_PRINTLN("Reverting to Join state");
node.clearSession();
reply = false;
} break;
case(RADIOLIB_LORAWAN_TS009_SWITCH_CLASS): {
uint8_t classType = dataDown[1];
node.setClass(classType);
RADIOLIB_DEBUG_PRINTLN("Switching to class: %s", classType == 0 ? "A" : (classType == 1 ? "B" : "C"));
reply = false;
} break;
case(RADIOLIB_LORAWAN_TS009_ADR_BIT_CHANGE): {
bool adr = (bool)dataDown[1];
node.setADR(adr);
RADIOLIB_DEBUG_PRINTLN("ADR: %d", adr);
reply = false;
} break;
case(RADIOLIB_LORAWAN_TS009_REGIONAL_DUTY_CYCLE): {
bool dutycycle = (bool)dataDown[1];
node.setDutyCycle(dutycycle, 36000);
RADIOLIB_DEBUG_PRINTLN("Dutycycle: %d", dutycycle);
reply = false;
} break;
case(RADIOLIB_LORAWAN_TS009_TX_PERIODICITY_CHANGE): {
uint32_t defaultIntervalSecs = 30;
uint32_t intervals[11] = {defaultIntervalSecs, 5, 10, 20, 30, 40, 50, 60, 120, 240, 480};
periodicity = intervals[dataDown[1]];
RADIOLIB_DEBUG_PRINTLN("Tx Periodicity: %d", periodicity);
reply = false;
} break;
case(RADIOLIB_LORAWAN_TS009_TX_FRAMES_CTRL): {
switch(dataDown[1]) {
case(0):
// no change
// isConfirmed = isConfirmed;
break;
case(1):
isConfirmed = false;
break;
case(2):
isConfirmed = true;
break;
}
RADIOLIB_DEBUG_PRINTLN("Confirmed: %d", isConfirmed);
reply = false;
} break;
case(RADIOLIB_LORAWAN_TS009_ECHO_PAYLOAD): {
lenUp = lenDown;
for (int i = 1; i < lenDown; i++) {
dataUp[i] = dataDown[i] + 1;
}
fPort = RADIOLIB_LORAWAN_FPORT_TS009;
RADIOLIB_DEBUG_PRINTLN("Echoing payload");
reply = true;
} break;
case(RADIOLIB_LORAWAN_TS009_RX_APP_CNT): {
lenUp = 3;
uint16_t aFcntDown16 = (uint16_t)node.getAFCntDown();
dataUp[1] = aFcntDown16 & 0xFF;
dataUp[2] = aFcntDown16 >> 8;
fPort = RADIOLIB_LORAWAN_FPORT_TS009;
RADIOLIB_DEBUG_PRINTLN("aFCntDown16: %d", aFcntDown16);
reply = true;
} break;
case(RADIOLIB_LORAWAN_TS009_RX_APP_CNT_RESET): {
RADIOLIB_DEBUG_PRINTLN("Resetting Application Frame count");
RADIOLIB_DEBUG_PRINTLN("WARNING: not implemented - never used in tests!");
reply = false;
} break;
case(RADIOLIB_LORAWAN_TS009_LINK_CHECK): {
lenUp = 0;
fPort = RADIOLIB_LORAWAN_FPORT_MAC_COMMAND;
node.sendMacCommandReq(RADIOLIB_LORAWAN_MAC_LINK_CHECK);
RADIOLIB_DEBUG_PRINTLN("Requesting LinkCheck");
reply = true;
} break;
case(RADIOLIB_LORAWAN_TS009_DEVICE_TIME): {
lenUp = 0;
fPort = RADIOLIB_LORAWAN_FPORT_MAC_COMMAND;
node.sendMacCommandReq(RADIOLIB_LORAWAN_MAC_DEVICE_TIME);
RADIOLIB_DEBUG_PRINTLN("Requesting DeviceTime");
reply = true;
} break;
case(RADIOLIB_LORAWAN_TS009_PING_SLOT_INFO): {
lenUp = 0;
RADIOLIB_DEBUG_PRINTLN("Requesting PingSlotInfo not implemented");
// send PingSlotInfo MAC command which is not implemented
reply = false;
} break;
case(RADIOLIB_LORAWAN_TS009_TX_CW): {
// not implemented
uint16_t timeout = (dataDown[2] << 8) | dataDown[1];
uint32_t freqRaw = (dataDown[5] << 16) | (dataDown[4] << 8) | (dataDown[3]);
float freq = (float)freqRaw/10000.0;
uint8_t txPower = dataDown[6];
RADIOLIB_DEBUG_PRINTLN("Continuous wave: %7.3f MHz, %d dBm, %d s", freq, txPower, timeout);
radio.setFrequency(freq);
radio.setOutputPower(txPower);
radio.transmitDirect();
delay(timeout * 1000);
radio.standby();
reply = false;
} break;
case(RADIOLIB_LORAWAN_TS009_DUT_FPORT224_DISABLE): {
RADIOLIB_DEBUG_PRINTLN("Disabling FPort 224");
node.removePackage(RADIOLIB_LORAWAN_PACKAGE_TS009);
reply = false;
} break;
case(RADIOLIB_LORAWAN_TS009_DUT_VERSIONS): {
lenUp = 13;
// firmware version - this is RadioLib's version as an example
dataUp[1] = RADIOLIB_VERSION_MAJOR;
dataUp[2] = RADIOLIB_VERSION_MINOR;
dataUp[3] = RADIOLIB_VERSION_PATCH;
dataUp[4] = RADIOLIB_VERSION_EXTRA;
// lorawan version
dataUp[5] = 1;
#if (LORAWAN_VERSION == 1)
dataUp[6] = 1;
dataUp[7] = 0;
#else
dataUp[6] = 0;
dataUp[7] = 4;
#endif
dataUp[8] = 0;
// regional parameters version
dataUp[9] = 1;
dataUp[10] = 0;
dataUp[11] = 4;
dataUp[12] = 0;
fPort = RADIOLIB_LORAWAN_FPORT_TS009;
RADIOLIB_DEBUG_PRINTLN("Requested DUT versions");
reply = true;
} break;
}
// if we must reply, copy the command ID into the uplink buffer
if(reply) {
dataUp[0] = dataDown[0];
}
}