diff --git a/tasmota/xdrv_10_scripter.ino b/tasmota/xdrv_10_scripter.ino index 326c0df47..042478b07 100755 --- a/tasmota/xdrv_10_scripter.ino +++ b/tasmota/xdrv_10_scripter.ino @@ -7872,6 +7872,8 @@ bool Xdrv10(uint8_t function) Webserver->on("/exs", HTTP_POST,[]() { Webserver->sendHeader("Location","/exs");Webserver->send(303);}, script_upload_start); Webserver->on("/exs", HTTP_GET, ScriptExecuteUploadSuccess); #endif // USE_WEBSERVER + break; + case FUNC_SAVE_BEFORE_RESTART: if (bitRead(Settings.rule_enabled, 0)) { Run_Scripter(">R", 2, 0); diff --git a/tasmota/xsns_46_MLX90614.ino b/tasmota/xsns_46_MLX90614.ino index 8032cdf2f..3cdb1dda6 100644 --- a/tasmota/xsns_46_MLX90614.ino +++ b/tasmota/xsns_46_MLX90614.ino @@ -50,13 +50,15 @@ void MLX90614_Init(void) void MLX90614_Every_Second(void) { - mlx90614.i2c_buf = I2cRead24(I2_ADR_IRT, MLX90614_TOBJ1); + //mlx90614.i2c_buf = I2cRead24(I2_ADR_IRT, MLX90614_TOBJ1); + mlx90614.value = MLX90614_read16(I2_ADR_IRT, MLX90614_TOBJ1); if (mlx90614.value & 0x8000) { mlx90614.obj_temp = -999; } else { mlx90614.obj_temp = ((float)mlx90614.value * 0.02) - 273.15; } - mlx90614.i2c_buf = I2cRead24(I2_ADR_IRT,MLX90614_TA); + //mlx90614.i2c_buf = I2cRead24(I2_ADR_IRT,MLX90614_TA); + mlx90614.value = MLX90614_read16(I2_ADR_IRT, MLX90614_TA); if (mlx90614.value & 0x8000) { mlx90614.amb_temp = -999; } else { @@ -86,6 +88,51 @@ void MLX90614_Show(uint8_t json) } } +uint16_t MLX90614_read16(uint8_t addr, uint8_t a) { + uint16_t ret; + + Wire.beginTransmission(addr); + Wire.write(a); + Wire.endTransmission(false); + + Wire.requestFrom(addr, (size_t)3); + uint8_t buff[5]; + buff[0] = addr << 1; + buff[1] = a; + buff[2] = (addr << 1) | 1; + buff[3] = Wire.read(); + buff[4] = Wire.read(); + ret = buff[3] | (buff[4] << 8); + uint8_t pec = Wire.read(); + uint8_t cpec = MLX90614_crc8(buff, sizeof(buff)); + //AddLog(LOG_LEVEL_INFO,PSTR("%x - %x"),pec, cpec); + + if (pec != cpec) { + AddLog(LOG_LEVEL_INFO,PSTR("mlx checksum error")); + } + return ret; +} + + +uint8_t MLX90614_crc8(uint8_t *addr, uint8_t len) +// The PEC calculation includes all bits except the START, REPEATED START, STOP, +// ACK, and NACK bits. The PEC is a CRC-8 with polynomial X8+X2+X1+1. +{ + uint8_t crc = 0; + while (len--) { + uint8_t inbyte = *addr++; + for (uint8_t i = 8; i; i--) { + uint8_t carry = (crc ^ inbyte) & 0x80; + crc <<= 1; + if (carry) + crc ^= 0x7; + inbyte <<= 1; + } + } + return crc; +} + + /*********************************************************************************************\ * Interface \*********************************************************************************************/ diff --git a/tasmota/xsns_53_sml.ino b/tasmota/xsns_53_sml.ino index 4b9ccc1e8..0a300b96f 100755 --- a/tasmota/xsns_53_sml.ino +++ b/tasmota/xsns_53_sml.ino @@ -2293,8 +2293,26 @@ dddef_exit: script_meter_desc[index].type = *lp; lp++; if (*lp != ',') { - script_meter_desc[index].sopt = *lp&7; - lp++; + switch (*lp) { + case 'N': + lp++; + script_meter_desc[index].sopt = 0x10 | (*lp & 3); + lp++; + break; + case 'E': + lp++; + script_meter_desc[index].sopt = 0x20 | (*lp & 3); + lp++; + break; + case 'O': + lp++; + script_meter_desc[index].sopt = 0x30 | (*lp & 3); + lp++; + break; + default: + script_meter_desc[index].sopt = *lp&7; + lp++; + } } else { script_meter_desc[index].sopt = 0; } @@ -2491,15 +2509,36 @@ init10: #endif SerialConfig smode = SERIAL_8N1; - if (meter_desc_p[meters].sopt == 2) { - smode = SERIAL_8N2; - } - if (meter_desc_p[meters].type=='M') { - smode = SERIAL_8E1; + + if (meter_desc_p[meters].sopt & 0xf0) { + // new serial config + switch (meter_desc_p[meters].sopt >> 4) { + case 1: + if ((meter_desc_p[meters].sopt & 1) == 1) smode = SERIAL_8N1; + else smode = SERIAL_8N2; + break; + case 2: + if ((meter_desc_p[meters].sopt & 1) == 1) smode = SERIAL_8E1; + else smode = SERIAL_8E2; + break; + case 3: + if ((meter_desc_p[meters].sopt & 1) == 1) smode = SERIAL_8O1; + else smode = SERIAL_8O2; + break; + } + } else { + // depecated serial config if (meter_desc_p[meters].sopt == 2) { - smode = SERIAL_8E2; + smode = SERIAL_8N2; + } + if (meter_desc_p[meters].type=='M') { + smode = SERIAL_8E1; + if (meter_desc_p[meters].sopt == 2) { + smode = SERIAL_8E2; + } } } + #ifdef ESP8266 if (meter_ss[meters]->begin(meter_desc_p[meters].params)) { meter_ss[meters]->flush();