Merge branch 'master' into master

This commit is contained in:
Jm Casler
2021-03-25 19:32:13 -07:00
committed by GitHub
24 changed files with 343 additions and 116 deletions

View File

@@ -97,7 +97,8 @@ static void lsIdle()
static void lsExit()
{
// setGPSPower(true); // restore GPS power
if (gps) gps->forceWake(true);
if (gps)
gps->forceWake(true);
}
static void nbEnter()
@@ -172,7 +173,7 @@ Fsm powerFSM(&stateBOOT);
void PowerFSM_setup()
{
bool isRouter = radioConfig.preferences.is_router;
// If we are not a router and we already have AC power go to POWER state after init, otherwise go to ON
// We assume routers might be powered all the time, but from a low current (solar) source
bool isLowPower = radioConfig.preferences.is_low_power || isRouter;
@@ -180,7 +181,7 @@ void PowerFSM_setup()
/* To determine if we're externally powered, assumptions
1) If we're powered up and there's no battery, we must be getting power externally. (because we'd be dead otherwise)
2) If we detect USB power from the power management chip, we must be getting power externally.
2) If we detect USB power from the power management chip, we must be getting power externally.
*/
bool hasPower = !isLowPower && powerStatus && (!powerStatus->getHasBattery() || powerStatus->getHasUSB());
@@ -249,6 +250,11 @@ void PowerFSM_setup()
powerFSM.add_transition(&stateDARK, &stateDARK, EVENT_CONTACT_FROM_PHONE, NULL, "Contact from phone");
// each time we get a new update packet make sure we are staying in the ON state so the screen stays awake (also we don't
// shutdown bluetooth if is_router)
powerFSM.add_transition(&stateDARK, &stateON, EVENT_FIRMWARE_UPDATE, NULL, "Got firmware update");
powerFSM.add_transition(&stateON, &stateON, EVENT_FIRMWARE_UPDATE, NULL, "Got firmware update");
powerFSM.add_transition(&stateNB, &stateDARK, EVENT_PACKET_FOR_PHONE, NULL, "Packet for phone");
powerFSM.add_timed_transition(&stateON, &stateDARK, getPref_screen_on_secs() * 1000, NULL, "Screen-on timeout");

View File

@@ -18,6 +18,7 @@
#define EVENT_SERIAL_DISCONNECTED 12
#define EVENT_POWER_CONNECTED 13
#define EVENT_POWER_DISCONNECTED 14
#define EVENT_FIRMWARE_UPDATE 15 // We just received a new firmware update packet from the phone
extern Fsm powerFSM;
extern State statePOWER, stateSERIAL;

View File

@@ -1,14 +1,14 @@
#include <Arduino.h>
#include "../concurrency/LockGuard.h"
#include "../graphics/Screen.h"
#include "../main.h"
#include "BluetoothSoftwareUpdate.h"
#include "NodeDB.h"
#include "PowerFSM.h"
#include "RadioLibInterface.h"
#include "configuration.h"
#include "nimble/BluetoothUtil.h"
#include "NodeDB.h"
#include "../graphics/Screen.h"
#include "../main.h"
#include <CRC32.h>
#include <Update.h>
@@ -51,8 +51,8 @@ int update_size_callback(uint16_t conn_handle, uint16_t attr_handle, struct ble_
screen->startFirmwareUpdateScreen();
if (RadioLibInterface::instance)
RadioLibInterface::instance->disable(); // FIXME, nasty hack - the RF95 ISR/SPI code on ESP32 can fail while we are
// writing flash - shut the radio off during updates
RadioLibInterface::instance->disable(); // FIXME, nasty hack - the RF95 ISR/SPI code on ESP32 can fail while we
// are writing flash - shut the radio off during updates
}
}
@@ -78,7 +78,7 @@ int update_data_callback(uint16_t conn_handle, uint16_t attr_handle, struct ble_
crc.update(data, len);
Update.write(data, len);
updateActualSize += len;
powerFSM.trigger(EVENT_CONTACT_FROM_PHONE);
powerFSM.trigger(EVENT_FIRMWARE_UPDATE);
return 0;
}
@@ -107,8 +107,7 @@ int update_crc32_callback(uint16_t conn_handle, uint16_t attr_handle, struct ble
if (update_region == U_SPIFFS) {
DEBUG_MSG("SPIFFS updated!\n");
nodeDB.saveToDisk(); // Since we just wiped spiffs, we need to save our current state
}
else {
} else {
DEBUG_MSG("Appload updated, rebooting in 5 seconds!\n");
rebootAtMsec = millis() + 5000;
}

View File

@@ -33,7 +33,7 @@ int16_t Channels::generateHash(ChannelIndex channelNum)
return -1; // invalid
else {
const char *name = getName(channelNum);
uint8_t h = xorHash((const uint8_t *) name, strlen(name));
uint8_t h = xorHash((const uint8_t *)name, strlen(name));
h ^= xorHash(k.bytes, k.length);
@@ -184,7 +184,7 @@ void Channels::onConfigChanged()
Channel &Channels::getByIndex(ChannelIndex chIndex)
{
assert(chIndex < channelFile.channels_count);
assert(chIndex < channelFile.channels_count); // This should be equal to MAX_NUM_CHANNELS
Channel *ch = channelFile.channels + chIndex;
return *ch;
}
@@ -278,11 +278,11 @@ const char *Channels::getPrimaryName()
*/
bool Channels::decryptForHash(ChannelIndex chIndex, ChannelHash channelHash)
{
if(chIndex > getNumChannels() || getHash(chIndex) != channelHash) {
// DEBUG_MSG("Skipping channel %d (hash %x) due to invalid hash/index, want=%x\n", chIndex, getHash(chIndex), channelHash);
if (chIndex > getNumChannels() || getHash(chIndex) != channelHash) {
// DEBUG_MSG("Skipping channel %d (hash %x) due to invalid hash/index, want=%x\n", chIndex, getHash(chIndex),
// channelHash);
return false;
}
else {
} else {
DEBUG_MSG("Using channel %d (hash 0x%x)\n", chIndex, channelHash);
setCrypto(chIndex);
return true;

View File

@@ -31,6 +31,39 @@ MeshPlugin::~MeshPlugin()
assert(0); // FIXME - remove from list of plugins once someone needs this feature
}
MeshPacket *MeshPlugin::allocAckNak(Routing_Error err, NodeNum to, PacketId idFrom, ChannelIndex chIndex)
{
Routing c = Routing_init_default;
c.error_reason = err;
// Now that we have moded sendAckNak up one level into the class heirarchy we can no longer assume we are a RoutingPlugin
// So we manually call pb_encode_to_bytes and specify routing port number
// auto p = allocDataProtobuf(c);
MeshPacket *p = router->allocForSending();
p->decoded.portnum = PortNum_ROUTING_APP;
p->decoded.payload.size = pb_encode_to_bytes(p->decoded.payload.bytes, sizeof(p->decoded.payload.bytes), Routing_fields, &c);
p->priority = MeshPacket_Priority_ACK;
p->hop_limit = 0; // Assume just immediate neighbors for now
p->to = to;
p->decoded.request_id = idFrom;
p->channel = chIndex;
DEBUG_MSG("Alloc an err=%d,to=0x%x,idFrom=0x%x,id=0x%x\n", err, to, idFrom, p->id);
return p;
}
MeshPacket *MeshPlugin::allocErrorResponse(Routing_Error err, const MeshPacket *p)
{
auto r = allocAckNak(err, getFrom(p), p->id, p->channel);
setReplyTo(r, *p);
return r;
}
void MeshPlugin::callPlugins(const MeshPacket &mp)
{
// DEBUG_MSG("In call plugins\n");
@@ -52,33 +85,47 @@ void MeshPlugin::callPlugins(const MeshPacket &mp)
auto ch = channels.getByIndex(mp.channel);
assert(ch.has_settings);
/// Is the channel this packet arrived on acceptable? (security check)
bool rxChannelOk = !pi.boundChannel || (mp.from == 0) || (strcmp(ch.settings.name, pi.boundChannel) == 0);
/// We only call plugins that are interested in the packet (and the message is destined to us or we are promiscious)
bool wantsPacket = rxChannelOk && (pi.isPromiscuous || toUs) && pi.wantPacket(&mp);
// DEBUG_MSG("Plugin %s wantsPacket=%d\n", pi.name, wantsPacket);
bool wantsPacket = (pi.isPromiscuous || toUs) && pi.wantPacket(&mp);
if (wantsPacket) {
// DEBUG_MSG("Plugin %s wantsPacket=%d\n", pi.name, wantsPacket);
pluginFound = true;
bool handled = pi.handleReceived(mp);
/// Is the channel this packet arrived on acceptable? (security check)
bool rxChannelOk = !pi.boundChannel || (mp.from == 0) || (strcmp(ch.settings.name, pi.boundChannel) == 0);
// Possibly send replies (but only if the message was directed to us specifically, i.e. not for promiscious sniffing)
// also: we only let the one plugin send a reply, once that happens, remaining plugins are not considered
if (!rxChannelOk) {
// no one should have already replied!
assert(!currentReply);
// NOTE: we send a reply *even if the (non broadcast) request was from us* which is unfortunate but necessary because
// currently when the phone sends things, it sends things using the local node ID as the from address. A better
// solution (FIXME) would be to let phones have their own distinct addresses and we 'route' to them like any other
// node.
if (mp.decoded.want_response && toUs && (getFrom(&mp) != ourNodeNum || mp.to == ourNodeNum) && !currentReply) {
pi.sendResponse(mp);
DEBUG_MSG("Plugin %s sent a response\n", pi.name);
if (mp.decoded.want_response) {
DEBUG_MSG("packet on wrong channel, returning error\n");
currentReply = pi.allocErrorResponse(Routing_Error_NOT_AUTHORIZED, &mp);
} else
DEBUG_MSG("packet on wrong channel, but client didn't want response\n");
} else {
DEBUG_MSG("Plugin %s considered\n", pi.name);
}
if (handled) {
DEBUG_MSG("Plugin %s handled and skipped other processing\n", pi.name);
break;
bool handled = pi.handleReceived(mp);
// Possibly send replies (but only if the message was directed to us specifically, i.e. not for promiscious
// sniffing) also: we only let the one plugin send a reply, once that happens, remaining plugins are not
// considered
// NOTE: we send a reply *even if the (non broadcast) request was from us* which is unfortunate but necessary
// because currently when the phone sends things, it sends things using the local node ID as the from address. A
// better solution (FIXME) would be to let phones have their own distinct addresses and we 'route' to them like
// any other node.
if (mp.decoded.want_response && toUs && (getFrom(&mp) != ourNodeNum || mp.to == ourNodeNum) && !currentReply) {
pi.sendResponse(mp);
DEBUG_MSG("Plugin %s sent a response\n", pi.name);
} else {
DEBUG_MSG("Plugin %s considered\n", pi.name);
}
if (handled) {
DEBUG_MSG("Plugin %s handled and skipped other processing\n", pi.name);
break;
}
}
}
@@ -90,8 +137,7 @@ void MeshPlugin::callPlugins(const MeshPacket &mp)
DEBUG_MSG("Sending response\n");
service.sendToMesh(currentReply);
currentReply = NULL;
}
else {
} else {
// No one wanted to reply to this requst, tell the requster that happened
DEBUG_MSG("No one responded, send a nak\n");
routingPlugin->sendAckNak(Routing_Error_NO_RESPONSE, getFrom(&mp), mp.id, mp.channel);

View File

@@ -1,5 +1,6 @@
#pragma once
#include "mesh/Channels.h"
#include "mesh/MeshTypes.h"
#include <vector>
@@ -90,6 +91,11 @@ class MeshPlugin
*/
virtual bool wantUIFrame() { return false; }
MeshPacket *allocAckNak(Routing_Error err, NodeNum to, PacketId idFrom, ChannelIndex chIndex);
/// Send an error response for the specified packet.
MeshPacket *allocErrorResponse(Routing_Error err, const MeshPacket *p);
private:
/**
* If any of the current chain of plugins has already sent a reply, it will be here. This is useful to allow

View File

@@ -83,16 +83,17 @@ bool NodeDB::resetRadioConfig()
radioGeneration++;
radioConfig.has_preferences = true;
if (radioConfig.preferences.factory_reset) {
DEBUG_MSG("Performing factory reset!\n");
installDefaultDeviceState();
didFactoryReset = true;
} else if (channelFile.channels_count == 0) {
}
if (channelFile.channels_count != MAX_NUM_CHANNELS) {
DEBUG_MSG("Setting default channel and radio preferences!\n");
channels.initDefaults();
radioConfig.has_preferences = true;
}
channels.onConfigChanged();
@@ -451,6 +452,8 @@ void NodeDB::updatePosition(uint32_t nodeId, const Position &p)
info->position.latitude_i = p.latitude_i;
info->position.longitude_i = p.longitude_i;
}
if (p.altitude)
info->position.altitude = p.altitude;
info->has_position = true;
updateGUIforNode = info;
notifyObservers(true); // Force an update whether or not our node counts have changed
@@ -486,8 +489,7 @@ void NodeDB::updateUser(uint32_t nodeId, const User &p)
/// we updateGUI and updateGUIforNode if we think our this change is big enough for a redraw
void NodeDB::updateFrom(const MeshPacket &mp)
{
if (mp.which_payloadVariant == MeshPacket_decoded_tag) {
if (mp.which_payloadVariant == MeshPacket_decoded_tag && mp.from) {
DEBUG_MSG("Update DB node 0x%x, rx_time=%u\n", mp.from, mp.rx_time);
NodeInfo *info = getOrCreateNode(getFrom(&mp));
@@ -498,7 +500,8 @@ void NodeDB::updateFrom(const MeshPacket &mp)
info->position.time = mp.rx_time;
}
info->snr = mp.rx_snr; // keep the most recent SNR we received for this node.
if (mp.rx_snr)
info->snr = mp.rx_snr; // keep the most recent SNR we received for this node.
}
}

View File

@@ -115,7 +115,8 @@ void Router::abortSendAndNak(Routing_Error err, MeshPacket *p)
packetPool.release(p);
}
void Router::setReceivedMessage() {
void Router::setReceivedMessage()
{
setInterval(0); // Run ASAP, so we can figure out our correct sleep time
}
@@ -123,9 +124,13 @@ ErrorCode Router::sendLocal(MeshPacket *p)
{
// No need to deliver externally if the destination is the local node
if (p->to == nodeDB.getNodeNum()) {
printPacket("Enqueuing local", p);
fromRadioQueue.enqueue(p);
setReceivedMessage();
if (fromRadioQueue.enqueue(p, 0)) {
printPacket("Enqueued local", p);
setReceivedMessage();
} else {
printPacket("BUG! fromRadioQueue is full! Discarding!", p);
packetPool.release(p);
}
return ERRNO_OK;
} else if (!iface) {
// We must be sending to remote nodes also, fail if no interface found
@@ -143,9 +148,10 @@ ErrorCode Router::sendLocal(MeshPacket *p)
}
}
void printBytes(const char *label, const uint8_t *p, size_t numbytes) {
void printBytes(const char *label, const uint8_t *p, size_t numbytes)
{
DEBUG_MSG("%s: ", label);
for(size_t i = 0; i < numbytes; i++)
for (size_t i = 0; i < numbytes; i++)
DEBUG_MSG("%02x ", p[i]);
DEBUG_MSG("\n");
}
@@ -189,7 +195,7 @@ ErrorCode Router::send(MeshPacket *p)
return ERRNO_TOO_LARGE;
}
//printBytes("plaintext", bytes, numbytes);
// printBytes("plaintext", bytes, numbytes);
auto hash = channels.setActiveByIndex(p->channel);
if (hash < 0) {
@@ -247,19 +253,18 @@ bool Router::perhapsDecode(MeshPacket *p)
rawSize); // we have to copy into a scratch buffer, because these bytes are a union with the decoded protobuf
crypto->decrypt(p->from, p->id, rawSize, bytes);
//printBytes("plaintext", bytes, p->encrypted.size);
// printBytes("plaintext", bytes, p->encrypted.size);
// Take those raw bytes and convert them back into a well structured protobuf we can understand
memset(&p->decoded, 0, sizeof(p->decoded));
memset(&p->decoded, 0, sizeof(p->decoded));
if (!pb_decode_from_bytes(bytes, rawSize, Data_fields, &p->decoded)) {
DEBUG_MSG("Invalid protobufs in received mesh packet (bad psk?)!\n");
} else if(p->decoded.portnum == PortNum_UNKNOWN_APP) {
} else if (p->decoded.portnum == PortNum_UNKNOWN_APP) {
DEBUG_MSG("Invalid portnum (bad psk?)!\n");
}
else {
} else {
// parsing was successful
p->which_payloadVariant = MeshPacket_decoded_tag; // change type to decoded
p->channel = chIndex; // change to store the index instead of the hash
p->channel = chIndex; // change to store the index instead of the hash
printPacket("decoded message", p);
return true;
}
@@ -285,7 +290,7 @@ void Router::handleReceived(MeshPacket *p)
p->rx_time = getValidTime(RTCQualityFromNet); // store the arrival timestamp for the phone
// Take those raw bytes and convert them back into a well structured protobuf we can understand
bool decoded = perhapsDecode(p);
bool decoded = perhapsDecode(p);
if (decoded) {
// parsing was successful, queue for our recipient
printPacket("handleReceived", p);
@@ -293,18 +298,20 @@ void Router::handleReceived(MeshPacket *p)
// call any promiscious plugins here, make a (non promisiocous) plugin for forwarding messages to phone api
// sniffReceived(p);
MeshPlugin::callPlugins(*p);
} else {
DEBUG_MSG("packet decoding failed\n");
}
}
void Router::perhapsHandleReceived(MeshPacket *p)
{
assert(radioConfig.has_preferences);
bool ignore = is_in_repeated(radioConfig.preferences.ignore_incoming, getFrom(p));
bool ignore = is_in_repeated(radioConfig.preferences.ignore_incoming, p->from);
if (ignore)
DEBUG_MSG("Ignoring incoming message, 0x%x is in our ignore list\n", p->from);
else if (ignore |= shouldFilterReceived(p)) {
// DEBUG_MSG("Incoming message was filtered 0x%x\n", p->from);
DEBUG_MSG("Incoming message was filtered 0x%x\n", p->from);
}
// Note: we avoid calling shouldFilterReceived if we are supposed to ignore certain nodes - because some overrides might

View File

@@ -142,6 +142,7 @@ void SX1262Interface::addReceiveMetadata(MeshPacket *mp)
{
// DEBUG_MSG("PacketStatus %x\n", lora.getPacketStatus());
mp->rx_snr = lora.getSNR();
mp->rx_rssi = lround(lora.getRSSI());
}
/** We override to turn on transmitter power as needed.

View File

@@ -31,7 +31,9 @@ template <class T> class TypedQueue
bool isEmpty() { return uxQueueMessagesWaiting(h) == 0; }
bool enqueue(T x, TickType_t maxWait = portMAX_DELAY)
/** euqueue a packet. Also, maxWait used to default to portMAX_DELAY, but we now want to callers to THINK about what blocking
* they want */
bool enqueue(T x, TickType_t maxWait)
{
if (reader) {
reader->setInterval(0);

View File

@@ -125,7 +125,7 @@ extern const pb_msgdesc_t ChannelFile_msg;
/* Maximum encoded size of messages (where known) */
#define LegacyRadioConfig_size 4
#define LegacyRadioConfig_LegacyPreferences_size 2
#define DeviceState_size 4898
#define DeviceState_size 4920
#define ChannelFile_size 832
#ifdef __cplusplus

View File

@@ -57,7 +57,9 @@ typedef enum _Routing_Error {
Routing_Error_MAX_RETRANSMIT = 5,
Routing_Error_NO_CHANNEL = 6,
Routing_Error_TOO_LARGE = 7,
Routing_Error_NO_RESPONSE = 8
Routing_Error_NO_RESPONSE = 8,
Routing_Error_BAD_REQUEST = 32,
Routing_Error_NOT_AUTHORIZED = 33
} Routing_Error;
typedef enum _MeshPacket_Priority {
@@ -150,6 +152,7 @@ typedef struct _MeshPacket {
uint8_t hop_limit;
bool want_ack;
MeshPacket_Priority priority;
int32_t rx_rssi;
} MeshPacket;
typedef struct _NodeInfo {
@@ -206,8 +209,8 @@ typedef struct _ToRadio {
#define _CriticalErrorCode_ARRAYSIZE ((CriticalErrorCode)(CriticalErrorCode_Brownout+1))
#define _Routing_Error_MIN Routing_Error_NONE
#define _Routing_Error_MAX Routing_Error_NO_RESPONSE
#define _Routing_Error_ARRAYSIZE ((Routing_Error)(Routing_Error_NO_RESPONSE+1))
#define _Routing_Error_MAX Routing_Error_NOT_AUTHORIZED
#define _Routing_Error_ARRAYSIZE ((Routing_Error)(Routing_Error_NOT_AUTHORIZED+1))
#define _MeshPacket_Priority_MIN MeshPacket_Priority_UNSET
#define _MeshPacket_Priority_MAX MeshPacket_Priority_MAX
@@ -228,7 +231,7 @@ extern "C" {
#define RouteDiscovery_init_default {0, {0, 0, 0, 0, 0, 0, 0, 0}}
#define Routing_init_default {0, {RouteDiscovery_init_default}}
#define Data_init_default {_PortNum_MIN, {0, {0}}, 0, 0, 0, 0}
#define MeshPacket_init_default {0, 0, 0, 0, {Data_init_default}, 0, 0, 0, 0, 0, _MeshPacket_Priority_MIN}
#define MeshPacket_init_default {0, 0, 0, 0, {Data_init_default}, 0, 0, 0, 0, 0, _MeshPacket_Priority_MIN, 0}
#define NodeInfo_init_default {0, false, User_init_default, false, Position_init_default, 0}
#define MyNodeInfo_init_default {0, 0, 0, "", "", "", _CriticalErrorCode_MIN, 0, 0, 0, 0, 0}
#define LogRecord_init_default {"", 0, "", _LogRecord_Level_MIN}
@@ -239,7 +242,7 @@ extern "C" {
#define RouteDiscovery_init_zero {0, {0, 0, 0, 0, 0, 0, 0, 0}}
#define Routing_init_zero {0, {RouteDiscovery_init_zero}}
#define Data_init_zero {_PortNum_MIN, {0, {0}}, 0, 0, 0, 0}
#define MeshPacket_init_zero {0, 0, 0, 0, {Data_init_zero}, 0, 0, 0, 0, 0, _MeshPacket_Priority_MIN}
#define MeshPacket_init_zero {0, 0, 0, 0, {Data_init_zero}, 0, 0, 0, 0, 0, _MeshPacket_Priority_MIN, 0}
#define NodeInfo_init_zero {0, false, User_init_zero, false, Position_init_zero, 0}
#define MyNodeInfo_init_zero {0, 0, 0, "", "", "", _CriticalErrorCode_MIN, 0, 0, 0, 0, 0}
#define LogRecord_init_zero {"", 0, "", _LogRecord_Level_MIN}
@@ -291,6 +294,7 @@ extern "C" {
#define MeshPacket_hop_limit_tag 10
#define MeshPacket_want_ack_tag 11
#define MeshPacket_priority_tag 12
#define MeshPacket_rx_rssi_tag 13
#define NodeInfo_num_tag 1
#define NodeInfo_user_tag 2
#define NodeInfo_position_tag 3
@@ -362,7 +366,8 @@ X(a, STATIC, SINGULAR, FIXED32, rx_time, 7) \
X(a, STATIC, SINGULAR, FLOAT, rx_snr, 8) \
X(a, STATIC, SINGULAR, UINT32, hop_limit, 10) \
X(a, STATIC, SINGULAR, BOOL, want_ack, 11) \
X(a, STATIC, SINGULAR, UENUM, priority, 12)
X(a, STATIC, SINGULAR, UENUM, priority, 12) \
X(a, STATIC, SINGULAR, INT32, rx_rssi, 13)
#define MeshPacket_CALLBACK NULL
#define MeshPacket_DEFAULT NULL
#define MeshPacket_payloadVariant_decoded_MSGTYPE Data
@@ -454,12 +459,12 @@ extern const pb_msgdesc_t ToRadio_msg;
#define RouteDiscovery_size 40
#define Routing_size 42
#define Data_size 260
#define MeshPacket_size 298
#define MeshPacket_size 309
#define NodeInfo_size 126
#define MyNodeInfo_size 89
#define LogRecord_size 81
#define FromRadio_size 307
#define ToRadio_size 301
#define FromRadio_size 318
#define ToRadio_size 312
#ifdef __cplusplus
} /* extern "C" */

View File

@@ -77,7 +77,8 @@ void registerHandlers(HTTPServer *insecureServer, HTTPSServer *secureServer)
ResourceNode *nodeAPIv1ToRadio = new ResourceNode("/api/v1/toradio", "PUT", &handleAPIv1ToRadio);
ResourceNode *nodeAPIv1FromRadio = new ResourceNode("/api/v1/fromradio", "GET", &handleAPIv1FromRadio);
ResourceNode *nodeHotspot = new ResourceNode("/hotspot-detect.html", "GET", &handleHotspot);
ResourceNode *nodeHotspotApple = new ResourceNode("/hotspot-detect.html", "GET", &handleHotspot);
ResourceNode *nodeHotspotAndroid = new ResourceNode("/generate_204", "GET", &handleHotspot);
ResourceNode *nodeFavicon = new ResourceNode("/favicon.ico", "GET", &handleFavicon);
ResourceNode *nodeRoot = new ResourceNode("/", "GET", &handleRoot);
ResourceNode *nodeStaticBrowse = new ResourceNode("/static", "GET", &handleStaticBrowse);
@@ -96,7 +97,8 @@ void registerHandlers(HTTPServer *insecureServer, HTTPSServer *secureServer)
secureServer->registerNode(nodeAPIv1ToRadioOptions);
secureServer->registerNode(nodeAPIv1ToRadio);
secureServer->registerNode(nodeAPIv1FromRadio);
secureServer->registerNode(nodeHotspot);
secureServer->registerNode(nodeHotspotApple);
secureServer->registerNode(nodeHotspotAndroid);
secureServer->registerNode(nodeFavicon);
secureServer->registerNode(nodeRoot);
secureServer->registerNode(nodeStaticBrowse);
@@ -117,7 +119,8 @@ void registerHandlers(HTTPServer *insecureServer, HTTPSServer *secureServer)
insecureServer->registerNode(nodeAPIv1ToRadioOptions);
insecureServer->registerNode(nodeAPIv1ToRadio);
insecureServer->registerNode(nodeAPIv1FromRadio);
insecureServer->registerNode(nodeHotspot);
insecureServer->registerNode(nodeHotspotApple);
insecureServer->registerNode(nodeHotspotAndroid);
insecureServer->registerNode(nodeFavicon);
insecureServer->registerNode(nodeRoot);
insecureServer->registerNode(nodeStaticBrowse);

View File

@@ -56,13 +56,21 @@ bool AdminPlugin::handleReceivedProtobuf(const MeshPacket &mp, const AdminMessag
case AdminMessage_set_channel_tag:
DEBUG_MSG("Client is setting channel %d\n", r->set_channel.index);
handleSetChannel(r->set_channel);
if (r->set_channel.index < 0 || r->set_channel.index >= MAX_NUM_CHANNELS)
reply = allocErrorResponse(Routing_Error_BAD_REQUEST, &mp);
else
handleSetChannel(r->set_channel);
break;
case AdminMessage_get_channel_request_tag:
DEBUG_MSG("Client is getting channel %d\n", r->get_channel_request - 1);
handleGetChannel(mp, r->get_channel_request - 1);
case AdminMessage_get_channel_request_tag: {
uint32_t i = r->get_channel_request - 1;
DEBUG_MSG("Client is getting channel %u\n", i);
if (i >= MAX_NUM_CHANNELS)
reply = allocErrorResponse(Routing_Error_BAD_REQUEST, &mp);
else
handleGetChannel(mp, i);
break;
}
case AdminMessage_get_radio_request_tag:
DEBUG_MSG("Client is getting radio\n");

View File

@@ -18,17 +18,16 @@ bool RoutingPlugin::handleReceivedProtobuf(const MeshPacket &mp, const Routing *
printPacket("Delivering rx packet", &mp);
service.handleFromRadio(&mp);
}
return false; // Let others look at this message also if they want
}
MeshPacket *RoutingPlugin::allocReply()
{
assert(currentRequest);
// We only consider making replies if the request was a legit routing packet (not just something we were sniffing)
if(currentRequest->decoded.portnum == PortNum_ROUTING_APP) {
if (currentRequest->decoded.portnum == PortNum_ROUTING_APP) {
assert(0); // 1.2 refactoring fixme, Not sure if anything needs this yet?
// return allocDataProtobuf(u);
}
@@ -37,26 +36,12 @@ MeshPacket *RoutingPlugin::allocReply()
void RoutingPlugin::sendAckNak(Routing_Error err, NodeNum to, PacketId idFrom, ChannelIndex chIndex)
{
Routing c = Routing_init_default;
c.error_reason = err;
auto p = allocDataProtobuf(c);
p->priority = MeshPacket_Priority_ACK;
p->hop_limit = 0; // Assume just immediate neighbors for now
p->to = to;
p->decoded.request_id = idFrom;
p->channel = chIndex;
DEBUG_MSG("Sending an err=%d,to=0x%x,idFrom=0x%x,id=0x%x\n", err, to, idFrom, p->id);
auto p = allocAckNak(err, to, idFrom, chIndex);
router->sendLocal(p); // we sometimes send directly to the local node
}
RoutingPlugin::RoutingPlugin()
: ProtobufPlugin("routing", PortNum_ROUTING_APP, Routing_fields)
RoutingPlugin::RoutingPlugin() : ProtobufPlugin("routing", PortNum_ROUTING_APP, Routing_fields)
{
isPromiscuous = true;
}

View File

@@ -232,8 +232,6 @@ StoreForwardPlugin::StoreForwardPlugin()
Uncomment the preferences below if you want to use the plugin
without having to configure it from the PythonAPI or WebUI.
*/
if (StoreForward_Dev) {
radioConfig.preferences.store_forward_plugin_enabled = 1;
radioConfig.preferences.is_router = 1;