diff --git a/tasmota/CHANGELOG.md b/tasmota/CHANGELOG.md index 02b4dc209..4e0cdc436 100644 --- a/tasmota/CHANGELOG.md +++ b/tasmota/CHANGELOG.md @@ -9,6 +9,7 @@ - Add initial support for Telegram bot (#8619) - Add support for HP303B Temperature and Pressure sensor by Robert Jaakke (#8638) - Add rule trigger ``System#Init`` to allow early rule execution without wifi and mqtt initialized yet +- Add serial to TCP bridge, ``TCPStart`` and ``TCPBaudRate`` (needs #define USE_TCP_BRIDGE) ### 8.3.1.2 20200522 diff --git a/tasmota/i18n.h b/tasmota/i18n.h index 1a254bdfc..543a4c9b9 100644 --- a/tasmota/i18n.h +++ b/tasmota/i18n.h @@ -643,6 +643,7 @@ #define D_LOG_UPNP "UPP: " // UPnP #define D_LOG_WIFI "WIF: " // Wifi #define D_LOG_ZIGBEE "ZIG: " // Zigbee +#define D_LOG_TCP "TCP: " // TCP bridge /********************************************************************************************/ diff --git a/tasmota/language/bg_BG.h b/tasmota/language/bg_BG.h index 935704e74..62d48e0a4 100644 --- a/tasmota/language/bg_BG.h +++ b/tasmota/language/bg_BG.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/cs_CZ.h b/tasmota/language/cs_CZ.h index a04a6b16b..cbbe58921 100644 --- a/tasmota/language/cs_CZ.h +++ b/tasmota/language/cs_CZ.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/de_DE.h b/tasmota/language/de_DE.h index 02464daa6..9c605da62 100644 --- a/tasmota/language/de_DE.h +++ b/tasmota/language/de_DE.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/el_GR.h b/tasmota/language/el_GR.h index 333458c72..ff5486540 100644 --- a/tasmota/language/el_GR.h +++ b/tasmota/language/el_GR.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/en_GB.h b/tasmota/language/en_GB.h index 92637b350..4f4180dd4 100644 --- a/tasmota/language/en_GB.h +++ b/tasmota/language/en_GB.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/es_ES.h b/tasmota/language/es_ES.h index 701f3e107..2447cdc05 100644 --- a/tasmota/language/es_ES.h +++ b/tasmota/language/es_ES.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/fr_FR.h b/tasmota/language/fr_FR.h index f91bd7fbd..80cf87061 100644 --- a/tasmota/language/fr_FR.h +++ b/tasmota/language/fr_FR.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/he_HE.h b/tasmota/language/he_HE.h index 3550a1abd..e6af68ddc 100644 --- a/tasmota/language/he_HE.h +++ b/tasmota/language/he_HE.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/hu_HU.h b/tasmota/language/hu_HU.h index 1a58472e4..eb797bcab 100644 --- a/tasmota/language/hu_HU.h +++ b/tasmota/language/hu_HU.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/it_IT.h b/tasmota/language/it_IT.h index 22181a7be..75a1d4361 100644 --- a/tasmota/language/it_IT.h +++ b/tasmota/language/it_IT.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/ko_KO.h b/tasmota/language/ko_KO.h index a004ecec7..4b7e8538a 100644 --- a/tasmota/language/ko_KO.h +++ b/tasmota/language/ko_KO.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/nl_NL.h b/tasmota/language/nl_NL.h index ab6a28485..c9979814b 100644 --- a/tasmota/language/nl_NL.h +++ b/tasmota/language/nl_NL.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/pl_PL.h b/tasmota/language/pl_PL.h index aea969baf..4827d26be 100644 --- a/tasmota/language/pl_PL.h +++ b/tasmota/language/pl_PL.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/pt_BR.h b/tasmota/language/pt_BR.h index 02c4b4ecc..450bea0d5 100644 --- a/tasmota/language/pt_BR.h +++ b/tasmota/language/pt_BR.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/pt_PT.h b/tasmota/language/pt_PT.h index 4507cecba..189b5ec3c 100644 --- a/tasmota/language/pt_PT.h +++ b/tasmota/language/pt_PT.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/ro_RO.h b/tasmota/language/ro_RO.h index 66e82ad55..aaea0a0b2 100644 --- a/tasmota/language/ro_RO.h +++ b/tasmota/language/ro_RO.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/ru_RU.h b/tasmota/language/ru_RU.h index 7c7fc770b..be28c69a2 100644 --- a/tasmota/language/ru_RU.h +++ b/tasmota/language/ru_RU.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "А" diff --git a/tasmota/language/sk_SK.h b/tasmota/language/sk_SK.h index e242f9bc1..4b667150a 100644 --- a/tasmota/language/sk_SK.h +++ b/tasmota/language/sk_SK.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/sv_SE.h b/tasmota/language/sv_SE.h index 1649b7f5f..edf7b3f1e 100644 --- a/tasmota/language/sv_SE.h +++ b/tasmota/language/sv_SE.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/tr_TR.h b/tasmota/language/tr_TR.h index 8a1063d7a..5089b6e15 100644 --- a/tasmota/language/tr_TR.h +++ b/tasmota/language/tr_TR.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "A" diff --git a/tasmota/language/uk_UA.h b/tasmota/language/uk_UA.h index a16675ae4..5f6b23754 100644 --- a/tasmota/language/uk_UA.h +++ b/tasmota/language/uk_UA.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "А" diff --git a/tasmota/language/zh_CN.h b/tasmota/language/zh_CN.h index 0da3126fd..a86e2c7ee 100644 --- a/tasmota/language/zh_CN.h +++ b/tasmota/language/zh_CN.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "安" diff --git a/tasmota/language/zh_TW.h b/tasmota/language/zh_TW.h index 1fb664d08..b1b4424cd 100644 --- a/tasmota/language/zh_TW.h +++ b/tasmota/language/zh_TW.h @@ -691,6 +691,8 @@ #define D_GPIO_WEBCAM_PSCLK "CAM_PSCLK" #define D_GPIO_WEBCAM_HSD "CAM_HSD" #define D_GPIO_WEBCAM_PSRCS "CAM_PSRCS" +#define D_SENSOR_TCP_TXD "TCP Tx" +#define D_SENSOR_TCP_RXD "TCP Rx" // Units #define D_UNIT_AMPERE "安" diff --git a/tasmota/my_user_config.h b/tasmota/my_user_config.h index 3bec4d347..1e57de3bb 100644 --- a/tasmota/my_user_config.h +++ b/tasmota/my_user_config.h @@ -577,6 +577,7 @@ #define STARTING_OFFSET 30 // Turn on NovaSDS XX-seconds before tele_period is reached //#define USE_HPMA // Add support for Honeywell HPMA115S0 particle concentration sensor (+1k4) #define USE_SERIAL_BRIDGE // Add support for software Serial Bridge (+0k8 code) +//#define USE_TCP_BRIDGE // Add support for Serial to TCP bridge (+1.3k code) //#define USE_MP3_PLAYER // Use of the DFPlayer Mini MP3 Player RB-DFR-562 commands: play, volume and stop #define MP3_VOLUME 10 // Set the startup volume on init, the range can be 0..30(max) //#define USE_AZ7798 // Add support for AZ-Instrument 7798 CO2 datalogger (+1k6 code) diff --git a/tasmota/settings.h b/tasmota/settings.h index afc2f5672..db19c1199 100644 --- a/tasmota/settings.h +++ b/tasmota/settings.h @@ -568,8 +568,9 @@ struct { uint8_t windmeter_tele_pchange; // F3E uint8_t ledpwm_on; // F3F uint8_t ledpwm_off; // F40 + uint8_t tcp_baudrate; // F41 - uint8_t free_f42[119]; // F41 - Decrement if adding new Setting variables just above and below + uint8_t free_f42[118]; // F42 - Decrement if adding new Setting variables just above and below // Only 32 bit boundary variables below uint16_t pulse_counter_debounce_low; // FB8 diff --git a/tasmota/tasmota_template.h b/tasmota/tasmota_template.h index 8b44a547b..a87c39939 100644 --- a/tasmota/tasmota_template.h +++ b/tasmota/tasmota_template.h @@ -234,6 +234,8 @@ enum UserSelectablePins { GPIO_BOILER_OT_TX, // OpenTherm Boiler TX pin GPIO_WINDMETER_SPEED, // WindMeter speed counter pin GPIO_BL0940_RX, // BL0940 serial interface + GPIO_TCP_TX, // TCP Serial bridge + GPIO_TCP_RX, // TCP Serial bridge GPIO_SENSOR_END }; // Programmer selectable GPIO functionality @@ -324,7 +326,8 @@ const char kSensorNames[] PROGMEM = D_SENSOR_AS3935 "|" D_SENSOR_PMS5003_TX "|" D_SENSOR_BOILER_OT_RX "|" D_SENSOR_BOILER_OT_TX "|" D_SENSOR_WINDMETER_SPEED "|" - D_SENSOR_BL0940_RX + D_SENSOR_BL0940_RX "|" + D_SENSOR_TCP_TXD "|" D_SENSOR_TCP_RXD ; const char kSensorNamesFixed[] PROGMEM = @@ -682,6 +685,10 @@ const uint8_t kGpioNiceList[] PROGMEM = { #ifdef USE_AS3935 GPIO_AS3935, #endif +#ifdef USE_TCP_BRIDGE + AGPIO(GPIO_TCP_TX), // TCP Serial bridge + AGPIO(GPIO_TCP_RX), // TCP Serial bridge +#endif }; /********************************************************************************************/ diff --git a/tasmota/tasmota_template_ESP32.h b/tasmota/tasmota_template_ESP32.h index aea45ea6a..5457ed33a 100644 --- a/tasmota/tasmota_template_ESP32.h +++ b/tasmota/tasmota_template_ESP32.h @@ -129,6 +129,7 @@ enum UserSelectablePins { GPIO_WINDMETER_SPEED, // WindMeter speed counter pin GPIO_KEY1_TC, // Touch pin as button GPIO_BL0940_RX, // BL0940 serial interface + GPIO_TCP_TX, GPIO_TCP_RX, // TCP to serial bridge GPIO_SENSOR_END }; enum ProgramSelectablePins { @@ -218,7 +219,8 @@ const char kSensorNames[] PROGMEM = D_GPIO_WEBCAM_PSRCS "|" D_SENSOR_BOILER_OT_RX "|" D_SENSOR_BOILER_OT_TX "|" D_SENSOR_WINDMETER_SPEED "|" D_SENSOR_BUTTON "_tc|" - D_SENSOR_BL0940_RX + D_SENSOR_BL0940_RX "|" + D_SENSOR_TCP_TXD "|" D_SENSOR_TCP_RXD ; const char kSensorNamesFixed[] PROGMEM = @@ -547,6 +549,10 @@ const uint16_t kGpioNiceList[] PROGMEM = { AGPIO(GPIO_WEBCAM_PSCLK), AGPIO(GPIO_WEBCAM_HSD) + MAX_WEBCAM_HSD, AGPIO(GPIO_WEBCAM_PSRCS), +#endif +#ifdef USE_TCP_BRIDGE + AGPIO(GPIO_TCP_TX), // TCP Serial bridge + AGPIO(GPIO_TCP_RX), // TCP Serial bridge #endif AGPIO(GPIO_KEY1_TC) + MAX_KEYS }; diff --git a/tasmota/xdrv_41_tcp_bridge.ino b/tasmota/xdrv_41_tcp_bridge.ino new file mode 100644 index 000000000..a6513ec46 --- /dev/null +++ b/tasmota/xdrv_41_tcp_bridge.ino @@ -0,0 +1,205 @@ +/* + xdrv_41_tcp_bridge.ino - TCP to serial bridge + + Copyright (C) 2020 Theo Arends and Stephan Hadinger + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . +*/ + +#ifdef USE_TCP_BRIDGE + +#define XDRV_41 41 + +#ifndef TCP_BRIDGE_CONNECTIONS +#define TCP_BRIDGE_CONNECTIONS 2 // number of maximum parallel connections +#endif + +#ifndef TCP_BRIDGE_BUF_SIZE +#define TCP_BRIDGE_BUF_SIZE 255 // size of the buffer, above 132 required for efficient XMODEM +#endif + +//const uint16_t tcp_port = 8880; +WiFiServer *server_tcp = nullptr; +//WiFiClient client_tcp1, client_tcp2; +WiFiClient client_tcp[TCP_BRIDGE_CONNECTIONS]; +uint8_t client_next = 0; +uint8_t *tcp_buf = nullptr; // data transfer buffer + +#include +TasmotaSerial *TCPSerial = nullptr; + +const char kTCPCommands[] PROGMEM = "TCP" "|" // prefix + "Start" "|" "Baudrate" + ; + +void (* const TCPCommand[])(void) PROGMEM = { + &CmndTCPStart, &CmndTCPBaudrate + }; + +// +// Called at event loop, checks for incoming data from the CC2530 +// +void TCPLoop(void) +{ + uint8_t c; + bool busy; // did we transfer some data? + int32_t buf_len; + + if (!TCPSerial) return; + + // check for a new client connection + if ((server_tcp) && (server_tcp->hasClient())) { + // find an empty slot + uint32_t i; + for (i=0; iavailable(); + break; + } + } + if (i >= ARRAY_SIZE(client_tcp)) { + i = client_next++ % ARRAY_SIZE(client_tcp); + WiFiClient &client = client_tcp[i]; + client.stop(); + client = server_tcp->available(); + } + } + + do { + busy = false; // exit loop if no data was transferred + + // start reading the UART, this buffer can quickly overflow + buf_len = 0; + while ((buf_len < TCP_BRIDGE_BUF_SIZE) && (TCPSerial->available())) { + c = TCPSerial->read(); + if (c >= 0) { + tcp_buf[buf_len++] = c; + busy = true; + } + } + if (buf_len > 0) { + char hex_char[TCP_BRIDGE_BUF_SIZE+1]; + ToHex_P(tcp_buf, buf_len, hex_char, 256); + AddLog_P2(LOG_LEVEL_DEBUG, PSTR(D_LOG_TCP "from MCU: %s"), hex_char); + + for (uint32_t i=0; i= 0) { + tcp_buf[buf_len++] = c; + busy = true; + } + } + if (buf_len > 0) { + char hex_char[TCP_BRIDGE_BUF_SIZE+1]; + ToHex_P(tcp_buf, buf_len, hex_char, 256); + AddLog_P2(LOG_LEVEL_DEBUG, PSTR(D_LOG_TCP "to MCU/%d: %s"), i+1, hex_char); + TCPSerial->write(tcp_buf, buf_len); + } + } + + yield(); // avoid WDT if heavy traffic + } while (busy); +} + +/********************************************************************************************/ +void TCPInit(void) { + if (PinUsed(GPIO_TCP_RX) && PinUsed(GPIO_TCP_TX)) { + tcp_buf = (uint8_t*) malloc(TCP_BRIDGE_BUF_SIZE); + if (!tcp_buf) { AddLog_P2(LOG_LEVEL_ERROR, PSTR(D_LOG_TCP "could not allocate buffer")); return; } + + if (!Settings.tcp_baudrate) { Settings.tcp_baudrate = 115200 / 1200; } + TCPSerial = new TasmotaSerial(Pin(GPIO_TCP_RX), Pin(GPIO_TCP_TX), seriallog_level ? 1 : 2, 0, TCP_BRIDGE_BUF_SIZE); // set a receive buffer of 256 bytes + TCPSerial->begin(Settings.tcp_baudrate * 1200); + if (TCPSerial->hardwareSerial()) { + ClaimSerial(); + } + } +} + +/*********************************************************************************************\ + * Commands +\*********************************************************************************************/ + +// +// Command `ZbConfig` +// +void CmndTCPStart(void) { + + if (!TCPSerial) { return; } + int32_t tcp_port = XdrvMailbox.payload; + + if (server_tcp) { + AddLog_P2(LOG_LEVEL_INFO, PSTR(D_LOG_TCP "Stopping TCP server")); + server_tcp->stop(); + delete server_tcp; + server_tcp = nullptr; + + for (uint32_t i=0; i 0) { + AddLog_P2(LOG_LEVEL_INFO, PSTR(D_LOG_TCP "Starting TCP server on port %d"), tcp_port); + server_tcp = new WiFiServer(tcp_port); + server_tcp->begin(); // start TCP server + server_tcp->setNoDelay(true); + } + + ResponseCmndDone(); +} + +void CmndTCPBaudrate(void) { + if ((XdrvMailbox.payload >= 1200) && (XdrvMailbox.payload <= 115200)) { + XdrvMailbox.payload /= 1200; // Make it a valid baudrate + Settings.tcp_baudrate = XdrvMailbox.payload; + TCPSerial->begin(Settings.tcp_baudrate * 1200); // Reinitialize serial port with new baud rate + } + ResponseCmndNumber(Settings.tcp_baudrate * 1200); +} + +/*********************************************************************************************\ + * Interface +\*********************************************************************************************/ + +bool Xdrv41(uint8_t function) +{ + bool result = false; + + switch (function) { + case FUNC_LOOP: + TCPLoop(); + break; + case FUNC_PRE_INIT: + TCPInit(); + break; + case FUNC_COMMAND: + result = DecodeCommand(kTCPCommands, TCPCommand); + break; + } + return result; +} + +#endif // USE_TCP_BRIDGE