// process a packet from HQ void leadIncoming(const char *packet, size_t len, unsigned short *index) { char *type, *command, *buffer; buffer = (char*)malloc(len); memcpy(buffer, packet, len); uint16_t to; unsigned long id; type = j0g_str("type", buffer, index); if (hqVerboseOutput) { Serial.println(type); } if (strcmp(type, "online") == 0) { Shell.allReportHQ(); } if (strcmp(type, "command") == 0) { to = atoi(j0g_str("to", buffer, index)); id = strtoul(j0g_str("id", buffer, index), NULL, 10); command = j0g_str("command", buffer, index); if (strlen(j0g_str("to", buffer, index)) == 0 || !id || !command) { if (hqVerboseOutput) { Serial.println(F("invalid command, requires to, id, command")); Serial.print(F("to: ")); Serial.println(to); Serial.print(F("id: ")); Serial.println(id); Serial.print(F("command: ")); Serial.println(command); } free(buffer); return; } // handle internal ones first if (to == Scout.getAddress()) { setOutputHandler(&printToString<&leadCommandOutput>); doCommand(command); resetOutputHandler(); StringBuffer report; report.appendSprintf("{\"type\":\"reply\",\"from\":%d,\"id\":%lu,\"end\":true,\"reply\":", to, id); report.appendJsonString(leadCommandOutput, true); report += "}\n"; leadSignal(report); leadCommandOutput = (char*)NULL; free(buffer); return; } // we can only send one command at a time if (leadCommandTo) { // TODO we could stop reading the HQ socket in this mode and then never get a busy? free(buffer); return leadCommandError(to,id,"busy"); } // send over mesh to recipient and cache id for any replies leadAnswerID = id; leadCommandTo = to; leadCommandChunks = command; leadCommandChunksAt = 0; leadCommandRetries = 0; leadCommandChunk(); } free(buffer); }
// [3,[0,1,2],[v,v,v],4] StringBuffer ScoutHandler::report(StringBuffer &report) { report.setCharAt(report.length() - 1, ','); report.appendSprintf("%lu]",millis()); Scout.handler.announce(0xBEEF, report); return report2json(report); }