From e87240d841caa02af2e11ed633f6327460dab1ca Mon Sep 17 00:00:00 2001 From: Andrey Klimov Date: Sat, 6 Jun 2020 18:03:57 +0300 Subject: [PATCH] new interface class itemCmd as interface between objects Modbus polling->MQTT syslog fix different level of logging infoSerial errorSerial --- compiled/lighthub21/uploadOTA.sh | 1 + lighthub/item.cpp | 95 +++++++++++ lighthub/item.h | 61 +++++-- lighthub/main.cpp | 277 +++++++++++++++---------------- lighthub/modules/out_modbus.cpp | 62 +++++-- lighthub/textconst.h | 18 +- lighthub/utils.cpp | 25 ++- lighthub/utils.h | 6 +- 8 files changed, 369 insertions(+), 176 deletions(-) create mode 100755 compiled/lighthub21/uploadOTA.sh diff --git a/compiled/lighthub21/uploadOTA.sh b/compiled/lighthub21/uploadOTA.sh new file mode 100755 index 0000000..6b263f1 --- /dev/null +++ b/compiled/lighthub21/uploadOTA.sh @@ -0,0 +1 @@ +../tools/mac/arduinoOTA -address 192.168.88.59 -port 65280 -username arduino -password password -sketch firmware.bin -b -upload /sketch diff --git a/lighthub/item.cpp b/lighthub/item.cpp index 18c9948..e2ed62c 100644 --- a/lighthub/item.cpp +++ b/lighthub/item.cpp @@ -54,12 +54,91 @@ extern lan_status lanStatus; int retrieveCode(char **psubItem); + + + itemCmd itemCmd::Percents(int i) + { + type=ST_PERCENTS; + param.aslong=i; + return *this; + } + + itemCmd itemCmd::Int(int32_t i) + { + type=ST_INT32; + param.asInt32=i; + return *this; + } + + itemCmd itemCmd::Int(uint32_t i) + { + type=ST_UINT32; + param.asUint32=i; + return *this; + } + + + itemCmd itemCmd::Cmd(uint8_t i) + { + type=ST_COMMAND; + param.cmd_code=i; + return *this; + } + + char * itemCmd::toString(char * Buffer, int bufLen) + { + if (!Buffer) return NULL; + switch (type) + { + case ST_VOID: + return NULL; + + case ST_PERCENTS: + case ST_PERCENTS255: + case ST_UINT32: + snprintf(Buffer, bufLen, "%u", param.asUint32); + break; + case ST_INT32: + snprintf(Buffer, bufLen, "%d", param.asInt32); + + break; + case ST_HS: + case ST_HSV: + case ST_HSV255: + snprintf(Buffer, bufLen, "%d,%d,%d", param.h, param.s, param.v); + + break; + case ST_FLOAT_CELSIUS: + case ST_FLOAT_FARENHEIT: + case ST_FLOAT: + snprintf(Buffer, bufLen, "%d", param.asfloat); + break; + case ST_RGB: + snprintf(Buffer, bufLen, "%d,%d,%d", param.r, param.g, param.b); + break; + + case ST_RGBW: + snprintf(Buffer, bufLen, "%d,%d,%d", param.r, param.g, param.b,param.w); + break; + + case ST_STRING: + strncpy(Buffer, param.asString,bufLen); + + break; + case ST_COMMAND: + strncpy_P(Buffer, commands_P[param.cmd_code], bufLen); + } + return Buffer; + } + int txt2cmd(char *payload) { int cmd = CMD_UNKNOWN; + if (!payload || !payload[0]) return cmd; // Check for command if (*payload == '-' || (*payload >= '0' && *payload <= '9')) cmd = CMD_NUM; else if (*payload == '%') cmd = CMD_UP; +/* else if (strcmp_P(payload, ON_P) == 0) cmd = CMD_ON; else if (strcmp_P(payload, OFF_P) == 0) cmd = CMD_OFF; else if (strcmp_P(payload, REST_P) == 0) cmd = CMD_RESTORE; @@ -81,10 +160,26 @@ int txt2cmd(char *payload) { else if (strcmp_P(payload, HIGH_P) == 0) cmd = CMD_HIGH; else if (strcmp_P(payload, MED_P) == 0) cmd = CMD_MED; else if (strcmp_P(payload, LOW_P) == 0) cmd = CMD_LOW; +*/ else if (*payload == '{') cmd = CMD_JSON; else if (*payload == '#') cmd = CMD_RGB; + else + { + for(uint8_t i=1; i (SERIAL_8N1); + } + + /* else if (strncmp_P(payload, HSV_P, strlen (HSV_P)) == 0) cmd = CMD_HSV; else if (strncmp_P(payload, RGB_P, strlen (RGB_P)) == 0) cmd = CMD_RGB; + */ + return cmd; } diff --git a/lighthub/item.h b/lighthub/item.h index f7b9725..1ca7704 100644 --- a/lighthub/item.h +++ b/lighthub/item.h @@ -61,8 +61,18 @@ e-mail anklimov@gmail.com #define CMD_NUM 0 #define CMD_UNKNOWN -1 #define CMD_JSON -2 -#define CMD_RGB -3 -#define CMD_HSV -4 +//#define CMD_RGB -3 +//#define CMD_HSV -4 + +typedef char cmdstr[9]; + +const cmdstr commands_P[] PROGMEM = +{ +"","ON","OFF","RESTORE","TOGGLE","HALT","XON","XOFF","INCREASE","DECREASE", +"HEAT","COOL","AUTO","FAN_ONLY","DRY","STOP","HIGH","MEDIUM","LOW", +"TRUE","FALSE","ENABLED","DISABLED","RGB","HSV" +}; +#define commandsNum sizeof(commands_P)/sizeof(cmdstr) #define CMD_ON 1 #define CMD_OFF 2 @@ -78,10 +88,16 @@ e-mail anklimov@gmail.com #define CMD_AUTO 0xc #define CMD_FAN 0xd #define CMD_DRY 0xe -//#define CMD_SET 0xf +#define CMD_STOP 0xf #define CMD_HIGH 0x10 //AC fan leve #define CMD_MED 0x11 #define CMD_LOW 0x12 +#define CMD_ENABLED 0x13 +#define CMD_DISABLED 0x14 +#define CMD_TRUE 0x15 +#define CMD_FALSE 0x16 +#define CMD_RGB 0x17 +#define CMD_HSV 0x18 //#define CMD_CURTEMP 0xf #define CMD_MASK 0xff #define FLAG_MASK 0xff00 @@ -94,6 +110,10 @@ e-mail anklimov@gmail.com #define ACTION_NEEDED 0x1000 #define ACTION_IN_PROCESS 0x2000 + + + + //#define CMD_REPORT 32 #define I_TYPE 0 //Type of item @@ -130,7 +150,12 @@ ST_FLOAT_FARENHEIT= 5, ST_RGB = 6, ST_RGBW = 7, ST_PERCENTS255 = 8, -ST_HSV255 = 9 +ST_HSV255 = 9, +ST_INT32 = 10, +ST_UINT32 = 11, +ST_STRING = 12, +ST_FLOAT = 13, +ST_COMMAND = 15 }; @@ -138,7 +163,17 @@ ST_HSV255 = 9 typedef union { long int aslong; - float asfloat; + int32_t asInt32; + uint32_t asUint32; + char* asString; + float asfloat; + struct + { + uint8_t cmd_code; + uint8_t cmd_flag; + uint8_t cmd_effect; + uint8_t cmd_effect_param; + }; struct { uint8_t v; uint8_t s; @@ -155,14 +190,18 @@ typedef union }; } itemStore; -/* -typedef union +class itemCmd { - long int aslong; - struct +public: + itemStoreType type; + itemStore param; + itemCmd Percents(int i); + itemCmd Int(int32_t i); + itemCmd Int(uint32_t i); + itemCmd Cmd(uint8_t i); + char * toString(char * Buffer, int bufLen); + } ; -} RGBWstore; -*/ #pragma pack(pop) class Item diff --git a/lighthub/main.cpp b/lighthub/main.cpp index f6b40e6..3fdd715 100644 --- a/lighthub/main.cpp +++ b/lighthub/main.cpp @@ -118,6 +118,7 @@ EthernetClient ethClient; EthernetUDP udpSyslogClient; Syslog udpSyslog(udpSyslogClient, SYSLOG_PROTO_BSD); unsigned long nextSyslogPingTime; +static char syslogDeviceHostname[16]; Streamlog debugSerial(&debugSerialPort,LOG_DEBUG,&udpSyslog); Streamlog errorSerial(&debugSerialPort,LOG_ERROR,&udpSyslog); @@ -329,14 +330,14 @@ else void printMACAddress() { - debugSerial<valuestring; char *syslogAppname = aJson.getArrayItem(udpSyslogArr, 3)->valuestring; */ - debugSerial<= 4) user = getStringFromConfig(mqttArr, 3); if (!loadFlash(OFFSET_MQTT_PWD, passwordBuf, sizeof(passwordBuf)) && (n >= 5)) { password = getStringFromConfig(mqttArr, 4); - debugSerial<50){ - debugSerial<=1 ) { DMXoutSetup(maxChannels = aJson.getArrayItem(dmxoutArr, numParams-1)->valueint); - debugSerial<child; owReady = owSetup(&Changed); - if (owReady) debugSerial<type == aJson_Object)) { DeviceAddress addr; - //debugSerial<name); + //infoSerial<name); SetAddr(item->name, addr); owAdd(addr); } @@ -1066,26 +1066,26 @@ configLocked--; } void printConfigSummary() { - debugSerial< 1) { strncpy(configServer, args[1], sizeof(configServer) - 1); saveFlash(OFFSET_CONFIGSERVER, configServer); - debugSerial< 0) { - debugSerial.printf("[HTTP] GET... code: %d\n", httpResponseCode); + infoSerial.printf("[HTTP] GET... code: %d\n", httpResponseCode); if (httpResponseCode == HTTP_CODE_OK) { String response = httpClient.getString(); debugSerial<valuefloat; if (!aJson.getArrayItem(thermoExtensionArray, IET_ATTEMPTS)->valueint) { - debugSerial<name<name<valueint)) diff --git a/lighthub/modules/out_modbus.cpp b/lighthub/modules/out_modbus.cpp index b84bc55..91712a6 100644 --- a/lighthub/modules/out_modbus.cpp +++ b/lighthub/modules/out_modbus.cpp @@ -39,14 +39,14 @@ struct serial_t const reg_t regSize_P[] PROGMEM = { - { "i16", (int) PAR_I16 }, - { "i32", (int) PAR_I32 }, - { "u16", (int) PAR_U16 }, - { "u32", (int) PAR_U32 }, - { "i8h", (int) PAR_I8H }, - { "i8l", (int) PAR_I8L }, - { "u8h", (int) PAR_U8H }, - { "u8l", (int) PAR_U8L } + { "i16", (uint8_t) PAR_I16 }, + { "i32", (uint8_t) PAR_I32 }, + { "u16", (uint8_t) PAR_U16 }, + { "u32", (uint8_t) PAR_U32 }, + { "i8h", (uint8_t) PAR_I8H }, + { "i8l", (uint8_t) PAR_I8L }, + { "u8h", (uint8_t) PAR_U8H }, + { "u8l", (uint8_t) PAR_U8L } } ; #define regSizeNum sizeof(regSize_P)/sizeof(reg_t) @@ -86,7 +86,7 @@ uint16_t str2SerialParam(char * str) } int str2regSize(char * str) { - for(uint8_t i=0; iparameters->child; + bool is8bit = false; while (paramObj) { aJsonObject *regObj = aJson.getObjectItem(paramObj, "reg"); @@ -207,13 +208,50 @@ int out_Modbus::findRegister(int registerNum, int posInBuffer) { aJsonObject *typeObj = aJson.getObjectItem(paramObj, "type"); aJsonObject *mapObj = aJson.getObjectItem(paramObj, "map"); + aJsonObject * itemParametersObj = aJson.getArrayItem(item->itemArg, 2); uint16_t data = node.getResponseBuffer(posInBuffer); - debugSerial << F("MB got ")<name<type == aJson_String) regType=str2regSize(typeObj->valuestring); + switch(regType) { + + case PAR_I16: + isSigned=true; + case PAR_U16: + param=data; + break; + case PAR_I32: + isSigned=true; + case PAR_U32: + param = data | (node.getResponseBuffer(posInBuffer+1)<<16); + break; + case PAR_U8L: + is8bit=true; + param = data & 0xFF; + break; + case PAR_U8H: + is8bit=true; + param = data << 8; + } + + if (mapObj && (mapObj->type==aJson_Array || mapObj->type==aJson_Object)) + mappedParam = mapInt(param,mapObj); + else mappedParam.Int(param); + + if (itemParametersObj && itemParametersObj->type ==aJson_Object) + { + aJsonObject *execObj = aJson.getObjectItem(itemParametersObj,paramObj->name); + if (execObj) executeCommand(execObj, -1, mappedParam); + } + debugSerial << F("MB got ")<name<next; } -return 0; +return is8bit; } int out_Modbus::Poll(short cause) diff --git a/lighthub/textconst.h b/lighthub/textconst.h index 4acc0ad..bfe3a9e 100644 --- a/lighthub/textconst.h +++ b/lighthub/textconst.h @@ -71,7 +71,9 @@ const char freeheap_P[] PROGMEM = "freeheap"; */ + //Commands + const char ON_P[] PROGMEM = "ON"; const char OFF_P[] PROGMEM = "OFF"; const char REST_P[] PROGMEM = "REST"; @@ -79,6 +81,7 @@ const char TOGGLE_P[] PROGMEM = "TOGGLE"; const char HALT_P[] PROGMEM = "HALT"; const char XON_P[] PROGMEM = "XON"; const char XOFF_P[] PROGMEM = "XOFF"; +/* const char INCREASE_P[] PROGMEM = "INCREASE"; const char DECREASE_P[] PROGMEM = "DECREASE"; const char TRUE_P[] PROGMEM = "TRUE"; @@ -86,15 +89,20 @@ const char FALSE_P[] PROGMEM = "FALSE"; const char ENABLED_P[] PROGMEM = "ENABLED"; const char DISABLED_P[] PROGMEM = "DISABLED"; - +*/ const char HEAT_P[] PROGMEM = "HEAT"; const char COOL_P[] PROGMEM = "COOL"; const static char AUTO_P[] PROGMEM = "AUTO"; + + const char FAN_ONLY_P[] PROGMEM = "FAN_ONLY"; const char DRY_P[] PROGMEM = "DRY"; const char HIGH_P[] PROGMEM = "HIGH"; const char MED_P[] PROGMEM = "MEDIUM"; const char LOW_P[] PROGMEM = "LOW"; + + + // SubTopics const char SET_P[] PROGMEM = "set"; const char CMD_P[] PROGMEM = "cmd"; @@ -102,13 +110,7 @@ const char MODE_P[] PROGMEM = "mode"; const char FAN_P[] PROGMEM = "fan"; const char HUE_P[] PROGMEM = "hue"; const char SAT_P[] PROGMEM = "sat"; -/* -const char TEMP_P[] PROGMEM = "temp"; -const char SETPOINT_P[] PROGMEM = "setpoint"; -const char POWER_P[] PROGMEM = "power"; -const char VOL_P[] PROGMEM = "vol"; -const char HEAT_P[] PROGMEM = "heat"; -*/ + const char HSV_P[] PROGMEM = "HSV"; const char RGB_P[] PROGMEM = "RGB"; diff --git a/lighthub/utils.cpp b/lighthub/utils.cpp index 713d5be..ba8918e 100644 --- a/lighthub/utils.cpp +++ b/lighthub/utils.cpp @@ -521,7 +521,17 @@ bool isTimeOver(uint32_t timestamp, uint32_t currTime, uint32_t time, uint32_t m } -bool executeCommand(aJsonObject* cmd, int8_t toggle, char* defCmd) + + +bool executeCommand(aJsonObject* cmd, int8_t toggle) +{ + itemCmd _itemCmd; + _itemCmd.type = ST_VOID; + return executeCommand(cmd,toggle,_itemCmd); +} + +bool executeCommand(aJsonObject* cmd, int8_t toggle, itemCmd _itemCmd) +//bool executeCommand(aJsonObject* cmd, int8_t toggle, char* defCmd) { switch (cmd->type) { @@ -533,7 +543,7 @@ switch (cmd->type) aJsonObject * command = cmd->child; while (command) { - executeCommand(command,toggle,defCmd); + executeCommand(command,toggle,_itemCmd); command = command->next; } configLocked--; @@ -561,12 +571,13 @@ switch (toggle) } char * itemCommand; +char Buffer[16]; if(icmd && icmd->type == aJson_String) itemCommand = icmd->valuestring; - else itemCommand = defCmd; + else itemCommand = _itemCmd.toString(Buffer,sizeof(Buffer)); char * emitCommand; if(ecmd && ecmd->type == aJson_String) emitCommand = ecmd->valuestring; - else emitCommand = defCmd; + else emitCommand = _itemCmd.toString(Buffer,sizeof(Buffer)); //debugSerial << F("IN:") << (pin) << F(" : ") <valuestring<< F(" -> ")< #include "aJSON.h" #include "options.h" +#include "item.h" #ifdef WITH_PRINTEX_LIB #include "PrintEx.h" using namespace ios; @@ -60,4 +61,7 @@ void printUlongValueToStr(char *valstr, unsigned long value); void scan_i2c_bus(); void softRebootFunc(); bool isTimeOver(uint32_t timestamp, uint32_t currTime, uint32_t time, uint32_t modulo = 0xFFFFFFFF); -bool executeCommand(aJsonObject* cmd, int8_t toggle = -1, char* defCmd = NULL); +//bool executeCommand(aJsonObject* cmd, int8_t toggle = -1, char* defCmd = NULL); +bool executeCommand(aJsonObject* cmd, int8_t toggle = -1); +bool executeCommand(aJsonObject* cmd, int8_t toggle, itemCmd _itemCmd); +itemCmd mapInt(int32_t arg, aJsonObject* map);