sh import re-enabeld
This commit is contained in:
parent
043f06a699
commit
29814b4949
|
|
@ -1597,7 +1597,7 @@ static void IRAM_ATTR touchISR2() {
|
|||
static void checkTouchButton(Button & button) {
|
||||
if (button.isTouched) {
|
||||
int tmp = touchRead(button.pin & 0x7f);
|
||||
Serial.printf("touch read %d: value is %d\n", button.pin & 0x7f, tmp);
|
||||
//Serial.printf("touch read %d: value is %d\n", button.pin & 0x7f, tmp);
|
||||
if (tmp > sonde.config.touch_thresh + 5) {
|
||||
button.isTouched = false;
|
||||
unsigned long elapsed = my_millis() - button.keydownTime;
|
||||
|
|
|
|||
|
|
@ -3,7 +3,7 @@ var cfgs = [
|
|||
[ "wifi", "Wifi mode (0=off, 1=client, 2=AP, 3=client or AP, 4=client-noscan)" ],
|
||||
[ "mdnsname", "Network mDNS name"],
|
||||
[ "ephftp", "FTP server for ephemeris data (RS92 decoder)"],
|
||||
[ "debug", "Debug mode (0/1)" ],
|
||||
[ "debug", "Debug level (0=err/1=warn/2=info/3=all;+10=color)" ],
|
||||
[ "maxsonde", "Maximum number of QRG entries (must be ≤ 50)" ],
|
||||
[ "rxlat", "Receiver fixed latitude"],
|
||||
[ "rxlon", "Receiver fixed longitude"],
|
||||
|
|
|
|||
|
|
@ -38,7 +38,7 @@ tft_orient=1
|
|||
# General config settings
|
||||
#-------------------------------#
|
||||
maxsonde=20
|
||||
debug=0
|
||||
debug=1
|
||||
# wifi mode: 1=client in background; 2=AP in background; 3=client on startup, ap if failure
|
||||
wifi=3
|
||||
# TCP/IP KISS TNC in port 14590 for APRSdroid (0=disabled, 1=enabled)
|
||||
|
|
|
|||
|
|
@ -607,7 +607,7 @@ void ILI9225Display::drawString(uint16_t x, uint16_t y, const char *s, int16_t w
|
|||
// Standard font
|
||||
if(findex==0) {
|
||||
SPI_MUTEX_LOCK();
|
||||
DebugPrintf(DEBUG_DISPLAY, "Simple Text %s at %d,%d [%d]\n", s, x, y, width);
|
||||
LOG_D(TAG, "Simple Text %s at %d,%d [%d]\n", s, x, y, width);
|
||||
// for gpx fonts and new library, cursor is at baseline!!
|
||||
int h = 6;
|
||||
if( alignright ) {
|
||||
|
|
@ -648,7 +648,7 @@ void ILI9225Display::drawString(uint16_t x, uint16_t y, const char *s, int16_t w
|
|||
}
|
||||
|
||||
if(findex-1>=ngfx) findex=1;
|
||||
DebugPrintf(DEBUG_DISPLAY,"GFX Text %s at %d,%d+%d in color %x, width=%d (w=%d)\n", s, x, y, gfxoffsets[findex-1].yofs, fg, width, w);
|
||||
LOG_D(TAG, "GFX Text %s at %d,%d+%d in color %x, width=%d (w=%d)\n", s, x, y, gfxoffsets[findex-1].yofs, fg, width, w);
|
||||
#if 0
|
||||
// Text by clear rectangle and refill, causes some flicker
|
||||
tft->fillRectangle(x, y, x + width, y + gfxoffsets[findex-1].yclear, bg);
|
||||
|
|
@ -668,11 +668,11 @@ void ILI9225Display::drawString(uint16_t x, uint16_t y, const char *s, int16_t w
|
|||
if(alignright) {
|
||||
// fill with bg from x+w to width
|
||||
if(width>w) tft->fillRect( x, y, width-w, height, bg);
|
||||
DebugPrintf(DEBUG_DISPLAY,"rtext fill %d %d %d %d -- %d %d\n", x, y, width-w, height, x1, y1);
|
||||
LOG_D(TAG, "rtext fill %d %d %d %d -- %d %d\n", x, y, width-w, height, x1, y1);
|
||||
} else {
|
||||
// fill with bg from x+w to width
|
||||
if(width>w) tft->fillRect( x+w, y, width-w, height, bg);
|
||||
DebugPrintf(DEBUG_DISPLAY,"ltext fill %d %d %d %d -- %d %d\n", x+w, y, width-w, height, x1, y1);
|
||||
LOG_D(TAG, "ltext fill %d %d %d %d -- %d %d\n", x+w, y, width-w, height, x1, y1);
|
||||
}
|
||||
#else
|
||||
uint16_t height = gfxoffsets[findex-1].yclear;
|
||||
|
|
@ -687,10 +687,10 @@ void ILI9225Display::drawString(uint16_t x, uint16_t y, const char *s, int16_t w
|
|||
int x0 = 0;
|
||||
if(alignright) { x0 = width - w; }
|
||||
int y0 = gfxoffsets[findex-1].yofs;
|
||||
DebugPrintf(DEBUG_DISPLAY,"GFX: w=%d h=%d\n", width, height);
|
||||
LOG_D(TAG, "GFX: w=%d h=%d\n", width, height);
|
||||
for (uint8_t k = 0; k < strlen(s); k++) {
|
||||
x0 += tft->drawGFXcharBM(x0, y0, s[k], fg, bitmap, width, height) + 1;
|
||||
DebugPrintf(DEBUG_DISPLAY,"[%c->%d]",s[k],x0);
|
||||
LOG_D(TAG, "[%c->%d]",s[k],x0);
|
||||
}
|
||||
// TODO: if x+width exceeds display width, garbage is generated....
|
||||
drawBitmap(x, y, bitmap, width, height);
|
||||
|
|
@ -1092,7 +1092,7 @@ void Display::initFromFile(int index) {
|
|||
const char *ptr;
|
||||
readLine(d, lineBuf, LINEBUFLEN);
|
||||
const char *s = trim(lineBuf);
|
||||
DebugPrintf(DEBUG_SPARSER, "Line: '%s'\n", s);
|
||||
LOG_D(TAG, "Line: '%s'\n", s);
|
||||
if(*s == '#') continue; // ignore comments
|
||||
switch(what) {
|
||||
case -1: // wait for start of screen (@)
|
||||
|
|
@ -1104,7 +1104,7 @@ void Display::initFromFile(int index) {
|
|||
}
|
||||
char *label = strdup(s+1);
|
||||
entrysize = countEntries(d);
|
||||
DebugPrintf(DEBUG_SPARSER,"Reading entry with %d elements\n", entrysize);
|
||||
LOG_D(TAG, "Reading entry with %d elements\n", entrysize);
|
||||
idx++;
|
||||
int res = allocDispInfo(entrysize, &newlayouts[idx], label);
|
||||
if(res<0) {
|
||||
|
|
@ -1118,7 +1118,7 @@ void Display::initFromFile(int index) {
|
|||
if(strncmp(s,"timer=",6)==0) { // timer values
|
||||
char t1[10],t2[10],t3[10];
|
||||
sscanf(s+6, "%5[0-9a-zA-Z-] , %5[0-9a-zA-Z-] , %5[0-9a-zA-Z-]", t1, t2, t3);
|
||||
DebugPrintf(DEBUG_SPARSER,"timers are %s, %s, %s\n", t1, t2, t3);
|
||||
LOG_D(TAG, "timers are %s, %s, %s\n", t1, t2, t3);
|
||||
newlayouts[idx].timeouts[0] = (*t1=='n'||*t1=='N')?sonde.config.norx_timeout:atoi(t1);
|
||||
newlayouts[idx].timeouts[1] = (*t2=='n'||*t2=='N')?sonde.config.norx_timeout:atoi(t2);
|
||||
newlayouts[idx].timeouts[2] = (*t3=='n'||*t3=='N')?sonde.config.norx_timeout:atoi(t3);
|
||||
|
|
@ -1174,7 +1174,7 @@ void Display::initFromFile(int index) {
|
|||
newlayouts[idx].de[what].y = y;
|
||||
newlayouts[idx].de[what].width = n>2 ? w : WIDTH_AUTO;
|
||||
parseDispElement(text, newlayouts[idx].de+what);
|
||||
DebugPrintf(DEBUG_SPARSER,"entry at %d,%d width=%d font %d, color=%x,%x\n", (int)x, (int)y, newlayouts[idx].de[what].width, newlayouts[idx].de[what].fmt,
|
||||
LOG_D(TAG, "entry at %d,%d width=%d font %d, color=%x,%x\n", (int)x, (int)y, newlayouts[idx].de[what].width, newlayouts[idx].de[what].fmt,
|
||||
newlayouts[idx].de[what].fg, newlayouts[idx].de[what].bg);
|
||||
if(newlayouts[idx].de[what].func == disp.drawGPS) {
|
||||
newlayouts[idx].usegps = GPSUSE_BASE|GPSUSE_DIST|GPSUSE_BEARING; // just all for now
|
||||
|
|
@ -1288,7 +1288,7 @@ void Display::drawVS(DispEntry *de) {
|
|||
return;
|
||||
}
|
||||
snprintf(buf, 16, " %+2.1f", sonde.si()->d.vs);
|
||||
DebugPrintf(DEBUG_DISPLAY, "drawVS: extra is %s width=%d\n", de->extra?de->extra:"<null>", de->width);
|
||||
LOG_D(TAG, "drawVS: extra is %s width=%d\n", de->extra?de->extra:"<null>", de->width);
|
||||
if(de->extra) { strcat(buf, de->extra); }
|
||||
drawString(de, buf+strlen(buf)-5- (de->extra?strlen(de->extra):0) );
|
||||
if(!de->extra) rdis->drawTile(de->x+5,de->y,2,ms_tiles);
|
||||
|
|
@ -1523,7 +1523,7 @@ void Display::calcGPS() {
|
|||
gpsBear = -1;
|
||||
}
|
||||
|
||||
DebugPrintf(DEBUG_DISPLAY, "GPS data: valid%d GPS at %f,%f (alt=%d,cog=%d); sonde at dist=%d, dir=%d rel.bear=%d\n",gpsPos.valid?1:0,
|
||||
LOG_D(TAG, "GPS data: valid%d GPS at %f,%f (alt=%d,cog=%d); sonde at dist=%d, dir=%d rel.bear=%d\n",gpsPos.valid?1:0,
|
||||
gpsPos.lat, gpsPos.lon, gpsPos.alt, gpsPos.course, gpsDist, gpsDir, gpsBear);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -214,6 +214,7 @@ int ShFreqImport::handleChar(char c) {
|
|||
// lat lon in deg, dist in km, time in minutes
|
||||
int ShFreqImport::shImportSendRequest(int client, float lat, float lon, int dist, int time) {
|
||||
#if 0
|
||||
// This should now be checked by caller.... call this function only if connected (and idle)!
|
||||
// caller should call only if connected..
|
||||
if(!client->connected()) {
|
||||
if(!client->connect(sonde.config.sondehub.host, 80)) {
|
||||
|
|
@ -240,15 +241,10 @@ int ShFreqImport::shImportSendRequest(int client, float lat, float lon, int dist
|
|||
}
|
||||
|
||||
// return 0 if more data should be read (later), 1 if finished (close connection...)
|
||||
int ShFreqImport::shImportHandleReply(int client) {
|
||||
#if 0
|
||||
// TODO::::
|
||||
|
||||
if(!client->connected()) return 1;
|
||||
while(client->available()) {
|
||||
int res = handleChar(client->read());
|
||||
if(res) return res;
|
||||
}
|
||||
#endif
|
||||
int ShFreqImport::shImportHandleReply(const char *buf, int len) {
|
||||
for(int i=0; i<len; i++) {
|
||||
int ret = handleChar(buf[i]);
|
||||
if(ret) return ret;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -14,7 +14,7 @@ public:
|
|||
|
||||
// return 0: ok, need more data; 1: finished/failure, close connection
|
||||
// Asynchronous I/O. Handle data if available
|
||||
static int shImportHandleReply(int client);
|
||||
static int shImportHandleReply(const char *buf, int len);
|
||||
|
||||
private:
|
||||
static int stringToStype(const char *type);
|
||||
|
|
|
|||
|
|
@ -18,8 +18,6 @@
|
|||
#include "Display.h"
|
||||
#include <Wire.h>
|
||||
|
||||
uint8_t debug = 255-8-16;
|
||||
|
||||
RXTask rxtask = { -1, -1, -1, 0xFFFF, 0 };
|
||||
|
||||
const char *evstring[]={"NONE", "KEY1S", "KEY1D", "KEY1M", "KEY1L", "KEY2S", "KEY2D", "KEY2M", "KEY2L",
|
||||
|
|
|
|||
|
|
@ -2,15 +2,10 @@
|
|||
#ifndef Sonde_h
|
||||
#define Sonde_h
|
||||
|
||||
|
||||
#include <inttypes.h>
|
||||
#include <Arduino.h>
|
||||
|
||||
enum DbgLevel { DEBUG_OFF=0, DEBUG_INFO=1, DEBUG_SPARSER=16, DEBUG_DISPLAY=8 }; // to be extended for configuring serial debug output
|
||||
extern uint8_t debug;
|
||||
|
||||
#define DebugPrint(l,x) if(debug&l) { Serial.print(x); }
|
||||
#define DebugPrintln(l,x) if(debug&l) { Serial.println(x); }
|
||||
#define DebugPrintf(l,...) if(debug&l) { Serial.printf(__VA_ARGS__); }
|
||||
|
||||
// RX_TIMEOUT: no header detected
|
||||
// RX_ERROR: header detected, but data not decoded (crc error, etc.)
|
||||
|
|
|
|||
|
|
@ -0,0 +1,80 @@
|
|||
/*
|
||||
* This is free and unencumbered software released into the public domain.
|
||||
*
|
||||
* For more information, please refer to <https://unlicense.org>
|
||||
*/
|
||||
|
||||
//Regular text
|
||||
#define BLK "\e[0;30m"
|
||||
#define RED "\e[0;31m"
|
||||
#define GRN "\e[0;32m"
|
||||
#define YEL "\e[0;33m"
|
||||
#define BLU "\e[0;34m"
|
||||
#define MAG "\e[0;35m"
|
||||
#define CYN "\e[0;36m"
|
||||
#define WHT "\e[0;37m"
|
||||
|
||||
//Regular bold text
|
||||
#define BBLK "\e[1;30m"
|
||||
#define BRED "\e[1;31m"
|
||||
#define BGRN "\e[1;32m"
|
||||
#define BYEL "\e[1;33m"
|
||||
#define BBLU "\e[1;34m"
|
||||
#define BMAG "\e[1;35m"
|
||||
#define BCYN "\e[1;36m"
|
||||
#define BWHT "\e[1;37m"
|
||||
|
||||
//Regular underline text
|
||||
#define UBLK "\e[4;30m"
|
||||
#define URED "\e[4;31m"
|
||||
#define UGRN "\e[4;32m"
|
||||
#define UYEL "\e[4;33m"
|
||||
#define UBLU "\e[4;34m"
|
||||
#define UMAG "\e[4;35m"
|
||||
#define UCYN "\e[4;36m"
|
||||
#define UWHT "\e[4;37m"
|
||||
|
||||
//Regular background
|
||||
#define BLKB "\e[40m"
|
||||
#define REDB "\e[41m"
|
||||
#define GRNB "\e[42m"
|
||||
#define YELB "\e[43m"
|
||||
#define BLUB "\e[44m"
|
||||
#define MAGB "\e[45m"
|
||||
#define CYNB "\e[46m"
|
||||
#define WHTB "\e[47m"
|
||||
|
||||
//High intensty background
|
||||
#define BLKHB "\e[0;100m"
|
||||
#define REDHB "\e[0;101m"
|
||||
#define GRNHB "\e[0;102m"
|
||||
#define YELHB "\e[0;103m"
|
||||
#define BLUHB "\e[0;104m"
|
||||
#define MAGHB "\e[0;105m"
|
||||
#define CYNHB "\e[0;106m"
|
||||
#define WHTHB "\e[0;107m"
|
||||
|
||||
//High intensty text
|
||||
#define HBLK "\e[0;90m"
|
||||
#define HRED "\e[0;91m"
|
||||
#define HGRN "\e[0;92m"
|
||||
#define HYEL "\e[0;93m"
|
||||
#define HBLU "\e[0;94m"
|
||||
#define HMAG "\e[0;95m"
|
||||
#define HCYN "\e[0;96m"
|
||||
#define HWHT "\e[0;97m"
|
||||
|
||||
//Bold high intensity text
|
||||
#define BHBLK "\e[1;90m"
|
||||
#define BHRED "\e[1;91m"
|
||||
#define BHGRN "\e[1;92m"
|
||||
#define BHYEL "\e[1;93m"
|
||||
#define BHBLU "\e[1;94m"
|
||||
#define BHMAG "\e[1;95m"
|
||||
#define BHCYN "\e[1;96m"
|
||||
#define BHWHT "\e[1;97m"
|
||||
|
||||
//Reset
|
||||
#define CRESET "\e[0m"
|
||||
#define COLOR_RESET "\e[0m"
|
||||
|
||||
|
|
@ -2,6 +2,9 @@
|
|||
#include <sstream>
|
||||
#include <iomanip>
|
||||
|
||||
#define TAG "conn-sondehub"
|
||||
#include "logger.h"
|
||||
|
||||
#if FEATURE_SONDEHUB
|
||||
|
||||
#include "conn-sondehub.h"
|
||||
|
|
@ -27,8 +30,7 @@ extern const char *version_id;
|
|||
int shclient; // Sondehub v2
|
||||
ip_addr_t shclient_ipaddr;
|
||||
|
||||
int shImportInterval = 0;
|
||||
char shImport = 0;
|
||||
unsigned long time_next_import = 0;
|
||||
unsigned long time_last_update = 0;
|
||||
|
||||
enum SHState { SH_DISCONNECTED, SH_DNSLOOKUP, SH_DNSRESOLVED, SH_CONNECTING, SH_CONN_IDLE, SH_CONN_APPENDING, SH_CONN_WAITACK, SH_CONN_WAITIMPORTRES };
|
||||
|
|
@ -67,7 +69,7 @@ void ConnSondehub::netsetup() {
|
|||
time_last_update = 0; /* force sending update */
|
||||
|
||||
// SH import: initial refresh on connect, even if configured interval is longer
|
||||
shImportInterval = 5; // refresh now in 5 seconds
|
||||
time_next_import = millis() + 5000;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -80,10 +82,9 @@ void ConnSondehub::netsetup() {
|
|||
void ConnSondehub::updateSonde( SondeInfo *si ) {
|
||||
if (!sonde.config.sondehub.active)
|
||||
return;
|
||||
Serial.println("SH: updateSonde called");
|
||||
LOG_D(TAG, "updateSonde: si:%s, SH_FSM in state %d (%s), next import in %d s\n", si?"yes":"null", shclient_state, state2str(shclient_state), (time_next_import-millis())/1000);
|
||||
sondehub_client_fsm();
|
||||
|
||||
sondehub_reply_handler(); // TODO remove, done by fsm??
|
||||
if(si==NULL) {
|
||||
sondehub_finish_data();
|
||||
} else {
|
||||
|
|
@ -92,15 +93,6 @@ void ConnSondehub::updateSonde( SondeInfo *si ) {
|
|||
}
|
||||
|
||||
|
||||
void ConnSondehub::updateStation( PosInfo *pi ) {
|
||||
if (!sonde.config.sondehub.active)
|
||||
return;
|
||||
Serial.println("SH: updateStation called");
|
||||
sondehub_client_fsm();
|
||||
// Currently, internal reply_handler uses gpsInfo global variable instead of this pi
|
||||
sondehub_station_update();
|
||||
}
|
||||
|
||||
static void _sh_dns_found(const char * name, const ip_addr_t *ipaddr, void * /*arg*/) {
|
||||
if (ipaddr) {
|
||||
shclient_ipaddr = *ipaddr;
|
||||
|
|
@ -109,6 +101,7 @@ static void _sh_dns_found(const char * name, const ip_addr_t *ipaddr, void * /*a
|
|||
memset(&shclient_ipaddr, 0, sizeof(shclient_ipaddr));
|
||||
shclient_state = SH_DISCONNECTED; // DNS lookup failed
|
||||
// TODO: set "reply messge" to "DNS lookup failed"
|
||||
snprintf(rs_msg, MSG_SIZE, "DNS lookup failed for %s", name);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -121,7 +114,7 @@ void ConnSondehub::sondehub_client_fsm() {
|
|||
FD_SET(shclient, &fdeset);
|
||||
struct timeval selto = {0};
|
||||
|
||||
Serial.printf("SH_FSM in state %d (%s)\n", shclient_state, state2str(shclient_state));
|
||||
// LOG_D(TAG, "SH_FSM in state %d (%s), next import in %d s\n", shclient_state, state2str(shclient_state), (time_next_import-millis())/1000);
|
||||
|
||||
switch(shclient_state) {
|
||||
case SH_DISCONNECTED:
|
||||
|
|
@ -145,7 +138,7 @@ void ConnSondehub::sondehub_client_fsm() {
|
|||
shclient = socket(AF_INET, SOCK_STREAM, 0);
|
||||
int flags = fcntl(shclient, F_GETFL);
|
||||
if (fcntl(shclient, F_SETFL, flags | O_NONBLOCK) == -1) {
|
||||
Serial.println("Setting O_NONBLOCK failed");
|
||||
LOG_E(TAG, "Setting O_NONBLOCK failed\n");
|
||||
}
|
||||
|
||||
struct sockaddr_in sock_info;
|
||||
|
|
@ -174,7 +167,7 @@ void ConnSondehub::sondehub_client_fsm() {
|
|||
// Poll to see if we are now connected
|
||||
int res = select(shclient+1, NULL, &fdset, &fdeset, &selto);
|
||||
if(res<0) {
|
||||
Serial.println("SH_CONNECTING: select error");
|
||||
LOG_E(TAG, "SH_CONNECTING: select error\n");
|
||||
goto error;
|
||||
} else if (res==0) { // still pending
|
||||
break;
|
||||
|
|
@ -186,9 +179,9 @@ void ConnSondehub::sondehub_client_fsm() {
|
|||
if (getsockopt(shclient, SOL_SOCKET, SO_ERROR, (void*)(&sockerr), &len) < 0) {
|
||||
goto error;
|
||||
}
|
||||
Serial.printf("select returing %d. isset:%d iseset:%d sockerr:%d\n", res, FD_ISSET(shclient, &fdset), FD_ISSET(shclient, &fdeset), sockerr);
|
||||
LOG_D(TAG, "select returing %d. isset:%d iseset:%d sockerr:%d\n", res, FD_ISSET(shclient, &fdset), FD_ISSET(shclient, &fdeset), sockerr);
|
||||
if(sockerr) {
|
||||
Serial.printf("SH connect error: %s\n", strerror(sockerr));
|
||||
LOG_E(TAG, "SH connect error: %s\n", strerror(sockerr));
|
||||
goto error;
|
||||
}
|
||||
shclient_state = SH_CONN_IDLE;
|
||||
|
|
@ -197,17 +190,29 @@ void ConnSondehub::sondehub_client_fsm() {
|
|||
break;
|
||||
|
||||
case SH_CONN_IDLE:
|
||||
// if idle, check if we might want to send freq import request
|
||||
if (sonde.config.sondehub.fiactive) {
|
||||
unsigned long now = millis();
|
||||
if(now > time_next_import) {
|
||||
sondehub_send_fimport();
|
||||
}
|
||||
}
|
||||
|
||||
// Intentional fall-through: in idle state, read any data out of connection
|
||||
// in CONN_WAITACK we switch to IDLE as soon as we see the HTTP header
|
||||
|
||||
case SH_CONN_WAITACK:
|
||||
case SH_CONN_WAITIMPORTRES:
|
||||
{
|
||||
// In CONN_WAITACK:
|
||||
// If data starts with HTTP/1 this is the expected response, move to state CONN_IDLE
|
||||
// noise tolerant - should not be needed:
|
||||
// if the data contains HTTP/1 copy that to the start of the buffer, ignore anything up to that point
|
||||
// if not find the last \0 and append next response after the part afterwards
|
||||
|
||||
for(int k=0; k<10; k++) { // read more data...
|
||||
int res = select(shclient+1, &fdset, NULL, NULL, &selto);
|
||||
if(res<0) {
|
||||
Serial.println("SH_CONN_IDLE: select error");
|
||||
LOG_E(TAG, "SH_CONN_IDLE: select error\n");
|
||||
goto error;
|
||||
} else if (res==0) { // no data
|
||||
break;
|
||||
|
|
@ -225,33 +230,39 @@ void ConnSondehub::sondehub_client_fsm() {
|
|||
rs_msg[rs_msg_len] = buf[i];
|
||||
rs_msg_len++;
|
||||
}
|
||||
if(shclient_state == SH_CONN_WAITACK) {
|
||||
if(buf[i]=='\n') {
|
||||
// We still wait for the beginning of the ACK
|
||||
// so check if we got that. if yes, all good, continue reading :)
|
||||
// If not, ignore everything we have read so far...
|
||||
if(strncmp(rs_msg, "HTTP/1", 6)==0) { shclient_state = SH_CONN_IDLE; }
|
||||
else rs_msg_len = 0;
|
||||
}
|
||||
}
|
||||
if(shclient_state == SH_CONN_WAITACK) {
|
||||
if(buf[i]=='\n') {
|
||||
// We still wait for the beginning of the ACK
|
||||
// so check if we got that. if yes, all good, continue reading :)
|
||||
// If not, ignore everything we have read so far...
|
||||
if(strncmp(rs_msg, "HTTP/1", 6)==0) { shclient_state = SH_CONN_IDLE; }
|
||||
else rs_msg_len = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
rs_msg[rs_msg_len] = 0;
|
||||
if( shclient_state == SH_CONN_WAITIMPORTRES ) { // we are waiting for a reply to a sondehub frequency import request
|
||||
int import_res = ShFreqImport::shImportHandleReply(buf, res);
|
||||
LOG_D(TAG, "shImportHandleReply: ret=%d\n", import_res);
|
||||
// import_ress==0 means more data is expected, import_res==1 means complete reply received (or error)
|
||||
if (import_res == 1) {
|
||||
shclient_state = SH_CONN_IDLE;
|
||||
time_next_import = millis() + sonde.config.sondehub.fiinterval * 60000;
|
||||
}
|
||||
}
|
||||
}
|
||||
rs_msg[rs_msg_len] = 0;
|
||||
buf[res] = 0;
|
||||
|
||||
Serial.printf("shclient data (len=%d):", res);
|
||||
Serial.write( (uint8_t *)buf, res );
|
||||
// TODO: Maybe timestamp last received data?
|
||||
// TODO: Maybe repeat
|
||||
// TODO: Add timeout to WAITACK...
|
||||
}
|
||||
LOG_D(TAG, "client_fsm: got data (len=%d): %s\n", res, (char *)buf);
|
||||
// TODO: Maybe timestamp last received data?
|
||||
// TODO: Maybe repeat
|
||||
// TODO: Add timeout to WAITACK...
|
||||
}//for k=0..10
|
||||
}
|
||||
break;
|
||||
|
||||
case SH_CONN_WAITIMPORTRES:
|
||||
sondehub_reply_handler();
|
||||
break;
|
||||
|
||||
default:
|
||||
Serial.println("UNHANLDED CASE: SHOULD NOT HAPPAN*****");
|
||||
LOG_E(TAG, "UNHANLDED CASE: SHOULD NOT HAPPAN*****");
|
||||
}
|
||||
return;
|
||||
|
||||
|
|
@ -261,19 +272,23 @@ error:
|
|||
}
|
||||
|
||||
|
||||
// Sondehub v2 DB related code
|
||||
/*
|
||||
Update station data to the sondehub v2 DB
|
||||
*/
|
||||
/* which_pos: 0=none, 1=fixed, 2=gps */
|
||||
void ConnSondehub::sondehub_station_update() {
|
||||
void ConnSondehub::updateStation( PosInfo *pi ) {
|
||||
if (!sonde.config.sondehub.active)
|
||||
return;
|
||||
LOG_D(TAG, "updateStation\n");
|
||||
sondehub_client_fsm();
|
||||
// Currently, internal handler uses gpsInfo global variable instead of this pi
|
||||
|
||||
struct st_sondehub *conf = &sonde.config.sondehub;
|
||||
#define STATION_DATA_LEN 300
|
||||
char data[STATION_DATA_LEN];
|
||||
char *w;
|
||||
|
||||
sondehub_client_fsm(); // let's handle the connection state..
|
||||
Serial.printf("client state is %d (%s)\n", shclient_state, state2str(shclient_state));
|
||||
if(shclient_state != SH_CONN_IDLE) return; // Only if connected and idle can we send data...
|
||||
|
||||
unsigned long time_now = millis();
|
||||
|
|
@ -290,13 +305,13 @@ void ConnSondehub::sondehub_station_update() {
|
|||
// Use 30sec update time in chase mode, 60 min in station mode.
|
||||
unsigned long update_time = (chase == SH_LOC_CHASE) ? SONDEHUB_MOBILE_STATION_UPDATE_TIME : SONDEHUB_STATION_UPDATE_TIME;
|
||||
|
||||
Serial.printf("tlu:%d delta:%d upd=%d\nn", time_last_update, time_delta, update_time);
|
||||
LOG_D(TAG, "tlu:%d delta:%d upd=%d\n", time_last_update, time_delta, update_time);
|
||||
// If it is not yet time to send another update. do nothing....
|
||||
if(time_last_update != 0) { // if 0, force update
|
||||
if ( (time_delta <= update_time) ) return;
|
||||
}
|
||||
|
||||
Serial.println("sondehub_station_update()");
|
||||
LOG_D(TAG, "sondehub_station_update: send update\n");
|
||||
time_last_update = time_now;
|
||||
|
||||
w = data;
|
||||
|
|
@ -360,14 +375,14 @@ void ConnSondehub::sondehub_station_update() {
|
|||
"Content-Length: %d\r\n\r\n%s",
|
||||
conf->host, strlen(data), data);
|
||||
|
||||
Serial.printf("PUT /listeners HTTP/1.1\n"
|
||||
LOG_I(TAG, "PUT /listeners HTTP/1.1\n"
|
||||
"Host: %s\n"
|
||||
"accept: text/plain\n"
|
||||
"Content-Type: application/json\n"
|
||||
"Content-Length: %d\n\n%s",
|
||||
conf->host, strlen(data), data);
|
||||
|
||||
Serial.println("Waiting for response");
|
||||
LOG_D(TAG, "Waiting for response");
|
||||
// Now we do this asychronously
|
||||
shclient_state = SH_CONN_WAITACK;
|
||||
rs_msg_len = 0; // wait for new msg:
|
||||
|
|
@ -379,61 +394,54 @@ void ConnSondehub::sondehub_station_update() {
|
|||
Update sonde data to the sondehub v2 DB
|
||||
*/
|
||||
|
||||
void ConnSondehub::sondehub_reply_handler() {
|
||||
#if 0
|
||||
void ConnSondehub::sondehub_reply_handler(const char *buf) {
|
||||
// sondehub handler for tasks to be done even if no data is to be sent:
|
||||
// process response messages from sondehub
|
||||
// request frequency list (if active)
|
||||
// (probably the request part needs to be moved elsewhere! ==> TODO
|
||||
|
||||
if( shclient_state == SH_CONN_WAITIMPORTRES ) { // we are waiting for a reply to a sondehub frequency import request
|
||||
if(shclient_state == SH_CONN_WAITACK) {
|
||||
@@@@@
|
||||
if(buf[i]=='\n') {
|
||||
// We still wait for the beginning of the ACK
|
||||
// so check if we got that. if yes, all good, continue reading :)
|
||||
// If not, ignore everything we have read so far...
|
||||
if(strncmp(rs_msg, "HTTP/1", 6)==0) { shclient_state = SH_CONN_IDLE; }
|
||||
else rs_msg_len = 0;
|
||||
}
|
||||
} else if( shclient_state == SH_CONN_WAITIMPORTRES ) { // we are waiting for a reply to a sondehub frequency import request
|
||||
// while we are waiting, we do nothing else with sondehub...
|
||||
int res = ShFreqImport::shImportHandleReply(shclient);
|
||||
Serial.printf("ret: %d\n", res);
|
||||
LOG_D(TAG, "shImportHandleReply: ret=%d\n", res);
|
||||
// res==0 means more data is expected, res==1 means complete reply received (or error)
|
||||
if (res == 1) {
|
||||
shclient_state = SH_CONN_IDLE;
|
||||
// shImport = 2; // finished
|
||||
shImportInterval = sonde.config.sondehub.fiinterval * 60;
|
||||
time_next_import = millis() + sonde.config.sondehub.fiinterval * 60 * 1000;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
#if 0
|
||||
// send import requests if needed
|
||||
if (sonde.config.sondehub.fiactive) {
|
||||
if (shImport == 2) {
|
||||
Serial.printf("next sondehub frequncy import in %d seconds\n", shImportInterval);
|
||||
shImportInterval --;
|
||||
if (shImportInterval <= 0) {
|
||||
shImport = 0;
|
||||
}
|
||||
}
|
||||
else if (shImport == 0) {
|
||||
if (shState == SH_CONN_APPENDING || shState == SH_CONN_WAITACK)
|
||||
Serial.printf("Time to request next sondehub import.... but still busy with upload request");
|
||||
else
|
||||
sondehub_send_fimport();
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
#if 0
|
||||
// also handle periodic station updates here...
|
||||
// interval check moved to sondehub_station_update to avoid having to calculate distance in auto mode twice
|
||||
if (sonde.config.sondehub.active) {
|
||||
if (shState == SH_CONN_IDLE || shState == SH_DISCONNECTED ) {
|
||||
// (do not set station update while a telemetry report is being sent
|
||||
sondehub_station_update();
|
||||
/// TODO: Move this elsewhere, get timing right!
|
||||
#if 1
|
||||
if( shclient_state == SH_CONN_IDLE ) { // we are connected and idle, so fine to send frequency import request
|
||||
// send import requests if needed
|
||||
if (sonde.config.sondehub.fiactive) {
|
||||
unsigned long now = millis();
|
||||
LOG_D(TAG, "next sondehub frequncy import in %d seconds\n", (time_next_import-now)/1000);
|
||||
if(now > time_next_import) {
|
||||
sondehub_send_fimport();
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
|
||||
void ConnSondehub::sondehub_send_fimport() {
|
||||
#if 0
|
||||
if (shState == SH_CONN_APPENDING || shState == SH_CONN_WAITACK) {
|
||||
// Currently busy with SondeHub data upload
|
||||
// So do nothing here.
|
||||
// sond_fimport will be re-sent later, when shState becomes SH_CONN_IDLE
|
||||
if (shclient_state != SH_CONN_IDLE) {
|
||||
// Only send import if connection is idle (connected but no reply pending or partial request sent)
|
||||
return;
|
||||
}
|
||||
// It's time to run, so check prerequisites
|
||||
|
|
@ -445,14 +453,14 @@ void ConnSondehub::sondehub_send_fimport() {
|
|||
|
||||
int maxdist = sonde.config.sondehub.fimaxdist; // km
|
||||
int maxage = sonde.config.sondehub.fimaxage * 60; // fimaxage is hours, shImportSendRequest uses minutes
|
||||
int fiinterval = sonde.config.sondehub.fiinterval;
|
||||
Serial.printf("shimp : %f %f %d %d %d\n", lat, lon, maxdist, maxage, shImportInterval);
|
||||
if ( !isnan(lat) && !isnan(lon) && maxdist > 0 && maxage > 0 && fiinterval > 0 ) {
|
||||
int res = ShFreqImport::shImportSendRequest(&shclient, lat, lon, maxdist, maxage);
|
||||
if (res == 0) shImport = 1; // Request OK: wait for response
|
||||
else shImport = 2; // Request failed: wait interval, then retry
|
||||
int time_to_next_import = time_next_import - millis();
|
||||
LOG_D(TAG, "shimp : %f %f %d %d %d\n", lat, lon, maxdist, maxage, time_to_next_import/1000);
|
||||
if ( !isnan(lat) && !isnan(lon) && maxdist > 0 && maxage > 0 && time_to_next_import < 0 ) {
|
||||
int res = ShFreqImport::shImportSendRequest(shclient, lat, lon, maxdist, maxage);
|
||||
if (res == 0) {
|
||||
shclient_state = SH_CONN_WAITIMPORTRES;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -461,13 +469,12 @@ void ConnSondehub::sondehub_send_fimport() {
|
|||
void ConnSondehub::sondehub_send_data(SondeInfo * s) {
|
||||
struct st_sondehub *conf = &sonde.config.sondehub;
|
||||
|
||||
Serial.println("sondehub_send_data()");
|
||||
Serial.printf("shclient_state = %d\n", shclient_state);
|
||||
LOG_D(TAG, "sondehub_send_data: shclient_state = %d\n", shclient_state);
|
||||
|
||||
sondehub_client_fsm();
|
||||
// Only send data when in idle or appending state....
|
||||
if(shclient_state != SH_CONN_IDLE && shclient_state != SH_CONN_APPENDING) {
|
||||
Serial.println("Not in right state for sending next request...");
|
||||
LOG_W(TAG, "Not in right state for sending next request...\n");
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
@ -496,7 +503,7 @@ void ConnSondehub::sondehub_send_data(SondeInfo * s) {
|
|||
time(&now);
|
||||
gmtime_r(&now, &timeinfo);
|
||||
if (timeinfo.tm_year <= (2016 - 1900)) {
|
||||
Serial.println("Failed to obtain time");
|
||||
LOG_E(TAG, "Failed to obtain time\n");
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
@ -508,7 +515,7 @@ void ConnSondehub::sondehub_send_data(SondeInfo * s) {
|
|||
if ( realtype != STYPE_M20 && (int)s->d.sats < 4) return; // If not enough sats don't send to SondeHub
|
||||
|
||||
if ( abs(now - (time_t)s->d.time) > (3600 * SONDEHUB_TIME_THRESHOLD) ) {
|
||||
Serial.printf("Sonde time %d too far from current UTC time %ld", s->d.time, now);
|
||||
LOG_E(TAG, "Sonde time %d too far from current UTC time %ld", s->d.time, now);
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
@ -674,20 +681,18 @@ static const char *MONTHS[] = {"Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul",
|
|||
|
||||
void ConnSondehub::sondehub_send_header(SondeInfo * s, struct tm * now) {
|
||||
struct st_sondehub *conf = &sonde.config.sondehub;
|
||||
Serial.print("PUT /sondes/telemetry HTTP/1.1\r\n"
|
||||
"Host: ");
|
||||
Serial.println(conf->host);
|
||||
Serial.print("accept: text/plain\r\n"
|
||||
"Content-Type: application/json\r\n"
|
||||
"Transfer-Encoding: chunked\r\n");
|
||||
|
||||
dprintf(shclient, "PUT /sondes/telemetry HTTP/1.1\r\n"
|
||||
"Host: %s\n"
|
||||
"accept: text/plain\r\n"
|
||||
"Content-Type: application/json\r\n"
|
||||
"Transfer-Encoding: chunked\r\n", conf->host);
|
||||
LOG_D(TAG, "PUT /sondes/telemetry HTTP/1.1\r\n"
|
||||
"Host: %s\n"
|
||||
"accept: text/plain\r\n"
|
||||
"Content-Type: application/json\r\n"
|
||||
"Transfer-Encoding: chunked\r\n", conf->host);
|
||||
if (now) {
|
||||
Serial.printf("Date: %s, %02d %s %04d %02d:%02d:%02d GMT\r\n",
|
||||
LOG_D(TAG, "Date: %s, %02d %s %04d %02d:%02d:%02d GMT\r\n",
|
||||
DAYS[now->tm_wday], now->tm_mday, MONTHS[now->tm_mon], now->tm_year + 1900,
|
||||
now->tm_hour, now->tm_min, now->tm_sec);
|
||||
dprintf(shclient, "Date: %s, %02d %s %04d %02d:%02d:%02d GMT\r\n",
|
||||
|
|
@ -703,15 +708,14 @@ void ConnSondehub::sondehub_send_next(SondeInfo * s, char *chunk, int chunklen,
|
|||
write(shclient, chunk, chunklen);
|
||||
write(shclient, "\r\n", 2);
|
||||
|
||||
Serial.printf("%x\r\n", chunklen + 1);
|
||||
Serial.write((const uint8_t *)(first ? "[" : ","), 1);
|
||||
LOG_D(TAG, "%x\r\n%c", chunklen + 1, first ? "[" : ",");
|
||||
Serial.write((const uint8_t *)chunk, chunklen);
|
||||
Serial.print("\r\n");
|
||||
LOG_D(TAG, "\r\n");
|
||||
}
|
||||
void ConnSondehub::sondehub_send_last() {
|
||||
// last chunk. just the closing "]" of the json request
|
||||
dprintf(shclient, "1\r\n]\r\n0\r\n\r\n");
|
||||
Serial.printf("1\r\n]\r\n0\r\n\r\n");
|
||||
LOG_D(TAG, "1\r\n]\r\n0\r\n\r\n");
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -28,8 +28,7 @@ public:
|
|||
|
||||
private:
|
||||
void sondehub_client_fsm();
|
||||
void sondehub_station_update();
|
||||
void sondehub_reply_handler();
|
||||
void sondehub_reply_handler(const char *buf);
|
||||
void sondehub_send_fimport();
|
||||
void sondehub_send_data(SondeInfo * s);
|
||||
void sondehub_finish_data();
|
||||
|
|
|
|||
|
|
@ -1,15 +1,25 @@
|
|||
|
||||
#include "logger.h"
|
||||
#include <stdio.h>
|
||||
#include "colors.h"
|
||||
|
||||
const char *lvlcol[]={RED, YEL, GRN, BLU};
|
||||
|
||||
void Logger::logf(LOGLEVEL lvl, const char *module, const char *fmt, ...) {
|
||||
char buf[256];
|
||||
int color = sonde.config.debug >= 10 ? 1 : 0;
|
||||
int cfglvl = sonde.config.debug - 10*color;
|
||||
if(lvl > cfglvl) return;
|
||||
char buf[512];
|
||||
va_list ptr;
|
||||
va_start(ptr, fmt);
|
||||
strncpy(buf, module, 20);
|
||||
*buf = 0;
|
||||
if(color) { strlcat(buf, lvlcol[lvl], 512); }
|
||||
strlcat(buf, module, 512);
|
||||
strcat(buf, ": ");
|
||||
int len = strlen(buf);
|
||||
vsnprintf(buf+len, 255-len, fmt, ptr);
|
||||
vsnprintf(buf+len, 512-len, fmt, ptr);
|
||||
if(color) { strlcat(buf, COLOR_RESET, 512); }
|
||||
|
||||
Serial.print(buf);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
const char *version_name = "rdzTTGOsonde";
|
||||
const char *version_id = "dev20240912";
|
||||
const char *version_id = "dev20240913";
|
||||
const int SPIFFS_MAJOR=3;
|
||||
const int SPIFFS_MINOR=3;
|
||||
|
|
|
|||
Loading…
Reference in New Issue