From 29814b4949f23e27ea5a42ca456443d430df8f0d Mon Sep 17 00:00:00 2001 From: "Hansi, dl9rdz" Date: Fri, 13 Sep 2024 23:24:23 +0000 Subject: [PATCH] sh import re-enabeld --- RX_FSK/RX_FSK.ino | 2 +- RX_FSK/data/cfg.js | 2 +- RX_FSK/data/config.txt | 2 +- RX_FSK/src/Display.cpp | 24 ++-- RX_FSK/src/ShFreqImport.cpp | 16 +-- RX_FSK/src/ShFreqImport.h | 2 +- RX_FSK/src/Sonde.cpp | 2 - RX_FSK/src/Sonde.h | 7 +- RX_FSK/src/colors.h | 80 +++++++++++++ RX_FSK/src/conn-sondehub.cpp | 220 ++++++++++++++++++----------------- RX_FSK/src/conn-sondehub.h | 3 +- RX_FSK/src/logger.cpp | 16 ++- RX_FSK/version.h | 2 +- 13 files changed, 230 insertions(+), 148 deletions(-) create mode 100644 RX_FSK/src/colors.h diff --git a/RX_FSK/RX_FSK.ino b/RX_FSK/RX_FSK.ino index e6bb879..e7f2a10 100644 --- a/RX_FSK/RX_FSK.ino +++ b/RX_FSK/RX_FSK.ino @@ -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; diff --git a/RX_FSK/data/cfg.js b/RX_FSK/data/cfg.js index ee2b225..4dc261c 100644 --- a/RX_FSK/data/cfg.js +++ b/RX_FSK/data/cfg.js @@ -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"], diff --git a/RX_FSK/data/config.txt b/RX_FSK/data/config.txt index 02d4027..8299468 100644 --- a/RX_FSK/data/config.txt +++ b/RX_FSK/data/config.txt @@ -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) diff --git a/RX_FSK/src/Display.cpp b/RX_FSK/src/Display.cpp index 38b6ce0..bd70bb5 100644 --- a/RX_FSK/src/Display.cpp +++ b/RX_FSK/src/Display.cpp @@ -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:"", de->width); + LOG_D(TAG, "drawVS: extra is %s width=%d\n", de->extra?de->extra:"", 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); } diff --git a/RX_FSK/src/ShFreqImport.cpp b/RX_FSK/src/ShFreqImport.cpp index 9608948..8e25a7c 100644 --- a/RX_FSK/src/ShFreqImport.cpp +++ b/RX_FSK/src/ShFreqImport.cpp @@ -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 -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", diff --git a/RX_FSK/src/Sonde.h b/RX_FSK/src/Sonde.h index 077eb7e..a87874f 100644 --- a/RX_FSK/src/Sonde.h +++ b/RX_FSK/src/Sonde.h @@ -2,15 +2,10 @@ #ifndef Sonde_h #define Sonde_h + #include #include -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.) diff --git a/RX_FSK/src/colors.h b/RX_FSK/src/colors.h new file mode 100644 index 0000000..ed6e924 --- /dev/null +++ b/RX_FSK/src/colors.h @@ -0,0 +1,80 @@ +/* + * This is free and unencumbered software released into the public domain. + * + * For more information, please refer to + */ + +//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" + diff --git a/RX_FSK/src/conn-sondehub.cpp b/RX_FSK/src/conn-sondehub.cpp index 1c62168..8e79a69 100644 --- a/RX_FSK/src/conn-sondehub.cpp +++ b/RX_FSK/src/conn-sondehub.cpp @@ -2,6 +2,9 @@ #include #include +#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"); } diff --git a/RX_FSK/src/conn-sondehub.h b/RX_FSK/src/conn-sondehub.h index 917c577..948da72 100644 --- a/RX_FSK/src/conn-sondehub.h +++ b/RX_FSK/src/conn-sondehub.h @@ -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(); diff --git a/RX_FSK/src/logger.cpp b/RX_FSK/src/logger.cpp index 57f147a..c83b43d 100644 --- a/RX_FSK/src/logger.cpp +++ b/RX_FSK/src/logger.cpp @@ -1,15 +1,25 @@ #include "logger.h" #include +#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); } diff --git a/RX_FSK/version.h b/RX_FSK/version.h index ca43814..b4a046b 100644 --- a/RX_FSK/version.h +++ b/RX_FSK/version.h @@ -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;