diff --git a/src/AmsConfiguration.cpp b/src/AmsConfiguration.cpp index 7f41b14c..919dd102 100644 --- a/src/AmsConfiguration.cpp +++ b/src/AmsConfiguration.cpp @@ -232,6 +232,8 @@ bool AmsConfiguration::getDebugConfig(DebugConfig& config) { } bool AmsConfiguration::setDebugConfig(DebugConfig& config) { + if(!config.serial && !config.telnet) + config.level = 5; // Force error level when debug is disabled EEPROM.begin(EEPROM_SIZE); EEPROM.put(CONFIG_DEBUG_START, config); bool ret = EEPROM.commit(); diff --git a/src/AmsDataStorage.cpp b/src/AmsDataStorage.cpp index 27f07dca..e401bf7b 100644 --- a/src/AmsDataStorage.cpp +++ b/src/AmsDataStorage.cpp @@ -158,9 +158,9 @@ bool AmsDataStorage::update(AmsData* data) { } if(month.lastMeterReadTime > now) { - if(debugger->isActive(RemoteDebug::WARNING)) { +// if(debugger->isActive(RemoteDebug::WARNING)) { debugger->printf("(AmsDataStorage) Invalid future timestamp for month plot, resetting\n"); - } +// } month.activeImport = data->getActiveImportCounter() * 1000; month.activeExport = data->getActiveExportCounter() * 1000; month.lastMeterReadTime = now; @@ -171,18 +171,18 @@ bool AmsDataStorage::update(AmsData* data) { month.activeImport = data->getActiveImportCounter() * 1000; month.activeExport = data->getActiveExportCounter() * 1000; month.lastMeterReadTime = now; - if(debugger->isActive(RemoteDebug::WARNING)) { +// if(debugger->isActive(RemoteDebug::WARNING)) { debugger->printf("(AmsDataStorage) Too long since last month update, clearing data\n"); - } +// } for(int i = 1; i<=31; i++) { setDay(i, 0); } } else if(now - month.lastMeterReadTime < 87000) { int32_t val = (month.activeImport == 0 ? 0 : ((data->getActiveImportCounter() * 1000) - month.activeImport) - ((data->getActiveExportCounter() * 1000) - month.activeExport)); - if(debugger->isActive(RemoteDebug::INFO)) { +// if(debugger->isActive(RemoteDebug::INFO)) { debugger->printf("(AmsDataStorage) Usage for day %d: %d\n", tm.Day, val); - } +// } time_t yesterday = now - 3600; breakTime(yesterday, tm); @@ -198,9 +198,12 @@ bool AmsDataStorage::update(AmsData* data) { float iph = im / hrs; float eph = ex / hrs; - if(debugger->isActive(RemoteDebug::DEBUG)) { + // There is something wacky going on when it ends up here. The total value (im) is way way lower than it should be, which in + // turn causes low values for all estimates. And then when it returns to the normal case above, the value is waaay higher. + +// if(debugger->isActive(RemoteDebug::DEBUG)) { debugger->printf("(AmsDataStorage) Since last month update, hours: %.1f, import: %d (%.2f/hr), export: %d (%.2f/hr)\n", hrs, im, iph, ex, eph); - } +// } // Make sure last month read is at midnight if(tz != NULL) { @@ -209,9 +212,9 @@ bool AmsDataStorage::update(AmsData* data) { breakTime(month.lastMeterReadTime, tm); } month.lastMeterReadTime = month.lastMeterReadTime - (tm.Hour * 3600) - (tm.Minute * 60) - tm.Second; - if(debugger->isActive(RemoteDebug::DEBUG)) { - debugger->printf("(AmsDataStorage) Last month read after resetting to midnight: %lu", month.lastMeterReadTime); - } +// if(debugger->isActive(RemoteDebug::DEBUG)) { + debugger->printf("(AmsDataStorage) Last month read after resetting to midnight: %lu\n", month.lastMeterReadTime); +// } if(tz != NULL) { breakTime(tz->toLocal(now), tm); @@ -232,9 +235,9 @@ bool AmsDataStorage::update(AmsData* data) { float val = ((iph * hours) - (eph * hours)); setDay(last.Day, val); - if(debugger->isActive(RemoteDebug::INFO)) { +// if(debugger->isActive(RemoteDebug::INFO)) { debugger->printf("(AmsDataStorage) Estimated usage for day %u: %.1f (%lu)\n", last.Day, val, cur); - } +// } month.activeImport += iph * hours; month.activeExport += eph * hours; diff --git a/src/AmsToMqttBridge.ino b/src/AmsToMqttBridge.ino index c596f566..590cc182 100644 --- a/src/AmsToMqttBridge.ino +++ b/src/AmsToMqttBridge.ino @@ -13,7 +13,9 @@ */ #if defined(ESP8266) ADC_MODE(ADC_VCC); -#else if defined(ESP32) +#endif + +#if defined(ESP32) #include #endif #define WDT_TIMEOUT 10 diff --git a/src/IEC6205675.cpp b/src/IEC6205675.cpp index cdfe8df4..3f7d5935 100644 --- a/src/IEC6205675.cpp +++ b/src/IEC6205675.cpp @@ -3,7 +3,6 @@ #include "Timezone.h" IEC6205675::IEC6205675(const char* d, uint8_t useMeterType, uint8_t distributionSystem, CosemDateTime packageTimestamp, HDLCConfig* hc) { - uint32_t ui; double val; char str[64]; @@ -13,8 +12,8 @@ IEC6205675::IEC6205675(const char* d, uint8_t useMeterType, uint8_t distribution this->packageTimestamp = getTimestamp(packageTimestamp); - ui = getNumber(AMS_OBIS_ACTIVE_IMPORT, sizeof(AMS_OBIS_ACTIVE_IMPORT), ((char *) (d))); - if(ui == 0xFFFFFFFF) { + val = getNumber(AMS_OBIS_ACTIVE_IMPORT, sizeof(AMS_OBIS_ACTIVE_IMPORT), ((char *) (d))); + if(val == NOVALUE) { CosemData* data = getCosemDataAt(1, ((char *) (d))); // Kaifa special case... @@ -137,7 +136,7 @@ IEC6205675::IEC6205675(const char* d, uint8_t useMeterType, uint8_t distribution // Kaifa end } else { listType = 1; - activeImportPower = ui; + activeImportPower = val; meterType = AmsTypeUnknown; CosemData* version = findObis(AMS_OBIS_VERSION, sizeof(AMS_OBIS_VERSION), d); @@ -166,95 +165,96 @@ IEC6205675::IEC6205675(const char* d, uint8_t useMeterType, uint8_t distribution this->packageTimestamp = this->packageTimestamp > 0 ? tz.toUTC(this->packageTimestamp) : 0; } - ui = getString(AMS_OBIS_VERSION, sizeof(AMS_OBIS_VERSION), ((char *) (d)), str); - if(ui > 0) { + uint8_t str_len = 0; + str_len = getString(AMS_OBIS_VERSION, sizeof(AMS_OBIS_VERSION), ((char *) (d)), str); + if(str_len > 0) { listId = String(str); } - ui = getNumber(AMS_OBIS_ACTIVE_EXPORT, sizeof(AMS_OBIS_ACTIVE_EXPORT), ((char *) (d))); - if(ui != 0xFFFFFFFF) { - activeExportPower = ui; + val = getNumber(AMS_OBIS_ACTIVE_EXPORT, sizeof(AMS_OBIS_ACTIVE_EXPORT), ((char *) (d))); + if(val != NOVALUE) { + activeExportPower = val; } - ui = getNumber(AMS_OBIS_REACTIVE_IMPORT, sizeof(AMS_OBIS_REACTIVE_IMPORT), ((char *) (d))); - if(ui != 0xFFFFFFFF) { - reactiveImportPower = ui; + val = getNumber(AMS_OBIS_REACTIVE_IMPORT, sizeof(AMS_OBIS_REACTIVE_IMPORT), ((char *) (d))); + if(val != NOVALUE) { + reactiveImportPower = val; } - ui = getNumber(AMS_OBIS_REACTIVE_EXPORT, sizeof(AMS_OBIS_REACTIVE_EXPORT), ((char *) (d))); - if(ui != 0xFFFFFFFF) { - reactiveExportPower = ui; + val = getNumber(AMS_OBIS_REACTIVE_EXPORT, sizeof(AMS_OBIS_REACTIVE_EXPORT), ((char *) (d))); + if(val != NOVALUE) { + reactiveExportPower = val; } val = getNumber(AMS_OBIS_VOLTAGE_L1, sizeof(AMS_OBIS_VOLTAGE_L1), ((char *) (d))); - if(val != 0xFFFFFFFF) { + if(val != NOVALUE) { listType = 2; l1voltage = val; } val = getNumber(AMS_OBIS_VOLTAGE_L2, sizeof(AMS_OBIS_VOLTAGE_L2), ((char *) (d))); - if(val != 0xFFFFFFFF) { + if(val != NOVALUE) { listType = 2; l2voltage = val; } val = getNumber(AMS_OBIS_VOLTAGE_L3, sizeof(AMS_OBIS_VOLTAGE_L3), ((char *) (d))); - if(val != 0xFFFFFFFF) { + if(val != NOVALUE) { listType = 2; l3voltage = val; } val = getNumber(AMS_OBIS_CURRENT_L1, sizeof(AMS_OBIS_CURRENT_L1), ((char *) (d))); - if(val != 0xFFFFFFFF) { + if(val != NOVALUE) { listType = 2; l1current = val; } val = getNumber(AMS_OBIS_CURRENT_L2, sizeof(AMS_OBIS_CURRENT_L2), ((char *) (d))); - if(val != 0xFFFFFFFF) { + if(val != NOVALUE) { listType = 2; l2current = val; } val = getNumber(AMS_OBIS_CURRENT_L3, sizeof(AMS_OBIS_CURRENT_L3), ((char *) (d))); - if(val != 0xFFFFFFFF) { + if(val != NOVALUE) { listType = 2; l3current = val; } val = getNumber(AMS_OBIS_ACTIVE_IMPORT_COUNT, sizeof(AMS_OBIS_ACTIVE_IMPORT_COUNT), ((char *) (d))); - if(val != 0xFFFFFFFF) { + if(val != NOVALUE) { listType = 3; activeImportCounter = val / 1000.0; } val = getNumber(AMS_OBIS_ACTIVE_EXPORT_COUNT, sizeof(AMS_OBIS_ACTIVE_EXPORT_COUNT), ((char *) (d))); - if(val != 0xFFFFFFFF) { + if(val != NOVALUE) { listType = 3; activeExportCounter = val / 1000.0; } val = getNumber(AMS_OBIS_REACTIVE_IMPORT_COUNT, sizeof(AMS_OBIS_REACTIVE_IMPORT_COUNT), ((char *) (d))); - if(val != 0xFFFFFFFF) { + if(val != NOVALUE) { listType = 3; reactiveImportCounter = val / 1000.0; } val = getNumber(AMS_OBIS_REACTIVE_EXPORT_COUNT, sizeof(AMS_OBIS_REACTIVE_EXPORT_COUNT), ((char *) (d))); - if(val != 0xFFFFFFFF) { + if(val != NOVALUE) { listType = 3; reactiveExportCounter = val / 1000.0; } - ui = getString(AMS_OBIS_METER_MODEL, sizeof(AMS_OBIS_METER_MODEL), ((char *) (d)), str); - if(ui > 0) { + str_len = getString(AMS_OBIS_METER_MODEL, sizeof(AMS_OBIS_METER_MODEL), ((char *) (d)), str); + if(str_len > 0) { meterModel = String(str); } else { - ui = getString(AMS_OBIS_METER_MODEL_2, sizeof(AMS_OBIS_METER_MODEL_2), ((char *) (d)), str); - if(ui > 0) { + str_len = getString(AMS_OBIS_METER_MODEL_2, sizeof(AMS_OBIS_METER_MODEL_2), ((char *) (d)), str); + if(str_len > 0) { meterModel = String(str); } } - ui = getString(AMS_OBIS_METER_ID, sizeof(AMS_OBIS_METER_ID), ((char *) (d)), str); - if(ui > 0) { + str_len = getString(AMS_OBIS_METER_ID, sizeof(AMS_OBIS_METER_ID), ((char *) (d)), str); + if(str_len > 0) { meterId = String(str); } else { - ui = getString(AMS_OBIS_METER_ID_2, sizeof(AMS_OBIS_METER_ID_2), ((char *) (d)), str); - if(ui > 0) { + str_len = getString(AMS_OBIS_METER_ID_2, sizeof(AMS_OBIS_METER_ID_2), ((char *) (d)), str); + if(str_len > 0) { meterId = String(str); } } @@ -271,19 +271,19 @@ IEC6205675::IEC6205675(const char* d, uint8_t useMeterType, uint8_t distribution } val = getNumber(AMS_OBIS_POWER_FACTOR, sizeof(AMS_OBIS_POWER_FACTOR), ((char *) (d))); - if(val != 0xFFFFFFFF) { + if(val != NOVALUE) { powerFactor = val; } val = getNumber(AMS_OBIS_POWER_FACTOR_L1, sizeof(AMS_OBIS_POWER_FACTOR_L1), ((char *) (d))); - if(val != 0xFFFFFFFF) { + if(val != NOVALUE) { l1PowerFactor = val; } val = getNumber(AMS_OBIS_POWER_FACTOR_L2, sizeof(AMS_OBIS_POWER_FACTOR_L2), ((char *) (d))); - if(val != 0xFFFFFFFF) { + if(val != NOVALUE) { l2PowerFactor = val; } val = getNumber(AMS_OBIS_POWER_FACTOR_L3, sizeof(AMS_OBIS_POWER_FACTOR_L3), ((char *) (d))); - if(val != 0xFFFFFFFF) { + if(val != NOVALUE) { l3PowerFactor = val; } @@ -335,14 +335,15 @@ IEC6205675::IEC6205675(const char* d, uint8_t useMeterType, uint8_t distribution } threePhase = l1voltage > 0 && l2voltage > 0 && l3voltage > 0; - twoPhase = (l1voltage > 0 && l2voltage > 0) || (l2voltage > 0 && l3voltage > 0) || (l3voltage > 0 && l1voltage > 0); + if(!threePhase) + twoPhase = (l1voltage > 0 && l2voltage > 0) || (l2voltage > 0 && l3voltage > 0) || (l3voltage > 0 && l1voltage > 0); // Special case for Norwegian IT/TT meters that does not report all values if(distributionSystem == 1) { if(threePhase) { if(l2current == 0.0 && l1current > 0.0 && l3current > 0.0) { l2current = (((activeImportPower - activeExportPower) * sqrt(3)) - (l1voltage * l1current) - (l3voltage * l3current)) / l2voltage; - if(activeExportPower == 0) { + if(activeExportPower == 0.0) { l2current = max((float) 0.0, l2current); } } @@ -453,31 +454,39 @@ double IEC6205675::getNumber(uint8_t* obis, int matchlength, const char* ptr) { } double IEC6205675::getNumber(CosemData* item) { - double val = 0xFFFFFFFF; if(item != NULL) { + double ret = 0.0; char* pos = ((char*) item); switch(item->base.type) { - case CosemTypeLongUnsigned: - val = ntohs(item->lu.data); + case CosemTypeLongUnsigned: { + uint16_t u16 = ntohs(item->lu.data); + ret = u16; pos += 3; break; - case CosemTypeDLongUnsigned: - val = ntohl(item->dlu.data); + } + case CosemTypeDLongUnsigned: { + uint32_t u32 = ntohl(item->dlu.data); + ret = u32; pos += 5; break; - case CosemTypeLongSigned: - val = ntohs(item->lu.data); + } + case CosemTypeLongSigned: { + uint16_t u16 = ntohs(item->lu.data); // ntohs only works for uint16 ? + int16_t i16 = u16; // Cast to int16 before use? + ret = i16; // Who knows, got to try it all... pos += 3; break; + } } if(pos != NULL) { if(*pos++ == 0x02 && *pos++ == 0x02) { int8_t scale = *++pos; - val *= pow(10, scale); + ret *= pow(10, scale); } } + return ret; } - return val; + return NOVALUE; } time_t IEC6205675::getTimestamp(uint8_t* obis, int matchlength, const char* ptr) { diff --git a/src/IEC6205675.h b/src/IEC6205675.h index c5869aef..fabd7211 100644 --- a/src/IEC6205675.h +++ b/src/IEC6205675.h @@ -4,6 +4,8 @@ #include "AmsData.h" #include "ams/hdlc.h" +#define NOVALUE 0xFFFFFFFF + struct AmsOctetTimestamp { uint8_t type; CosemDateTime dt; diff --git a/src/web/AmsWebServer.cpp b/src/web/AmsWebServer.cpp index 7957eea6..3e878a28 100644 --- a/src/web/AmsWebServer.cpp +++ b/src/web/AmsWebServer.cpp @@ -14,6 +14,10 @@ #define HEAD_HTML_LEN HEAD32_HTML_LEN #endif +#if defined(ESP32) +#include +#endif + #include "root/foot_html.h" #include "root/index_html.h" #include "root/application_js.h" @@ -322,9 +326,6 @@ void AmsWebServer::indexHtml() { for(int i = 0; i<255; i++) { html.replace("${config.boardType" + String(i) + "}", sys.boardType == i ? "selected" : ""); } - for(int i = 0; i<5; i++) { - html.replace("${config.meterType" + String(i) + "}", sys.boardType == i ? "selected" : ""); - } html.replace("${config.wifiSsid}", wifi.ssid); html.replace("${config.wifiPassword}", wifi.psk); html.replace("${config.wifiStaticIp}", strlen(wifi.ip) > 0 ? "checked" : ""); @@ -1561,6 +1562,12 @@ void AmsWebServer::firmwareUpload() { String filename = upload.filename; if(!filename.endsWith(".bin")) { server.send(500, "text/plain", "500: couldn't create file"); + } else { + #if defined(ESP32) + esp_task_wdt_deinit(); + #elif defined(ESP8266) + ESP.wdtDisable(); + #endif } } uploadFile(FILE_FIRMWARE);