mirror of
https://github.com/jomjol/AI-on-the-edge-device.git
synced 2025-12-07 12:06:58 +03:00
v15.2.0 (#2345)
* Testcase for #2145 and debug-log (#2151) * new models ana-cont-11.0.5, ana-class100-1.5.7, dig-class100-1.6.0 * Testcase for #2145 Added debug log, if allowNegativeRates is handeled * Fix timezone config parser (#2169) * make sure to parse the whole config line * fix crash on empty timezone parameter --------- Co-authored-by: CaCO3 <caco@ruinelli.ch> * Enhance ROI pages (#2161) * Check if the ROIs are equidistant. Only if not, untick the checkbox * renaming * Check if the ROIs have same y, dy and dx. If so, tick the sync checkbox * only allow editing space when box is checked * fix sync check * show inner frame on all ROIs * cleanup * Check if the ROIs have same dy and dx. If so, tick the sync checkbox * checkbox position * renaming * renaming * show inner frame and cross hairs on all ROIs * update ROIs on ticking checkboxes * show timezone hint * fix deleting last ROI * cleanup --------- Co-authored-by: CaCO3 <caco@ruinelli.ch> * restart timeout on progress, catch error (#2170) * restart timeout on progress, catch error * . --------- Co-authored-by: CaCO3 <caco@ruinelli.ch> * BugFix #2167 * Release 15.1 preparations (#2171) * Update Changelog.md * Update Changelog.md * Update Changelog.md * Update changelog * Fix links to PR * Formating * Update Changelog.md * Update Changelog.md * Update Changelog.md * Update Changelog.md * Update Changelog.md * Update Changelog.md * Update Changelog.md * Update Changelog.md * Update Changelog.md * Update Changelog.md * Update Changelog.md * Update Changelog.md --------- Co-authored-by: Slider0007 <jobbelle@gmx.net> Co-authored-by: Slider0007 <115730895+Slider0007@users.noreply.github.com> * fix typo * Replace relative documentation links with absolute ones pointing to the external documentation (#2180) Co-authored-by: CaCO3 <caco@ruinelli.ch> * Sort model files in configuration combobox (#2189) * new models ana-cont-11.0.5, ana-class100-1.5.7, dig-class100-1.6.0 * Testcase for #2145 Added debug log, if allowNegativeRates is handeled * Sort model files in combobox * reboot task - increase stack size (#2201) Avoid stack overflow * Update interface_influxdb.cpp * Update Changelog.md * Show PSRAM usage (#2206) * centralize PSRAM usage (application code only) * update logging * update logging * fix use after free * initialize buffer * free rgb_image before ussing it for new allocation * use wrapper function * switch log level to debug * . * undo adding free() calls * . * add names to all CImage instances * . * . * . * revert changes of stbi_image_free() with free_psram_heap() on the places where is is not in PSRAM * . * typos * typo * Added MQTT Outbox explanation/warning * added CONFIG_SPIRAM_USE_MEMMAP explanation --------- Co-authored-by: CaCO3 <caco@ruinelli.ch> * Disable custom MQTT Outbox. This also moves the MQTT Publishing memory usage back to the internal RAM! * log MQTT connection refused reasons (#2216) * Revert PSRAM usage as it lead to memory fragmentation. See https://github.com/jomjol/AI-on-the-edge-device/issues/2200 for details * fix missing value data * Revert PSRAM usage as it lead to memory fragmentation. (#2224) See https://github.com/jomjol/AI-on-the-edge-device/issues/2200 for details Co-authored-by: CaCO3 <caco@ruinelli.ch> * Fix missing value data in graph (#2230) * fix missing value data --------- Co-authored-by: CaCO3 <caco@ruinelli.ch> * Update Changelog.md (#2231) * Update interface_influxdb.cpp (#2233) * update copyright year * Cleanup * Set prevalue using MQTT + set prevalue to RAW value (REST+MQTT) (#2252) * Use double instead of float * Error handling + set to RAW if newvalue < 0 * REST SetPrevalue: Set to RAW if newvalue < 0 * set prevalue with MQTT * removed the stb_image files and re-add them as a submodule. (#2223) - stb_image.h: Version update 2.25 -> 2.28 - stb_resize.h: Version update 0.96 -> 0.97 - stb_write.h: Version update 1.14 -> 1.16 Co-authored-by: CaCO3 <caco@ruinelli.ch> * Remove obsolete ClassFlowWriteList (#2264) * Renaming & cleanup of some modules / functions in source code (#2265) * Rename module tag name * Rename server_tflite.cpp -> MainFlowControl.cpp * Remove redundandant MQTTMainTopic function * Update * Remove obsolete GetMQTTMainTopic * Fix last element missing in digit model drop down (#2282) * Debug influxdb (#2283) * Fix time offset issues in InfluxDB component. (#2278) Closes #2273 Closes #2150 * Update interface_influxdb.cpp * Update interface_influxdb.cpp * Improve Logging * Implement TimeSync at beginning * Update time_sntp.cpp * Update time_sntp.cpp * Set Time After WLAN Init --------- Co-authored-by: Antonin Delpeuch <antonin@delpeuch.eu> * Implement a camera livestream handler (#2286) * fix leading NaN (#2310) * analogROI: Activate save button after ROI creation (#2326) * Migration of PlatformIO 5.2.0 to 6.1.0 (resp. ESP IDF from 4.4.2 to 5.0.1) (#2305) * Migration to PlatformIO 6.1.0 * Disable RMTMEM usage as it is no longer allowed -> Smart LEDs not functional! * moved miniz into subfolder of jomjol_fileserver_ota, else it does not build anymore. * cleanup * fix leading NaN (#2310) * Migration to PlatformIO 6.1.0 * Disable RMTMEM usage as it is no longer allowed -> Smart LEDs not functional! * moved miniz into subfolder of jomjol_fileserver_ota, else it does not build anymore. * cleanup * Task watchdog has new config name * Fix return value check. It must be something else than ESP_FAIL, but it does not need to be ESP_OK! * add missing strucures to work around new RMTMEM restriction (untested) --------- Co-authored-by: CaCO3 <caco@ruinelli.ch> * Keep MainFlowTask alive to handle reboot (#2325) * Shared PSRAM memory (#2285) * enable PSRAM logging * add extra functions for psram shared memroy handling * CImageBasis objects still should used dynamic memory (eg. rawImage), haw ever tmpImage must be placed inside the shared memory * Place all STBI allocs inside the shared memory * The models are placed in the shared PSRAM reagion and must be allocated through the dedicated functions * . * renaming * fix cast warning * add flag to switch STBI PSRAM usage * improve PSRAM shared handling * reserve shared PSRAM as early as possible * init logging eralier so we can use it in PSRAM shared alloc * move Wifi_LWIP, BSS_SEG and MQTT Outbox into PSRAM to ffree internal memory * Check if model fits into reserved shared memory * Update code/components/jomjol_tfliteclass/CTfLiteClass.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_flowcontroll/ClassFlowControll.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_image_proc/CImageBasis.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * . * . * . * . * Korrektur Merge Conflict in main.cpp --------- Co-authored-by: CaCO3 <caco@ruinelli.ch> Co-authored-by: jomjol <30766535+jomjol@users.noreply.github.com> * fix PSRAM init return value check * Extend InfluxDBv1 with individual topic names (#2319) * Implement individual influx topic * Update interface_influxdb.cpp * Update interface_influxdb.cpp * Update FieldName * analogROI: Activate save button after ROI creation (#2326) * Migration of PlatformIO 5.2.0 to 6.1.0 (resp. ESP IDF from 4.4.2 to 5.0.1) (#2305) * Migration to PlatformIO 6.1.0 * Disable RMTMEM usage as it is no longer allowed -> Smart LEDs not functional! * moved miniz into subfolder of jomjol_fileserver_ota, else it does not build anymore. * cleanup * fix leading NaN (#2310) * Migration to PlatformIO 6.1.0 * Disable RMTMEM usage as it is no longer allowed -> Smart LEDs not functional! * moved miniz into subfolder of jomjol_fileserver_ota, else it does not build anymore. * cleanup * Task watchdog has new config name * Fix return value check. It must be something else than ESP_FAIL, but it does not need to be ESP_OK! * add missing strucures to work around new RMTMEM restriction (untested) --------- Co-authored-by: CaCO3 <caco@ruinelli.ch> * Keep MainFlowTask alive to handle reboot (#2325) * Shared PSRAM memory (#2285) * enable PSRAM logging * add extra functions for psram shared memroy handling * CImageBasis objects still should used dynamic memory (eg. rawImage), haw ever tmpImage must be placed inside the shared memory * Place all STBI allocs inside the shared memory * The models are placed in the shared PSRAM reagion and must be allocated through the dedicated functions * . * renaming * fix cast warning * add flag to switch STBI PSRAM usage * improve PSRAM shared handling * reserve shared PSRAM as early as possible * init logging eralier so we can use it in PSRAM shared alloc * move Wifi_LWIP, BSS_SEG and MQTT Outbox into PSRAM to ffree internal memory * Check if model fits into reserved shared memory * Update code/components/jomjol_tfliteclass/CTfLiteClass.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_flowcontroll/ClassFlowControll.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_image_proc/CImageBasis.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * Update code/components/jomjol_helper/psram.cpp * . * . * . * . * Korrektur Merge Conflict in main.cpp --------- Co-authored-by: CaCO3 <caco@ruinelli.ch> Co-authored-by: jomjol <30766535+jomjol@users.noreply.github.com> * fix PSRAM init return value check * Extend incl. indiv. Measurement * Implement UX * Update ClassFlowInfluxDBv2.cpp * Implement individual influx topic * Update interface_influxdb.cpp * Update interface_influxdb.cpp * Update FieldName * Extend incl. indiv. Measurement * Implement UX * Update ClassFlowInfluxDBv2.cpp * Update main.cpp --------- Co-authored-by: Slider0007 <115730895+Slider0007@users.noreply.github.com> Co-authored-by: CaCO3 <caco3@ruinelli.ch> Co-authored-by: CaCO3 <caco@ruinelli.ch> * Update Changelog.md (#2344) * Update Changelog.md * Update Changelog.md * merge conflicts * merge conflicts * update changelog --------- Co-authored-by: Frank Haverland <fspapaping@googlemail.com> Co-authored-by: CaCO3 <caco@ruinelli.ch> Co-authored-by: jomjol <30766535+jomjol@users.noreply.github.com> Co-authored-by: Slider0007 <jobbelle@gmx.net> Co-authored-by: Slider0007 <115730895+Slider0007@users.noreply.github.com> Co-authored-by: Antonin Delpeuch <antonin@delpeuch.eu>
This commit is contained in:
@@ -1,5 +1,32 @@
|
||||
#include "SmartLeds.h"
|
||||
|
||||
|
||||
/* PlatformIO 6 (ESP IDF 5) does no longer allow access to RMTMEM,
|
||||
see https://docs.espressif.com/projects/esp-idf/en/latest/esp32/migration-guides/release-5.x/5.0/peripherals.html?highlight=rmtmem#id5
|
||||
As a dirty workaround, we copy the needed structures from rmt_struct.h
|
||||
In the long run, this should be replaced! */
|
||||
typedef struct rmt_item32_s {
|
||||
union {
|
||||
struct {
|
||||
uint32_t duration0 :15;
|
||||
uint32_t level0 :1;
|
||||
uint32_t duration1 :15;
|
||||
uint32_t level1 :1;
|
||||
};
|
||||
uint32_t val;
|
||||
};
|
||||
} rmt_item32_t;
|
||||
|
||||
//Allow access to RMT memory using RMTMEM.chan[0].data32[8]
|
||||
typedef volatile struct rmt_mem_s {
|
||||
struct {
|
||||
rmt_item32_t data32[64];
|
||||
} chan[8];
|
||||
} rmt_mem_t;
|
||||
extern rmt_mem_t RMTMEM;
|
||||
|
||||
|
||||
|
||||
IsrCore SmartLed::_interruptCore = CoreCurrent;
|
||||
intr_handle_t SmartLed::_interruptHandle = NULL;
|
||||
|
||||
|
||||
@@ -35,6 +35,20 @@
|
||||
#include <cassert>
|
||||
#include <cstring>
|
||||
|
||||
#include "esp_idf_version.h"
|
||||
#if (ESP_IDF_VERSION_MAJOR >= 5)
|
||||
#include "soc/periph_defs.h"
|
||||
#include "esp_private/periph_ctrl.h"
|
||||
#include "soc/gpio_sig_map.h"
|
||||
#include "soc/gpio_periph.h"
|
||||
#include "soc/io_mux_reg.h"
|
||||
#include "esp_rom_gpio.h"
|
||||
#define gpio_pad_select_gpio esp_rom_gpio_pad_select_gpio
|
||||
#define gpio_matrix_in(a,b,c) esp_rom_gpio_connect_in_signal(a,b,c)
|
||||
#define gpio_matrix_out(a,b,c,d) esp_rom_gpio_connect_out_signal(a,b,c,d)
|
||||
#define ets_delay_us(a) esp_rom_delay_us(a)
|
||||
#endif
|
||||
|
||||
#if defined ( ARDUINO )
|
||||
extern "C" { // ...someone forgot to put in the includes...
|
||||
#include "esp32-hal.h"
|
||||
@@ -65,6 +79,27 @@
|
||||
#include <stdio.h>
|
||||
#endif
|
||||
|
||||
#if (ESP_IDF_VERSION_MAJOR >= 4) && (ESP_IDF_VERSION_MINOR > 1)
|
||||
#include "hal/gpio_ll.h"
|
||||
#else
|
||||
#include "soc/gpio_periph.h"
|
||||
#define esp_rom_delay_us ets_delay_us
|
||||
static inline int gpio_ll_get_level(gpio_dev_t *hw, int gpio_num)
|
||||
{
|
||||
if (gpio_num < 32) {
|
||||
return (hw->in >> gpio_num) & 0x1;
|
||||
} else {
|
||||
return (hw->in1.data >> (gpio_num - 32)) & 0x1;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(5, 0, 0))
|
||||
#if !(configENABLE_BACKWARD_COMPATIBILITY == 1)
|
||||
#define xSemaphoreHandle SemaphoreHandle_t
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#include "Color.h"
|
||||
|
||||
namespace detail {
|
||||
|
||||
@@ -6,9 +6,6 @@
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "esp_system.h"
|
||||
#include "esp_event.h"
|
||||
|
||||
#include "server_tflite.h"
|
||||
|
||||
#include "esp_log.h"
|
||||
|
||||
@@ -22,8 +19,10 @@
|
||||
#include "ClassLogFile.h"
|
||||
#include "configFile.h"
|
||||
#include "Helper.h"
|
||||
|
||||
#ifdef ENABLE_MQTT
|
||||
#include "interface_mqtt.h"
|
||||
#include "interface_mqtt.h"
|
||||
#include "server_mqtt.h"
|
||||
#endif //ENABLE_MQTT
|
||||
|
||||
|
||||
@@ -331,7 +330,7 @@ bool GpioHandler::readConfig()
|
||||
|
||||
#ifdef ENABLE_MQTT
|
||||
// std::string mainTopicMQTT = "";
|
||||
std::string mainTopicMQTT = GetMQTTMainTopic();
|
||||
std::string mainTopicMQTT = mqttServer_getMainTopic();
|
||||
if (mainTopicMQTT.length() > 0)
|
||||
{
|
||||
mainTopicMQTT = mainTopicMQTT + "/GPIO";
|
||||
|
||||
@@ -4,6 +4,6 @@ list(APPEND EXTRA_COMPONENT_DIRS $ENV{IDF_PATH}/examples/common_components/proto
|
||||
|
||||
idf_component_register(SRCS ${app_sources}
|
||||
INCLUDE_DIRS "."
|
||||
REQUIRES esp32-camera esp_http_server jomjol_logfile jomjol_image_proc nvs_flash jomjol_fileserver_ota jomjol_controlGPIO)
|
||||
REQUIRES esp_timer esp32-camera esp_http_server jomjol_logfile jomjol_image_proc nvs_flash jomjol_fileserver_ota jomjol_controlGPIO)
|
||||
|
||||
|
||||
|
||||
@@ -21,6 +21,7 @@
|
||||
#include <nvs_flash.h>
|
||||
#include <sys/param.h>
|
||||
#include <string.h>
|
||||
#include <sys/stat.h>
|
||||
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
@@ -28,10 +29,31 @@
|
||||
#include "esp_camera.h"
|
||||
|
||||
#include "driver/ledc.h"
|
||||
#include "server_tflite.h"
|
||||
#include "MainFlowControl.h"
|
||||
|
||||
#if (ESP_IDF_VERSION_MAJOR >= 5)
|
||||
#include "soc/periph_defs.h"
|
||||
#include "esp_private/periph_ctrl.h"
|
||||
#include "soc/gpio_sig_map.h"
|
||||
#include "soc/gpio_periph.h"
|
||||
#include "soc/io_mux_reg.h"
|
||||
#include "esp_rom_gpio.h"
|
||||
#define gpio_pad_select_gpio esp_rom_gpio_pad_select_gpio
|
||||
#define gpio_matrix_in(a,b,c) esp_rom_gpio_connect_in_signal(a,b,c)
|
||||
#define gpio_matrix_out(a,b,c,d) esp_rom_gpio_connect_out_signal(a,b,c,d)
|
||||
#define ets_delay_us(a) esp_rom_delay_us(a)
|
||||
#endif
|
||||
|
||||
static const char *TAG = "CAM";
|
||||
|
||||
|
||||
/* Camera live stream */
|
||||
#define PART_BOUNDARY "123456789000000000000987654321"
|
||||
static const char* _STREAM_CONTENT_TYPE = "multipart/x-mixed-replace;boundary=" PART_BOUNDARY;
|
||||
static const char* _STREAM_BOUNDARY = "\r\n--" PART_BOUNDARY "\r\n";
|
||||
static const char* _STREAM_PART = "Content-Type: image/jpeg\r\nContent-Length: %u\r\n\r\n";
|
||||
|
||||
|
||||
static camera_config_t camera_config = {
|
||||
.pin_pwdn = CAM_PIN_PWDN,
|
||||
.pin_reset = CAM_PIN_RESET,
|
||||
@@ -512,7 +534,7 @@ esp_err_t CCamera::CaptureToHTTP(httpd_req_t *req, int delay)
|
||||
esp_camera_fb_return(fb);
|
||||
int64_t fr_end = esp_timer_get_time();
|
||||
|
||||
ESP_LOGI(TAG, "JPG: %uKB %ums", (uint32_t)(fb_len/1024), (uint32_t)((fr_end - fr_start)/1000));
|
||||
ESP_LOGI(TAG, "JPG: %dKB %dms", (int)(fb_len/1024), (int)((fr_end - fr_start)/1000));
|
||||
|
||||
if (delay > 0)
|
||||
LightOnOff(false);
|
||||
@@ -521,6 +543,74 @@ esp_err_t CCamera::CaptureToHTTP(httpd_req_t *req, int delay)
|
||||
}
|
||||
|
||||
|
||||
esp_err_t CCamera::CaptureToStream(httpd_req_t *req, bool FlashlightOn)
|
||||
{
|
||||
esp_err_t res = ESP_OK;
|
||||
size_t fb_len = 0;
|
||||
int64_t fr_start;
|
||||
char * part_buf[64];
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_INFO, TAG, "Live stream started");
|
||||
|
||||
if (FlashlightOn) {
|
||||
LEDOnOff(true);
|
||||
LightOnOff(true);
|
||||
}
|
||||
|
||||
//httpd_resp_set_hdr(req, "Access-Control-Allow-Origin", "*"); //stream is blocking web interface, only serving to local
|
||||
|
||||
httpd_resp_set_type(req, _STREAM_CONTENT_TYPE);
|
||||
httpd_resp_send_chunk(req, _STREAM_BOUNDARY, strlen(_STREAM_BOUNDARY));
|
||||
|
||||
while(1)
|
||||
{
|
||||
fr_start = esp_timer_get_time();
|
||||
camera_fb_t *fb = esp_camera_fb_get();
|
||||
esp_camera_fb_return(fb);
|
||||
fb = esp_camera_fb_get();
|
||||
if (!fb) {
|
||||
LogFile.WriteToFile(ESP_LOG_ERROR, TAG, "CaptureToStream: Camera framebuffer not available");
|
||||
break;
|
||||
}
|
||||
fb_len = fb->len;
|
||||
|
||||
if (res == ESP_OK){
|
||||
size_t hlen = snprintf((char *)part_buf, sizeof(part_buf), _STREAM_PART, fb_len);
|
||||
res = httpd_resp_send_chunk(req, (const char *)part_buf, hlen);
|
||||
}
|
||||
if (res == ESP_OK){
|
||||
res = httpd_resp_send_chunk(req, (const char *)fb->buf, fb_len);
|
||||
}
|
||||
if (res == ESP_OK){
|
||||
res = httpd_resp_send_chunk(req, _STREAM_BOUNDARY, strlen(_STREAM_BOUNDARY));
|
||||
}
|
||||
|
||||
esp_camera_fb_return(fb);
|
||||
|
||||
int64_t fr_end = esp_timer_get_time();
|
||||
ESP_LOGD(TAG, "JPG: %dKB %dms", (int)(fb_len/1024), (int)((fr_end - fr_start)/1000));
|
||||
|
||||
if (res != ESP_OK){ // Exit loop, e.g. also when closing the webpage
|
||||
break;
|
||||
}
|
||||
|
||||
int64_t fr_delta_ms = (fr_end - fr_start) / 1000;
|
||||
if (CAM_LIVESTREAM_REFRESHRATE > fr_delta_ms) {
|
||||
const TickType_t xDelay = (CAM_LIVESTREAM_REFRESHRATE - fr_delta_ms) / portTICK_PERIOD_MS;
|
||||
ESP_LOGD(TAG, "Stream: sleep for: %ldms", (long) xDelay*10);
|
||||
vTaskDelay(xDelay);
|
||||
}
|
||||
}
|
||||
|
||||
LEDOnOff(false);
|
||||
LightOnOff(false);
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_INFO, TAG, "Live stream stopped");
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
|
||||
void CCamera::LightOnOff(bool status)
|
||||
{
|
||||
GpioHandler* gpioHandler = gpio_handler_get();
|
||||
|
||||
@@ -40,6 +40,7 @@ class CCamera {
|
||||
void LightOnOff(bool status);
|
||||
void LEDOnOff(bool status);
|
||||
esp_err_t CaptureToHTTP(httpd_req_t *req, int delay = 0);
|
||||
esp_err_t CaptureToStream(httpd_req_t *req, bool FlashlightOn);
|
||||
void SetQualitySize(int qual, framesize_t resol);
|
||||
bool SetBrightnessContrastSaturation(int _brightness, int _contrast, int _saturation);
|
||||
void GetCameraParameter(httpd_req_t *req, int &qual, framesize_t &resol);
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
FILE(GLOB_RECURSE app_sources ${CMAKE_CURRENT_SOURCE_DIR}/*.*)
|
||||
|
||||
idf_component_register(SRCS ${app_sources}
|
||||
INCLUDE_DIRS "." "../../include"
|
||||
REQUIRES tflite-lib esp_http_server app_update esp_http_client nvs_flash jomjol_tfliteclass jomjol_flowcontroll spiffs jomjol_helper jomjol_controlGPIO miniz)
|
||||
INCLUDE_DIRS "." "../../include" "miniz"
|
||||
REQUIRES vfs tflite-lib esp_http_server app_update esp_http_client nvs_flash jomjol_tfliteclass jomjol_flowcontroll spiffs jomjol_helper jomjol_controlGPIO)
|
||||
|
||||
|
||||
|
||||
@@ -36,7 +36,7 @@ extern "C" {
|
||||
#include "../../include/defines.h"
|
||||
#include "ClassLogFile.h"
|
||||
|
||||
#include "server_tflite.h"
|
||||
#include "MainFlowControl.h"
|
||||
|
||||
#include "server_help.h"
|
||||
#ifdef ENABLE_MQTT
|
||||
@@ -47,7 +47,6 @@ extern "C" {
|
||||
#include "Helper.h"
|
||||
#include "miniz.h"
|
||||
|
||||
|
||||
static const char *TAG = "OTA FILE";
|
||||
|
||||
struct file_server_data {
|
||||
@@ -74,7 +73,7 @@ static esp_err_t send_datafile(httpd_req_t *req, bool send_full_file);
|
||||
|
||||
esp_err_t get_numbers_file_handler(httpd_req_t *req)
|
||||
{
|
||||
std::string ret = tfliteflow.getNumbersName();
|
||||
std::string ret = flowctrl.getNumbersName();
|
||||
|
||||
// ESP_LOGI(TAG, "Result get_numbers_file_handler: %s", ret.c_str());
|
||||
|
||||
|
||||
@@ -3,7 +3,10 @@
|
||||
#include <string>
|
||||
#include "string.h"
|
||||
|
||||
#include <esp_int_wdt.h>
|
||||
/* TODO Rethink the usage of the int watchdog. It is no longer to be used, see
|
||||
https://docs.espressif.com/projects/esp-idf/en/latest/esp32/migration-guides/release-5.x/5.0/system.html?highlight=esp_int_wdt */
|
||||
#include "esp_private/esp_int_wdt.h"
|
||||
|
||||
#include <esp_task_wdt.h>
|
||||
|
||||
|
||||
@@ -11,14 +14,13 @@
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "esp_system.h"
|
||||
#include "esp_event.h"
|
||||
#include "esp_event.h"
|
||||
#include "esp_log.h"
|
||||
#include <esp_ota_ops.h>
|
||||
#include "esp_http_client.h"
|
||||
#include "esp_flash_partitions.h"
|
||||
#include "esp_partition.h"
|
||||
#include <nvs.h>
|
||||
#include "esp_app_format.h"
|
||||
#include "nvs_flash.h"
|
||||
#include "driver/gpio.h"
|
||||
// #include "protocol_examples_common.h"
|
||||
@@ -26,7 +28,7 @@
|
||||
|
||||
#include <sys/stat.h>
|
||||
|
||||
#include "server_tflite.h"
|
||||
#include "MainFlowControl.h"
|
||||
#include "server_file.h"
|
||||
#include "server_GPIO.h"
|
||||
#ifdef ENABLE_MQTT
|
||||
@@ -157,12 +159,12 @@ static bool ota_update_task(std::string fn)
|
||||
LogFile.WriteToFile(ESP_LOG_ERROR, TAG, "(This can happen if either the OTA boot data or preferred boot image become somehow corrupted.)");
|
||||
}
|
||||
ESP_LOGI(TAG, "Running partition type %d subtype %d (offset 0x%08x)",
|
||||
running->type, running->subtype, running->address);
|
||||
running->type, running->subtype, (unsigned int)running->address);
|
||||
|
||||
|
||||
update_partition = esp_ota_get_next_update_partition(NULL);
|
||||
ESP_LOGI(TAG, "Writing to partition subtype %d at offset 0x%x",
|
||||
update_partition->subtype, update_partition->address);
|
||||
update_partition->subtype, (unsigned int)update_partition->address);
|
||||
// assert(update_partition != NULL);
|
||||
|
||||
int binary_file_length = 0;
|
||||
@@ -467,7 +469,7 @@ esp_err_t handler_ota_update(httpd_req_t *req)
|
||||
{
|
||||
const char* resp_str;
|
||||
|
||||
KillTFliteTasks();
|
||||
DeleteMainFlowTask();
|
||||
gpio_handler_deinit();
|
||||
if (ota_update_task(fn))
|
||||
{
|
||||
@@ -546,7 +548,7 @@ esp_err_t handler_ota_update(httpd_req_t *req)
|
||||
/*
|
||||
const char* resp_str;
|
||||
|
||||
KillTFliteTasks();
|
||||
DeleteMainFlowTask();
|
||||
gpio_handler_deinit();
|
||||
if (ota_update_task(fn))
|
||||
{
|
||||
@@ -570,13 +572,19 @@ esp_err_t handler_ota_update(httpd_req_t *req)
|
||||
|
||||
void hard_restart()
|
||||
{
|
||||
esp_task_wdt_init(1,true);
|
||||
esp_task_wdt_config_t twdt_config = {
|
||||
.timeout_ms = 1,
|
||||
.idle_core_mask = (1 << portNUM_PROCESSORS) - 1, // Bitmask of all cores
|
||||
.trigger_panic = true,
|
||||
};
|
||||
ESP_ERROR_CHECK(esp_task_wdt_init(&twdt_config));
|
||||
|
||||
esp_task_wdt_add(NULL);
|
||||
while(true);
|
||||
}
|
||||
|
||||
|
||||
void task_reboot(void *KillAutoFlow)
|
||||
void task_reboot(void *DeleteMainFlow)
|
||||
{
|
||||
// write a reboot, to identify a reboot by purpouse
|
||||
FILE* pfile = fopen("/sdcard/reboot.txt", "w");
|
||||
@@ -586,8 +594,8 @@ void task_reboot(void *KillAutoFlow)
|
||||
|
||||
vTaskDelay(3000 / portTICK_PERIOD_MS);
|
||||
|
||||
if ((bool)KillAutoFlow) {
|
||||
KillTFliteTasks(); // Kill autoflow task if executed in extra task, if not don't kill parent task
|
||||
if ((bool)DeleteMainFlow) {
|
||||
DeleteMainFlowTask(); // Kill autoflow task if executed in extra task, if not don't kill parent task
|
||||
}
|
||||
|
||||
Camera.LightOnOff(false);
|
||||
|
||||
@@ -2,6 +2,6 @@ FILE(GLOB_RECURSE app_sources ${CMAKE_CURRENT_SOURCE_DIR}/*.*)
|
||||
|
||||
idf_component_register(SRCS ${app_sources}
|
||||
INCLUDE_DIRS "."
|
||||
REQUIRES jomjol_tfliteclass jomjol_helper jomjol_controlcamera jomjol_mqtt jomjol_influxdb jomjol_fileserver_ota jomjol_image_proc jomjol_wlan)
|
||||
REQUIRES esp_timer esp_wifi jomjol_tfliteclass jomjol_helper jomjol_controlcamera jomjol_mqtt jomjol_influxdb jomjol_fileserver_ota jomjol_image_proc jomjol_wlan)
|
||||
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
#include "ClassFlowAlignment.h"
|
||||
#include "ClassFlowTakeImage.h"
|
||||
#include "ClassFlow.h"
|
||||
#include "server_tflite.h"
|
||||
#include "MainFlowControl.h"
|
||||
|
||||
#include "CRotateImage.h"
|
||||
#include "esp_log.h"
|
||||
@@ -190,10 +190,10 @@ bool ClassFlowAlignment::doFlow(string time)
|
||||
|
||||
if (!ImageTMP)
|
||||
{
|
||||
ImageTMP = new CImageBasis("ImageTMP", ImageBasis);
|
||||
ImageTMP = new CImageBasis("tmpImage", ImageBasis); // Make sure the name does not get change, it is relevant for the PSRAM allocation!
|
||||
if (!ImageTMP)
|
||||
{
|
||||
LogFile.WriteToFile(ESP_LOG_ERROR, TAG, "Can't allocate ImageTMP -> Exec this round aborted!");
|
||||
LogFile.WriteToFile(ESP_LOG_ERROR, TAG, "Can't allocate tmpImage -> Exec this round aborted!");
|
||||
LogFile.WriteHeapInfo("ClassFlowAlignment-doFlow");
|
||||
return false;
|
||||
}
|
||||
@@ -256,8 +256,8 @@ bool ClassFlowAlignment::doFlow(string time)
|
||||
if(References[0].alignment_algo != 3){
|
||||
DrawRef(ImageTMP);
|
||||
}
|
||||
tfliteflow.DigitalDrawROI(ImageTMP);
|
||||
tfliteflow.AnalogDrawROI(ImageTMP);
|
||||
flowctrl.DigitalDrawROI(ImageTMP);
|
||||
flowctrl.AnalogDrawROI(ImageTMP);
|
||||
ImageTMP->writeToMemoryAsJPG((ImageData*)AlgROI, 90);
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -374,8 +374,11 @@ bool ClassFlowCNNGeneral::ReadParameter(FILE* pfile, string& aktparamgraph)
|
||||
}
|
||||
}
|
||||
|
||||
if (!getNetworkParameter())
|
||||
if (!getNetworkParameter()) {
|
||||
LogFile.WriteToFile(ESP_LOG_ERROR, TAG, "An error occured on setting up the Network -> Disabling it!");
|
||||
disabled = true; // An error occured, disable this CNN!
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
for (int _ana = 0; _ana < GENERAL.size(); ++_ana)
|
||||
|
||||
@@ -25,10 +25,10 @@ extern "C" {
|
||||
#endif //ENABLE_MQTT
|
||||
|
||||
#include "server_help.h"
|
||||
#include "server_tflite.h"
|
||||
#include "MainFlowControl.h"
|
||||
#include "../../include/defines.h"
|
||||
|
||||
static const char* TAG = "CTRL";
|
||||
static const char* TAG = "FLOWCTRL";
|
||||
|
||||
//#define DEBUG_DETAIL_ON
|
||||
|
||||
@@ -99,8 +99,6 @@ std::string ClassFlowControll::TranslateAktstatus(std::string _input)
|
||||
#endif //ENABLE_INFLUXDB
|
||||
if (_input.compare("ClassFlowPostProcessing") == 0)
|
||||
return ("Post-Processing");
|
||||
if (_input.compare("ClassFlowWriteList") == 0)
|
||||
return ("Writing List");
|
||||
|
||||
return "Unkown Status";
|
||||
}
|
||||
@@ -164,16 +162,8 @@ void ClassFlowControll::AnalogDrawROI(CImageBasis *_zw)
|
||||
|
||||
|
||||
#ifdef ENABLE_MQTT
|
||||
string ClassFlowControll::GetMQTTMainTopic()
|
||||
bool ClassFlowControll::StartMQTTService()
|
||||
{
|
||||
for (int i = 0; i < FlowControll.size(); ++i)
|
||||
if (FlowControll[i]->name().compare("ClassFlowMQTT") == 0)
|
||||
return ((ClassFlowMQTT*) (FlowControll[i]))->GetMQTTMainTopic();
|
||||
|
||||
return "";
|
||||
}
|
||||
|
||||
bool ClassFlowControll::StartMQTTService() {
|
||||
/* Start the MQTT service */
|
||||
for (int i = 0; i < FlowControll.size(); ++i) {
|
||||
if (FlowControll[i]->name().compare("ClassFlowMQTT") == 0) {
|
||||
@@ -243,8 +233,6 @@ ClassFlow* ClassFlowControll::CreateClassFlow(std::string _type)
|
||||
if (toUpper(_type).compare("[INFLUXDBV2]") == 0)
|
||||
cfc = new ClassFlowInfluxDBv2(&FlowControll);
|
||||
#endif //ENABLE_INFLUXDB
|
||||
if (toUpper(_type).compare("[WRITELIST]") == 0)
|
||||
cfc = new ClassFlowWriteList(&FlowControll);
|
||||
|
||||
if (toUpper(_type).compare("[POSTPROCESSING]") == 0)
|
||||
{
|
||||
@@ -385,7 +373,7 @@ bool ClassFlowControll::doFlow(string time)
|
||||
zw_time = getCurrentTimeString("%H:%M:%S");
|
||||
aktstatus = TranslateAktstatus(FlowControll[i]->name());
|
||||
aktstatusWithTime = aktstatus + " (" + zw_time + ")";
|
||||
//LogFile.WriteToFile(ESP_LOG_INFO, TAG, aktstatusWithTime);
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Status: " + aktstatusWithTime);
|
||||
#ifdef ENABLE_MQTT
|
||||
MQTTPublish(mqttServer_getMainTopic() + "/" + "status", aktstatus, qos, false);
|
||||
#endif //ENABLE_MQTT
|
||||
@@ -470,10 +458,10 @@ string ClassFlowControll::getReadoutAll(int _type)
|
||||
}
|
||||
|
||||
|
||||
string ClassFlowControll::getReadout(bool _rawvalue = false, bool _noerror = false)
|
||||
string ClassFlowControll::getReadout(bool _rawvalue = false, bool _noerror = false, int _number = 0)
|
||||
{
|
||||
if (flowpostprocessing)
|
||||
return flowpostprocessing->getReadoutParam(_rawvalue, _noerror);
|
||||
return flowpostprocessing->getReadoutParam(_rawvalue, _noerror, _number);
|
||||
|
||||
string zw = "";
|
||||
string result = "";
|
||||
@@ -501,37 +489,40 @@ string ClassFlowControll::GetPrevalue(std::string _number)
|
||||
return flowpostprocessing->GetPreValue(_number);
|
||||
}
|
||||
|
||||
|
||||
return std::string("");
|
||||
}
|
||||
|
||||
|
||||
std::string ClassFlowControll::UpdatePrevalue(std::string _newvalue, std::string _numbers, bool _extern)
|
||||
bool ClassFlowControll::UpdatePrevalue(std::string _newvalue, std::string _numbers, bool _extern)
|
||||
{
|
||||
float zw;
|
||||
double newvalueAsDouble;
|
||||
char* p;
|
||||
|
||||
_newvalue = trim(_newvalue);
|
||||
// ESP_LOGD(TAG, "Input UpdatePreValue: %s", _newvalue.c_str());
|
||||
//ESP_LOGD(TAG, "Input UpdatePreValue: %s", _newvalue.c_str());
|
||||
|
||||
if (_newvalue.compare("0.0") == 0)
|
||||
{
|
||||
zw = 0;
|
||||
if (_newvalue.substr(0,8).compare("0.000000") == 0 || _newvalue.compare("0.0") == 0 || _newvalue.compare("0") == 0) {
|
||||
newvalueAsDouble = 0; // preset to value = 0
|
||||
}
|
||||
else
|
||||
{
|
||||
zw = strtof(_newvalue.c_str(), &p);
|
||||
if (zw == 0)
|
||||
return "- Error in String to Value Conversion!!! Must be of format value=123.456";
|
||||
else {
|
||||
newvalueAsDouble = strtod(_newvalue.c_str(), &p);
|
||||
if (newvalueAsDouble == 0) {
|
||||
LogFile.WriteToFile(ESP_LOG_WARN, TAG, "UpdatePrevalue: No valid value for processing: " + _newvalue);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (flowpostprocessing)
|
||||
{
|
||||
flowpostprocessing->SetPreValue(zw, _numbers, _extern);
|
||||
return _newvalue;
|
||||
if (flowpostprocessing) {
|
||||
if (flowpostprocessing->SetPreValue(newvalueAsDouble, _numbers, _extern))
|
||||
return true;
|
||||
else
|
||||
return false;
|
||||
}
|
||||
else {
|
||||
LogFile.WriteToFile(ESP_LOG_ERROR, TAG, "UpdatePrevalue: ERROR - Class Post-Processing not initialized");
|
||||
return false;
|
||||
}
|
||||
|
||||
return std::string();
|
||||
}
|
||||
|
||||
|
||||
@@ -737,7 +728,7 @@ esp_err_t ClassFlowControll::GetJPGStream(std::string _fn, httpd_req_t *req)
|
||||
|
||||
httpd_resp_set_type(req, "image/jpeg");
|
||||
result = httpd_resp_send(req, (const char *)fileBuffer, fileSize);
|
||||
delete fileBuffer;
|
||||
free(fileBuffer);
|
||||
}
|
||||
else if (aktstatus.find("Initialization") != -1) {
|
||||
FILE* file = fopen("/sdcard/html/Flowstate_initialization.jpg", "rb");
|
||||
@@ -764,7 +755,7 @@ esp_err_t ClassFlowControll::GetJPGStream(std::string _fn, httpd_req_t *req)
|
||||
|
||||
httpd_resp_set_type(req, "image/jpeg");
|
||||
result = httpd_resp_send(req, (const char *)fileBuffer, fileSize);
|
||||
delete fileBuffer;
|
||||
free(fileBuffer);
|
||||
}
|
||||
else if (aktstatus.find("Take Image") != -1) {
|
||||
if (flowalignment && flowalignment->AlgROI) {
|
||||
|
||||
@@ -18,7 +18,6 @@
|
||||
#include "ClassFlowInfluxDBv2.h"
|
||||
#endif //ENABLE_INFLUXDB
|
||||
#include "ClassFlowCNNGeneral.h"
|
||||
#include "ClassFlowWriteList.h"
|
||||
|
||||
class ClassFlowControll :
|
||||
public ClassFlow
|
||||
@@ -46,9 +45,9 @@ public:
|
||||
bool doFlow(string time);
|
||||
void doFlowTakeImageOnly(string time);
|
||||
bool getStatusSetupModus(){return SetupModeActive;};
|
||||
string getReadout(bool _rawvalue, bool _noerror);
|
||||
string getReadout(bool _rawvalue, bool _noerror, int _number);
|
||||
string getReadoutAll(int _type);
|
||||
string UpdatePrevalue(std::string _newvalue, std::string _numbers, bool _extern);
|
||||
bool UpdatePrevalue(std::string _newvalue, std::string _numbers, bool _extern);
|
||||
string GetPrevalue(std::string _number = "");
|
||||
bool ReadParameter(FILE* pfile, string& aktparamgraph);
|
||||
string getJSON();
|
||||
@@ -56,10 +55,6 @@ public:
|
||||
|
||||
string TranslateAktstatus(std::string _input);
|
||||
|
||||
#ifdef ENABLE_MQTT
|
||||
string GetMQTTMainTopic();
|
||||
#endif //ENABLE_MQTT
|
||||
|
||||
#ifdef ALGROI_LOAD_FROM_MEM_AS_JPG
|
||||
void DigitalDrawROI(CImageBasis *_zw);
|
||||
void AnalogDrawROI(CImageBasis *_zw);
|
||||
|
||||
@@ -50,7 +50,12 @@ struct NumberPost {
|
||||
int DecimalShiftInitial;
|
||||
float AnalogDigitalTransitionStart; // When is the digit > x.1, i.e. when does it start to tilt?
|
||||
int Nachkomma;
|
||||
string Fieldname; // Fieldname in InfluxDB2
|
||||
|
||||
string FieldV1; // Fieldname in InfluxDBv1
|
||||
string MeasurementV1; // Measurement in InfluxDBv1
|
||||
|
||||
string FieldV2; // Fieldname in InfluxDBv2
|
||||
string MeasurementV2; // Measurement in InfluxDBv2
|
||||
|
||||
bool isExtendedResolution;
|
||||
|
||||
|
||||
@@ -17,7 +17,8 @@ extern "C" {
|
||||
#include "esp_log.h"
|
||||
#include "../../include/defines.h"
|
||||
|
||||
static const char* TAG = "IMG";
|
||||
static const char* TAG = "FLOWIMAGE";
|
||||
|
||||
|
||||
ClassFlowImage::ClassFlowImage(const char* logTag)
|
||||
{
|
||||
|
||||
@@ -15,13 +15,12 @@
|
||||
|
||||
#include <time.h>
|
||||
|
||||
static const char* TAG = "class_flow_influxDb";
|
||||
static const char* TAG = "INFLUXDB";
|
||||
|
||||
void ClassFlowInfluxDB::SetInitialParameter(void)
|
||||
{
|
||||
uri = "";
|
||||
database = "";
|
||||
measurement = "";
|
||||
|
||||
OldValue = "";
|
||||
flowpostprocessing = NULL;
|
||||
@@ -86,33 +85,39 @@ bool ClassFlowInfluxDB::ReadParameter(FILE* pfile, string& aktparamgraph)
|
||||
{
|
||||
ESP_LOGD(TAG, "while loop reading line: %s", aktparamgraph.c_str());
|
||||
splitted = ZerlegeZeile(aktparamgraph);
|
||||
if ((toUpper(splitted[0]) == "USER") && (splitted.size() > 1))
|
||||
std::string _param = GetParameterName(splitted[0]);
|
||||
|
||||
if ((toUpper(_param) == "USER") && (splitted.size() > 1))
|
||||
{
|
||||
this->user = splitted[1];
|
||||
}
|
||||
if ((toUpper(splitted[0]) == "PASSWORD") && (splitted.size() > 1))
|
||||
if ((toUpper(_param) == "PASSWORD") && (splitted.size() > 1))
|
||||
{
|
||||
this->password = splitted[1];
|
||||
}
|
||||
if ((toUpper(splitted[0]) == "URI") && (splitted.size() > 1))
|
||||
if ((toUpper(_param) == "URI") && (splitted.size() > 1))
|
||||
{
|
||||
this->uri = splitted[1];
|
||||
}
|
||||
if (((toUpper(splitted[0]) == "MEASUREMENT")) && (splitted.size() > 1))
|
||||
{
|
||||
this->measurement = splitted[1];
|
||||
}
|
||||
if (((toUpper(splitted[0]) == "DATABASE")) && (splitted.size() > 1))
|
||||
if (((toUpper(_param) == "DATABASE")) && (splitted.size() > 1))
|
||||
{
|
||||
this->database = splitted[1];
|
||||
}
|
||||
if (((toUpper(_param) == "MEASUREMENT")) && (splitted.size() > 1))
|
||||
{
|
||||
handleMeasurement(splitted[0], splitted[1]);
|
||||
}
|
||||
if (((toUpper(_param) == "FIELD")) && (splitted.size() > 1))
|
||||
{
|
||||
handleFieldname(splitted[0], splitted[1]);
|
||||
}
|
||||
}
|
||||
|
||||
if ((uri.length() > 0) && (database.length() > 0) && (measurement.length() > 0))
|
||||
if ((uri.length() > 0) && (database.length() > 0))
|
||||
{
|
||||
// ESP_LOGD(TAG, "Init InfluxDB with uri: %s, measurement: %s, user: %s, password: %s", uri.c_str(), measurement.c_str(), user.c_str(), password.c_str());
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Init InfluxDB with uri: " + uri + ", measurement: " + measurement + ", user: " + user + ", password: " + password);
|
||||
InfluxDBInit(uri, database, measurement, user, password);
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Init InfluxDB with uri: " + uri + ", user: " + user + ", password: " + password);
|
||||
InfluxDBInit(uri, database, user, password);
|
||||
InfluxDBenable = true;
|
||||
} else {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "InfluxDB init skipped as we are missing some parameters");
|
||||
@@ -121,19 +126,13 @@ bool ClassFlowInfluxDB::ReadParameter(FILE* pfile, string& aktparamgraph)
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
string ClassFlowInfluxDB::GetInfluxDBMeasurement()
|
||||
{
|
||||
return measurement;
|
||||
}
|
||||
|
||||
|
||||
bool ClassFlowInfluxDB::doFlow(string zwtime)
|
||||
{
|
||||
if (!InfluxDBenable)
|
||||
return true;
|
||||
|
||||
std::string result;
|
||||
std::string measurement;
|
||||
std::string resulterror = "";
|
||||
std::string resultraw = "";
|
||||
std::string resultrate = "";
|
||||
@@ -147,20 +146,28 @@ bool ClassFlowInfluxDB::doFlow(string zwtime)
|
||||
|
||||
for (int i = 0; i < (*NUMBERS).size(); ++i)
|
||||
{
|
||||
measurement = (*NUMBERS)[i]->MeasurementV1;
|
||||
result = (*NUMBERS)[i]->ReturnValue;
|
||||
resultraw = (*NUMBERS)[i]->ReturnRawValue;
|
||||
resulterror = (*NUMBERS)[i]->ErrorMessageText;
|
||||
resultrate = (*NUMBERS)[i]->ReturnRateValue;
|
||||
resulttimestamp = (*NUMBERS)[i]->timeStamp;
|
||||
|
||||
namenumber = (*NUMBERS)[i]->name;
|
||||
if (namenumber == "default")
|
||||
namenumber = "value";
|
||||
if ((*NUMBERS)[i]->FieldV1.length() > 0)
|
||||
{
|
||||
namenumber = (*NUMBERS)[i]->FieldV1;
|
||||
}
|
||||
else
|
||||
namenumber = namenumber + "/value";
|
||||
{
|
||||
namenumber = (*NUMBERS)[i]->name;
|
||||
if (namenumber == "default")
|
||||
namenumber = "value";
|
||||
else
|
||||
namenumber = namenumber + "/value";
|
||||
}
|
||||
|
||||
if (result.length() > 0 && resulttimestamp.length() > 0)
|
||||
InfluxDBPublish(namenumber, result, resulttimestamp);
|
||||
if (result.length() > 0)
|
||||
InfluxDBPublish(measurement, namenumber, result, resulttimestamp);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -169,4 +176,50 @@ bool ClassFlowInfluxDB::doFlow(string zwtime)
|
||||
return true;
|
||||
}
|
||||
|
||||
void ClassFlowInfluxDB::handleMeasurement(string _decsep, string _value)
|
||||
{
|
||||
string _digit, _decpos;
|
||||
int _pospunkt = _decsep.find_first_of(".");
|
||||
// ESP_LOGD(TAG, "Name: %s, Pospunkt: %d", _decsep.c_str(), _pospunkt);
|
||||
if (_pospunkt > -1)
|
||||
_digit = _decsep.substr(0, _pospunkt);
|
||||
else
|
||||
_digit = "default";
|
||||
for (int j = 0; j < flowpostprocessing->NUMBERS.size(); ++j)
|
||||
{
|
||||
if (_digit == "default") // Set to default first (if nothing else is set)
|
||||
{
|
||||
flowpostprocessing->NUMBERS[j]->MeasurementV1 = _value;
|
||||
}
|
||||
if (flowpostprocessing->NUMBERS[j]->name == _digit)
|
||||
{
|
||||
flowpostprocessing->NUMBERS[j]->MeasurementV1 = _value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void ClassFlowInfluxDB::handleFieldname(string _decsep, string _value)
|
||||
{
|
||||
string _digit, _decpos;
|
||||
int _pospunkt = _decsep.find_first_of(".");
|
||||
// ESP_LOGD(TAG, "Name: %s, Pospunkt: %d", _decsep.c_str(), _pospunkt);
|
||||
if (_pospunkt > -1)
|
||||
_digit = _decsep.substr(0, _pospunkt);
|
||||
else
|
||||
_digit = "default";
|
||||
for (int j = 0; j < flowpostprocessing->NUMBERS.size(); ++j)
|
||||
{
|
||||
if (_digit == "default") // Set to default first (if nothing else is set)
|
||||
{
|
||||
flowpostprocessing->NUMBERS[j]->FieldV1 = _value;
|
||||
}
|
||||
if (flowpostprocessing->NUMBERS[j]->name == _digit)
|
||||
{
|
||||
flowpostprocessing->NUMBERS[j]->FieldV1 = _value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#endif //ENABLE_INFLUXDB
|
||||
@@ -21,14 +21,19 @@ protected:
|
||||
std::string user, password;
|
||||
bool InfluxDBenable;
|
||||
|
||||
void SetInitialParameter(void);
|
||||
void SetInitialParameter(void);
|
||||
|
||||
void handleFieldname(string _decsep, string _value);
|
||||
void handleMeasurement(string _decsep, string _value);
|
||||
|
||||
|
||||
|
||||
public:
|
||||
ClassFlowInfluxDB();
|
||||
ClassFlowInfluxDB(std::vector<ClassFlow*>* lfc);
|
||||
ClassFlowInfluxDB(std::vector<ClassFlow*>* lfc, ClassFlow *_prev);
|
||||
|
||||
string GetInfluxDBMeasurement();
|
||||
// string GetInfluxDBMeasurement();
|
||||
|
||||
bool ReadParameter(FILE* pfile, string& aktparamgraph);
|
||||
bool doFlow(string time);
|
||||
|
||||
@@ -15,13 +15,12 @@
|
||||
|
||||
#include <time.h>
|
||||
|
||||
static const char* TAG = "class_flow_influxDbv2";
|
||||
static const char* TAG = "INFLUXDBV2";
|
||||
|
||||
void ClassFlowInfluxDBv2::SetInitialParameter(void)
|
||||
{
|
||||
uri = "";
|
||||
database = "";
|
||||
measurement = "";
|
||||
dborg = "";
|
||||
dbtoken = "";
|
||||
// dbfield = "";
|
||||
@@ -102,14 +101,14 @@ bool ClassFlowInfluxDBv2::ReadParameter(FILE* pfile, string& aktparamgraph)
|
||||
{
|
||||
this->uri = splitted[1];
|
||||
}
|
||||
if (((toUpper(_param) == "MEASUREMENT")) && (splitted.size() > 1))
|
||||
{
|
||||
this->measurement = splitted[1];
|
||||
}
|
||||
if (((toUpper(_param) == "FIELDNAME")) && (splitted.size() > 1))
|
||||
if (((toUpper(_param) == "FIELD")) && (splitted.size() > 1))
|
||||
{
|
||||
handleFieldname(splitted[0], splitted[1]);
|
||||
}
|
||||
if (((toUpper(_param) == "MEASUREMENT")) && (splitted.size() > 1))
|
||||
{
|
||||
handleMeasurement(splitted[0], splitted[1]);
|
||||
}
|
||||
if (((toUpper(splitted[0]) == "DATABASE")) && (splitted.size() > 1))
|
||||
{
|
||||
this->database = splitted[1];
|
||||
@@ -117,15 +116,14 @@ bool ClassFlowInfluxDBv2::ReadParameter(FILE* pfile, string& aktparamgraph)
|
||||
}
|
||||
|
||||
printf("uri: %s\n", uri.c_str());
|
||||
printf("measurement: %s\n", measurement.c_str());
|
||||
printf("org: %s\n", dborg.c_str());
|
||||
printf("token: %s\n", dbtoken.c_str());
|
||||
|
||||
if ((uri.length() > 0) && (database.length() > 0) && (measurement.length() > 0) && (dbtoken.length() > 0) && (dborg.length() > 0))
|
||||
if ((uri.length() > 0) && (database.length() > 0) && (dbtoken.length() > 0) && (dborg.length() > 0))
|
||||
{
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Init InfluxDB with uri: " + uri + ", measurement: " + measurement + ", org: " + dborg + ", token: *****");
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Init InfluxDB with uri: " + uri + ", org: " + dborg + ", token: *****");
|
||||
// printf("vor V2 Init\n");
|
||||
InfluxDB_V2_Init(uri, database, measurement, dborg, dbtoken);
|
||||
InfluxDB_V2_Init(uri, database, dborg, dbtoken);
|
||||
// printf("nach V2 Init\n");
|
||||
InfluxDBenable = true;
|
||||
} else {
|
||||
@@ -135,11 +133,12 @@ bool ClassFlowInfluxDBv2::ReadParameter(FILE* pfile, string& aktparamgraph)
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
string ClassFlowInfluxDBv2::GetInfluxDBMeasurement()
|
||||
{
|
||||
return measurement;
|
||||
}
|
||||
*/
|
||||
|
||||
void ClassFlowInfluxDBv2::handleFieldname(string _decsep, string _value)
|
||||
{
|
||||
@@ -154,15 +153,36 @@ void ClassFlowInfluxDBv2::handleFieldname(string _decsep, string _value)
|
||||
{
|
||||
if (_digit == "default") // Set to default first (if nothing else is set)
|
||||
{
|
||||
flowpostprocessing->NUMBERS[j]->Fieldname = _value;
|
||||
flowpostprocessing->NUMBERS[j]->FieldV2 = _value;
|
||||
}
|
||||
if (flowpostprocessing->NUMBERS[j]->name == _digit)
|
||||
{
|
||||
flowpostprocessing->NUMBERS[j]->Fieldname = _value;
|
||||
flowpostprocessing->NUMBERS[j]->FieldV2 = _value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ClassFlowInfluxDBv2::handleMeasurement(string _decsep, string _value)
|
||||
{
|
||||
string _digit, _decpos;
|
||||
int _pospunkt = _decsep.find_first_of(".");
|
||||
// ESP_LOGD(TAG, "Name: %s, Pospunkt: %d", _decsep.c_str(), _pospunkt);
|
||||
if (_pospunkt > -1)
|
||||
_digit = _decsep.substr(0, _pospunkt);
|
||||
else
|
||||
_digit = "default";
|
||||
for (int j = 0; j < flowpostprocessing->NUMBERS.size(); ++j)
|
||||
{
|
||||
if (_digit == "default") // Set to default first (if nothing else is set)
|
||||
{
|
||||
flowpostprocessing->NUMBERS[j]->MeasurementV2 = _value;
|
||||
}
|
||||
if (flowpostprocessing->NUMBERS[j]->name == _digit)
|
||||
{
|
||||
flowpostprocessing->NUMBERS[j]->MeasurementV2 = _value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
bool ClassFlowInfluxDBv2::doFlow(string zwtime)
|
||||
@@ -170,6 +190,7 @@ bool ClassFlowInfluxDBv2::doFlow(string zwtime)
|
||||
if (!InfluxDBenable)
|
||||
return true;
|
||||
|
||||
std::string measurement;
|
||||
std::string result;
|
||||
std::string resulterror = "";
|
||||
std::string resultraw = "";
|
||||
@@ -178,21 +199,23 @@ bool ClassFlowInfluxDBv2::doFlow(string zwtime)
|
||||
string zw = "";
|
||||
string namenumber = "";
|
||||
|
||||
|
||||
if (flowpostprocessing)
|
||||
{
|
||||
std::vector<NumberPost*>* NUMBERS = flowpostprocessing->GetNumbers();
|
||||
|
||||
for (int i = 0; i < (*NUMBERS).size(); ++i)
|
||||
{
|
||||
measurement = (*NUMBERS)[i]->MeasurementV2;
|
||||
result = (*NUMBERS)[i]->ReturnValue;
|
||||
resultraw = (*NUMBERS)[i]->ReturnRawValue;
|
||||
resulterror = (*NUMBERS)[i]->ErrorMessageText;
|
||||
resultrate = (*NUMBERS)[i]->ReturnRateValue;
|
||||
resulttimestamp = (*NUMBERS)[i]->timeStamp;
|
||||
|
||||
if ((*NUMBERS)[i]->Fieldname.length() > 0)
|
||||
if ((*NUMBERS)[i]->FieldV2.length() > 0)
|
||||
{
|
||||
namenumber = (*NUMBERS)[i]->Fieldname;
|
||||
namenumber = (*NUMBERS)[i]->FieldV2;
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -206,7 +229,7 @@ bool ClassFlowInfluxDBv2::doFlow(string zwtime)
|
||||
printf("vor sende Influx_DB_V2 - namenumber. %s, result: %s, timestampt: %s", namenumber.c_str(), result.c_str(), resulttimestamp.c_str());
|
||||
|
||||
if (result.length() > 0)
|
||||
InfluxDB_V2_Publish(namenumber, result, resulttimestamp);
|
||||
InfluxDB_V2_Publish(measurement, namenumber, result, resulttimestamp);
|
||||
// InfluxDB_V2_Publish(namenumber, result, resulttimestamp);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -15,7 +15,7 @@ class ClassFlowInfluxDBv2 :
|
||||
public ClassFlow
|
||||
{
|
||||
protected:
|
||||
std::string uri, database, measurement;
|
||||
std::string uri, database;
|
||||
std::string dborg, dbtoken, dbfield;
|
||||
std::string OldValue;
|
||||
ClassFlowPostProcessing* flowpostprocessing;
|
||||
@@ -24,13 +24,15 @@ protected:
|
||||
void SetInitialParameter(void);
|
||||
|
||||
void handleFieldname(string _decsep, string _value);
|
||||
void handleMeasurement(string _decsep, string _value);
|
||||
|
||||
|
||||
public:
|
||||
ClassFlowInfluxDBv2();
|
||||
ClassFlowInfluxDBv2(std::vector<ClassFlow*>* lfc);
|
||||
ClassFlowInfluxDBv2(std::vector<ClassFlow*>* lfc, ClassFlow *_prev);
|
||||
|
||||
string GetInfluxDBMeasurement();
|
||||
// string GetInfluxDBMeasurement();
|
||||
|
||||
bool ReadParameter(FILE* pfile, string& aktparamgraph);
|
||||
bool doFlow(string time);
|
||||
|
||||
@@ -183,12 +183,6 @@ bool ClassFlowMQTT::ReadParameter(FILE* pfile, string& aktparamgraph)
|
||||
}
|
||||
|
||||
|
||||
string ClassFlowMQTT::GetMQTTMainTopic()
|
||||
{
|
||||
return maintopic;
|
||||
}
|
||||
|
||||
|
||||
bool ClassFlowMQTT::Start(float AutoInterval)
|
||||
{
|
||||
roundInterval = AutoInterval; // Minutes
|
||||
|
||||
@@ -31,7 +31,6 @@ public:
|
||||
ClassFlowMQTT(std::vector<ClassFlow*>* lfc);
|
||||
ClassFlowMQTT(std::vector<ClassFlow*>* lfc, ClassFlow *_prev);
|
||||
|
||||
string GetMQTTMainTopic();
|
||||
bool Start(float AutoInterval);
|
||||
|
||||
bool ReadParameter(FILE* pfile, string& aktparamgraph);
|
||||
|
||||
@@ -96,27 +96,49 @@ string ClassFlowPostProcessing::GetPreValue(std::string _number)
|
||||
return result;
|
||||
}
|
||||
|
||||
void ClassFlowPostProcessing::SetPreValue(double zw, string _numbers, bool _extern)
|
||||
|
||||
bool ClassFlowPostProcessing::SetPreValue(double _newvalue, string _numbers, bool _extern)
|
||||
{
|
||||
ESP_LOGD(TAG, "SetPrevalue: %f, %s", zw, _numbers.c_str());
|
||||
for (int j = 0; j < NUMBERS.size(); ++j)
|
||||
{
|
||||
// ESP_LOGD(TAG, "Number %d, %s", j, NUMBERS[j]->name.c_str());
|
||||
if (NUMBERS[j]->name == _numbers)
|
||||
{
|
||||
NUMBERS[j]->PreValue = zw;
|
||||
NUMBERS[j]->ReturnPreValue = std::to_string(zw);
|
||||
//ESP_LOGD(TAG, "SetPrevalue: %f, %s", zw, _numbers.c_str());
|
||||
|
||||
for (int j = 0; j < NUMBERS.size(); ++j) {
|
||||
//ESP_LOGD(TAG, "Number %d, %s", j, NUMBERS[j]->name.c_str());
|
||||
if (NUMBERS[j]->name == _numbers) {
|
||||
if (_newvalue >= 0) { // if new value posivive, use provided value to preset PreValue
|
||||
NUMBERS[j]->PreValue = _newvalue;
|
||||
}
|
||||
else { // if new value negative, use last raw value to preset PreValue
|
||||
char* p;
|
||||
double ReturnRawValueAsDouble = strtod(NUMBERS[j]->ReturnRawValue.c_str(), &p);
|
||||
if (ReturnRawValueAsDouble == 0) {
|
||||
LogFile.WriteToFile(ESP_LOG_WARN, TAG, "SetPreValue: RawValue not a valid value for further processing: "
|
||||
+ NUMBERS[j]->ReturnRawValue);
|
||||
return false;
|
||||
}
|
||||
NUMBERS[j]->PreValue = ReturnRawValueAsDouble;
|
||||
}
|
||||
|
||||
NUMBERS[j]->ReturnPreValue = std::to_string(NUMBERS[j]->PreValue);
|
||||
NUMBERS[j]->PreValueOkay = true;
|
||||
|
||||
if (_extern)
|
||||
{
|
||||
time(&(NUMBERS[j]->lastvalue));
|
||||
localtime(&(NUMBERS[j]->lastvalue));
|
||||
}
|
||||
// ESP_LOGD(TAG, "Found %d! - set to %f", j, NUMBERS[j]->PreValue);
|
||||
//ESP_LOGD(TAG, "Found %d! - set to %.8f", j, NUMBERS[j]->PreValue);
|
||||
|
||||
UpdatePreValueINI = true; // Only update prevalue file if a new value is set
|
||||
SavePreValue();
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_INFO, TAG, "SetPreValue: PreValue for " + NUMBERS[j]->name + " set to " +
|
||||
std::to_string(NUMBERS[j]->PreValue));
|
||||
return true;
|
||||
}
|
||||
}
|
||||
UpdatePreValueINI = true;
|
||||
SavePreValue();
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_WARN, TAG, "SetPreValue: Numbersname not found or not valid");
|
||||
return false; // No new value was set (e.g. wrong numbersname, no numbers at all)
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -68,7 +68,7 @@ public:
|
||||
void SavePreValue();
|
||||
string getJsonFromNumber(int i, std::string _lineend);
|
||||
string GetPreValue(std::string _number = "");
|
||||
void SetPreValue(double zw, string _numbers, bool _extern = false);
|
||||
bool SetPreValue(double zw, string _numbers, bool _extern = false);
|
||||
|
||||
std::string GetJSON(std::string _lineend = "\n");
|
||||
std::string getNumbersName();
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
#include "esp_wifi.h"
|
||||
#include "esp_log.h"
|
||||
#include "../../include/defines.h"
|
||||
#include "psram.h"
|
||||
|
||||
#include <time.h>
|
||||
|
||||
@@ -15,7 +16,7 @@
|
||||
|
||||
// #define WIFITURNOFF
|
||||
|
||||
static const char* TAG = "flow_make_image";
|
||||
static const char* TAG = "TAKEIMAGE";
|
||||
|
||||
esp_err_t ClassFlowTakeImage::camera_capture(){
|
||||
string nm = namerawimage;
|
||||
@@ -183,6 +184,8 @@ string ClassFlowTakeImage::getHTMLSingleStep(string host)
|
||||
|
||||
bool ClassFlowTakeImage::doFlow(string zwtime)
|
||||
{
|
||||
psram_init_shared_memory_for_take_image_step();
|
||||
|
||||
string logPath = CreateLogFolder(zwtime);
|
||||
|
||||
int flash_duration = (int) (waitbeforepicture * 1000);
|
||||
|
||||
@@ -1,91 +0,0 @@
|
||||
#include <sstream>
|
||||
#include "ClassFlowWriteList.h"
|
||||
#include "Helper.h"
|
||||
|
||||
#include "time_sntp.h"
|
||||
#include "../../include/defines.h"
|
||||
|
||||
#include <time.h>
|
||||
|
||||
void ClassFlowWriteList::SetInitialParameter(void)
|
||||
{
|
||||
flowpostprocessing = NULL;
|
||||
previousElement = NULL;
|
||||
ListFlowControll = NULL;
|
||||
disabled = false;
|
||||
}
|
||||
|
||||
ClassFlowWriteList::ClassFlowWriteList()
|
||||
{
|
||||
SetInitialParameter();
|
||||
}
|
||||
|
||||
ClassFlowWriteList::ClassFlowWriteList(std::vector<ClassFlow*>* lfc)
|
||||
{
|
||||
SetInitialParameter();
|
||||
|
||||
ListFlowControll = lfc;
|
||||
for (int i = 0; i < ListFlowControll->size(); ++i)
|
||||
{
|
||||
if (((*ListFlowControll)[i])->name().compare("ClassFlowPostProcessing") == 0)
|
||||
{
|
||||
flowpostprocessing = (ClassFlowPostProcessing*) (*ListFlowControll)[i];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
bool ClassFlowWriteList::ReadParameter(FILE* pfile, string& aktparamgraph)
|
||||
{
|
||||
std::vector<string> splitted;
|
||||
|
||||
aktparamgraph = trim(aktparamgraph);
|
||||
|
||||
if (aktparamgraph.size() == 0)
|
||||
if (!this->GetNextParagraph(pfile, aktparamgraph))
|
||||
return false;
|
||||
|
||||
if (toUpper(aktparamgraph).compare("[MQTT]") != 0)
|
||||
return false;
|
||||
|
||||
while (this->getNextLine(pfile, &aktparamgraph) && !this->isNewParagraph(aktparamgraph))
|
||||
{
|
||||
splitted = ZerlegeZeile(aktparamgraph);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
|
||||
bool ClassFlowWriteList::doFlow(string zwtime)
|
||||
{
|
||||
std::string line = "";
|
||||
|
||||
std::string result;
|
||||
std::string resulterror = "";
|
||||
std::string resultraw = "";
|
||||
std::string resultrate = "";
|
||||
std::string resulttimestamp = "";
|
||||
string zw = "";
|
||||
string namenumber = "";
|
||||
|
||||
if (flowpostprocessing)
|
||||
{
|
||||
std::vector<NumberPost*>* NUMBERS = flowpostprocessing->GetNumbers();
|
||||
|
||||
for (int i = 0; i < (*NUMBERS).size(); ++i)
|
||||
{
|
||||
result = (*NUMBERS)[i]->ReturnValue;
|
||||
resultraw = (*NUMBERS)[i]->ReturnRawValue;
|
||||
resulterror = (*NUMBERS)[i]->ErrorMessageText;
|
||||
resultrate = (*NUMBERS)[i]->ReturnRateValue;
|
||||
resulttimestamp = (*NUMBERS)[i]->timeStamp;
|
||||
|
||||
line = line + resulttimestamp + "\t" + resultraw + "\t" + result + "\t" + resultraw + "\t" + resultrate + "\t" + resulttimestamp + "\t";
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -1,27 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#ifndef CLASSFFLOWPWRITELIST_H
|
||||
#define CLASSFFLOWPWRITELIST_H
|
||||
|
||||
#include "ClassFlow.h"
|
||||
#include "ClassFlowPostProcessing.h"
|
||||
|
||||
#include <string>
|
||||
|
||||
class ClassFlowWriteList :
|
||||
public ClassFlow
|
||||
{
|
||||
protected:
|
||||
ClassFlowPostProcessing* flowpostprocessing;
|
||||
void SetInitialParameter(void);
|
||||
|
||||
public:
|
||||
ClassFlowWriteList();
|
||||
ClassFlowWriteList(std::vector<ClassFlow*>* lfc);
|
||||
|
||||
bool ReadParameter(FILE* pfile, string& aktparamgraph);
|
||||
bool doFlow(string time);
|
||||
string name(){return "ClassFlowWriteList";};
|
||||
};
|
||||
|
||||
#endif //CLASSFFLOWPWRITELIST_H
|
||||
@@ -1,9 +1,10 @@
|
||||
#include "server_tflite.h"
|
||||
#include "MainFlowControl.h"
|
||||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include "string.h"
|
||||
#include "esp_log.h"
|
||||
#include <esp_timer.h>
|
||||
|
||||
#include <iomanip>
|
||||
#include <sstream>
|
||||
@@ -27,8 +28,12 @@
|
||||
#include "connect_wlan.h"
|
||||
#include "psram.h"
|
||||
|
||||
// support IDF 5.x
|
||||
#ifndef portTICK_RATE_MS
|
||||
#define portTICK_RATE_MS portTICK_PERIOD_MS
|
||||
#endif
|
||||
|
||||
ClassFlowControll tfliteflow;
|
||||
ClassFlowControll flowctrl;
|
||||
|
||||
TaskHandle_t xHandletask_autodoFlow = NULL;
|
||||
|
||||
@@ -41,7 +46,8 @@ bool auto_isrunning = false;
|
||||
int countRounds = 0;
|
||||
bool isPlannedReboot = false;
|
||||
|
||||
static const char *TAG = "TFLITE SERVER";
|
||||
static const char *TAG = "MAINCTRL";
|
||||
|
||||
|
||||
//#define DEBUG_DETAIL_ON
|
||||
|
||||
@@ -75,26 +81,26 @@ int getCountFlowRounds()
|
||||
|
||||
esp_err_t GetJPG(std::string _filename, httpd_req_t *req)
|
||||
{
|
||||
return tfliteflow.GetJPGStream(_filename, req);
|
||||
return flowctrl.GetJPGStream(_filename, req);
|
||||
}
|
||||
|
||||
|
||||
esp_err_t GetRawJPG(httpd_req_t *req)
|
||||
{
|
||||
return tfliteflow.SendRawJPG(req);
|
||||
return flowctrl.SendRawJPG(req);
|
||||
}
|
||||
|
||||
|
||||
bool isSetupModusActive() {
|
||||
return tfliteflow.getStatusSetupModus();
|
||||
return false;
|
||||
bool isSetupModusActive()
|
||||
{
|
||||
return flowctrl.getStatusSetupModus();
|
||||
}
|
||||
|
||||
|
||||
void KillTFliteTasks()
|
||||
void DeleteMainFlowTask()
|
||||
{
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
ESP_LOGD(TAG, "KillTFliteTasks: xHandletask_autodoFlow: %ld", (long) xHandletask_autodoFlow);
|
||||
ESP_LOGD(TAG, "DeleteMainFlowTask: xHandletask_autodoFlow: %ld", (long) xHandletask_autodoFlow);
|
||||
#endif
|
||||
if( xHandletask_autodoFlow != NULL )
|
||||
{
|
||||
@@ -109,19 +115,19 @@ void KillTFliteTasks()
|
||||
|
||||
void doInit(void)
|
||||
{
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
ESP_LOGD(TAG, "Start tfliteflow.InitFlow(config);");
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
ESP_LOGD(TAG, "Start flowctrl.InitFlow(config);");
|
||||
#endif
|
||||
tfliteflow.InitFlow(CONFIG_FILE);
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
ESP_LOGD(TAG, "Finished tfliteflow.InitFlow(config);");
|
||||
flowctrl.InitFlow(CONFIG_FILE);
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
ESP_LOGD(TAG, "Finished flowctrl.InitFlow(config);");
|
||||
#endif
|
||||
|
||||
/* GPIO handler has to be initialized before MQTT init to ensure proper topic subscription */
|
||||
gpio_handler_init();
|
||||
|
||||
#ifdef ENABLE_MQTT
|
||||
tfliteflow.StartMQTTService();
|
||||
flowctrl.StartMQTTService();
|
||||
#endif //ENABLE_MQTT
|
||||
}
|
||||
|
||||
@@ -131,7 +137,7 @@ bool doflow(void)
|
||||
std::string zw_time = getCurrentTimeString(LOGFILE_TIME_FORMAT);
|
||||
ESP_LOGD(TAG, "doflow - start %s", zw_time.c_str());
|
||||
flowisrunning = true;
|
||||
tfliteflow.doFlow(zw_time);
|
||||
flowctrl.doFlow(zw_time);
|
||||
flowisrunning = false;
|
||||
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
@@ -207,6 +213,40 @@ esp_err_t handler_init(httpd_req_t *req)
|
||||
}
|
||||
|
||||
|
||||
esp_err_t handler_stream(httpd_req_t *req)
|
||||
{
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
LogFile.WriteHeapInfo("handler_stream - Start");
|
||||
ESP_LOGD(TAG, "handler_stream uri: %s", req->uri);
|
||||
#endif
|
||||
|
||||
char _query[50];
|
||||
char _value[10];
|
||||
bool flashlightOn = false;
|
||||
|
||||
if (httpd_req_get_url_query_str(req, _query, 50) == ESP_OK)
|
||||
{
|
||||
// ESP_LOGD(TAG, "Query: %s", _query);
|
||||
if (httpd_query_key_value(_query, "flashlight", _value, 10) == ESP_OK)
|
||||
{
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
ESP_LOGD(TAG, "flashlight is found%s", _size);
|
||||
#endif
|
||||
if (strlen(_value) > 0)
|
||||
flashlightOn = true;
|
||||
}
|
||||
}
|
||||
|
||||
Camera.CaptureToStream(req, flashlightOn);
|
||||
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
LogFile.WriteHeapInfo("handler_stream - Done");
|
||||
#endif
|
||||
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
|
||||
esp_err_t handler_flow_start(httpd_req_t *req) {
|
||||
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
@@ -278,7 +318,7 @@ esp_err_t handler_json(httpd_req_t *req)
|
||||
httpd_resp_set_hdr(req, "Access-Control-Allow-Origin", "*");
|
||||
httpd_resp_set_type(req, "application/json");
|
||||
|
||||
std::string zw = tfliteflow.getJSON();
|
||||
std::string zw = flowctrl.getJSON();
|
||||
if (zw.length() > 0)
|
||||
{
|
||||
httpd_resp_send(req, zw.c_str(), zw.length());
|
||||
@@ -371,7 +411,7 @@ esp_err_t handler_wasserzaehler(httpd_req_t *req)
|
||||
_intype = READOUT_TYPE_ERROR;
|
||||
|
||||
|
||||
zw = tfliteflow.getReadoutAll(_intype);
|
||||
zw = flowctrl.getReadoutAll(_intype);
|
||||
ESP_LOGD(TAG, "ZW: %s", zw.c_str());
|
||||
if (zw.length() > 0)
|
||||
httpd_resp_send(req, zw.c_str(), zw.length());
|
||||
@@ -380,7 +420,7 @@ esp_err_t handler_wasserzaehler(httpd_req_t *req)
|
||||
}
|
||||
|
||||
|
||||
std::string *status = tfliteflow.getActStatus();
|
||||
std::string *status = flowctrl.getActStatus();
|
||||
string query = std::string(_query);
|
||||
// ESP_LOGD(TAG, "Query: %s, query.c_str());
|
||||
if (query.find("full") != std::string::npos)
|
||||
@@ -398,8 +438,7 @@ esp_err_t handler_wasserzaehler(httpd_req_t *req)
|
||||
httpd_resp_sendstr_chunk(req, txt.c_str());
|
||||
}
|
||||
|
||||
|
||||
zw = tfliteflow.getReadout(_rawValue, _noerror);
|
||||
zw = flowctrl.getReadout(_rawValue, _noerror, 0);
|
||||
if (zw.length() > 0)
|
||||
httpd_resp_sendstr_chunk(req, zw.c_str());
|
||||
|
||||
@@ -418,11 +457,11 @@ esp_err_t handler_wasserzaehler(httpd_req_t *req)
|
||||
txt += "<table style=\"border-spacing: 5px\"><tr style=\"text-align: center; vertical-align: top;\">\n";
|
||||
|
||||
std::vector<HTMLInfo*> htmlinfodig;
|
||||
htmlinfodig = tfliteflow.GetAllDigital();
|
||||
htmlinfodig = flowctrl.GetAllDigital();
|
||||
|
||||
for (int i = 0; i < htmlinfodig.size(); ++i)
|
||||
{
|
||||
if (tfliteflow.GetTypeDigital() == Digital)
|
||||
if (flowctrl.GetTypeDigital() == Digital)
|
||||
{
|
||||
if (htmlinfodig[i]->val == 10)
|
||||
zw = "NaN";
|
||||
@@ -453,7 +492,7 @@ esp_err_t handler_wasserzaehler(httpd_req_t *req)
|
||||
txt += "<table style=\"border-spacing: 5px\"><tr style=\"text-align: center; vertical-align: top;\">\n";
|
||||
|
||||
std::vector<HTMLInfo*> htmlinfoana;
|
||||
htmlinfoana = tfliteflow.GetAllAnalog();
|
||||
htmlinfoana = flowctrl.GetAllAnalog();
|
||||
for (int i = 0; i < htmlinfoana.size(); ++i)
|
||||
{
|
||||
std::stringstream stream;
|
||||
@@ -675,7 +714,7 @@ esp_err_t handler_editflow(httpd_req_t *req)
|
||||
Camera.SetBrightnessContrastSaturation(bri, con, sat);
|
||||
Camera.SetLEDIntensity(intens);
|
||||
ESP_LOGD(TAG, "test_take - vor TakeImage");
|
||||
std::string zw = tfliteflow.doSingleStep("[TakeImage]", _host);
|
||||
std::string zw = flowctrl.doSingleStep("[TakeImage]", _host);
|
||||
httpd_resp_set_hdr(req, "Access-Control-Allow-Origin", "*");
|
||||
httpd_resp_send(req, zw.c_str(), zw.length());
|
||||
}
|
||||
@@ -690,7 +729,7 @@ esp_err_t handler_editflow(httpd_req_t *req)
|
||||
// ESP_LOGD(TAG, "Parameter host: %s", _host.c_str());
|
||||
|
||||
// string zwzw = "Do " + _task + " start\n"; ESP_LOGD(TAG, zwzw.c_str());
|
||||
std::string zw = tfliteflow.doSingleStep("[Alignment]", _host);
|
||||
std::string zw = flowctrl.doSingleStep("[Alignment]", _host);
|
||||
httpd_resp_set_hdr(req, "Access-Control-Allow-Origin", "*");
|
||||
httpd_resp_send(req, zw.c_str(), zw.length());
|
||||
}
|
||||
@@ -706,7 +745,7 @@ esp_err_t handler_editflow(httpd_req_t *req)
|
||||
esp_err_t handler_statusflow(httpd_req_t *req)
|
||||
{
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
LogFile.WriteHeapInfo("handler_prevalue - Start");
|
||||
LogFile.WriteHeapInfo("handler_statusflow - Start");
|
||||
#endif
|
||||
|
||||
const char* resp_str;
|
||||
@@ -715,10 +754,10 @@ esp_err_t handler_statusflow(httpd_req_t *req)
|
||||
if (bTaskAutoFlowCreated)
|
||||
{
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
ESP_LOGD(TAG, "handler_prevalue: %s", req->uri);
|
||||
ESP_LOGD(TAG, "handler_statusflow: %s", req->uri);
|
||||
#endif
|
||||
|
||||
string* zw = tfliteflow.getActStatusWithTime();
|
||||
string* zw = flowctrl.getActStatusWithTime();
|
||||
resp_str = zw->c_str();
|
||||
|
||||
httpd_resp_send(req, resp_str, HTTPD_RESP_USE_STRLEN);
|
||||
@@ -730,7 +769,7 @@ esp_err_t handler_statusflow(httpd_req_t *req)
|
||||
}
|
||||
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
LogFile.WriteHeapInfo("handler_prevalue - Done");
|
||||
LogFile.WriteHeapInfo("handler_statusflow - Done");
|
||||
#endif
|
||||
|
||||
return ESP_OK;
|
||||
@@ -802,50 +841,81 @@ esp_err_t handler_uptime(httpd_req_t *req)
|
||||
esp_err_t handler_prevalue(httpd_req_t *req)
|
||||
{
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
LogFile.WriteHeapInfo("handler_prevalue - Start");
|
||||
#endif
|
||||
|
||||
const char* resp_str;
|
||||
string zw;
|
||||
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
LogFile.WriteHeapInfo("handler_prevalue - Start");
|
||||
ESP_LOGD(TAG, "handler_prevalue: %s", req->uri);
|
||||
#endif
|
||||
|
||||
char _query[100];
|
||||
char _size[10] = "";
|
||||
char _numbers[50] = "default";
|
||||
// Default usage message when handler gets called without any parameter
|
||||
const std::string RESTUsageInfo =
|
||||
"00: Handler usage:<br>"
|
||||
"- To retrieve actual PreValue, please provide only a numbersname, e.g. /setPreValue?numbers=main<br>"
|
||||
"- To set PreValue to a new value, please provide a numbersname and a value, e.g. /setPreValue?numbers=main&value=1234.5678<br>"
|
||||
"NOTE:<br>"
|
||||
"value >= 0.0: Set PreValue to provided value<br>"
|
||||
"value < 0.0: Set PreValue to actual RAW value (as long RAW value is a valid number, without N)";
|
||||
|
||||
if (httpd_req_get_url_query_str(req, _query, 100) == ESP_OK)
|
||||
{
|
||||
// Default return error message when no return is programmed
|
||||
std::string sReturnMessage = "E90: Uninitialized";
|
||||
|
||||
char _query[100];
|
||||
char _numbersname[50] = "default";
|
||||
char _value[20] = "";
|
||||
|
||||
httpd_resp_set_hdr(req, "Access-Control-Allow-Origin", "*");
|
||||
|
||||
if (httpd_req_get_url_query_str(req, _query, 100) == ESP_OK) {
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
ESP_LOGD(TAG, "Query: %s", _query);
|
||||
#endif
|
||||
|
||||
if (httpd_query_key_value(_query, "value", _size, 10) == ESP_OK)
|
||||
{
|
||||
if (httpd_query_key_value(_query, "numbers", _numbersname, 50) != ESP_OK) { // If request is incomplete
|
||||
sReturnMessage = "E91: Query parameter incomplete or not valid!<br> "
|
||||
"Call /setPreValue to show REST API usage info and/or check documentation";
|
||||
httpd_resp_send(req, sReturnMessage.c_str(), sReturnMessage.length());
|
||||
return ESP_FAIL;
|
||||
}
|
||||
|
||||
if (httpd_query_key_value(_query, "value", _value, 20) == ESP_OK) {
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
ESP_LOGD(TAG, "Value: %s", _size);
|
||||
#endif
|
||||
}
|
||||
|
||||
httpd_query_key_value(_query, "numbers", _numbers, 50);
|
||||
}
|
||||
|
||||
if (strlen(_size) == 0)
|
||||
{
|
||||
zw = tfliteflow.GetPrevalue(std::string(_numbers));
|
||||
}
|
||||
else
|
||||
{
|
||||
zw = "SetPrevalue to " + tfliteflow.UpdatePrevalue(_size, _numbers, true);
|
||||
}
|
||||
|
||||
resp_str = zw.c_str();
|
||||
else { // if no parameter is provided, print handler usage
|
||||
httpd_resp_send(req, RESTUsageInfo.c_str(), RESTUsageInfo.length());
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
httpd_resp_set_hdr(req, "Access-Control-Allow-Origin", "*");
|
||||
|
||||
httpd_resp_send(req, resp_str, HTTPD_RESP_USE_STRLEN);
|
||||
if (strlen(_value) == 0) { // If no value is povided --> return actual PreValue
|
||||
sReturnMessage = flowctrl.GetPrevalue(std::string(_numbersname));
|
||||
|
||||
if (sReturnMessage.empty()) {
|
||||
sReturnMessage = "E92: Numbers name not found";
|
||||
httpd_resp_send(req, sReturnMessage.c_str(), sReturnMessage.length());
|
||||
return ESP_FAIL;
|
||||
}
|
||||
}
|
||||
else {
|
||||
// New value is positive: Set PreValue to provided value and return value
|
||||
// New value is negative and actual RAW value is a valid number: Set PreValue to RAW value and return value
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "REST API handler_prevalue called: numbersname: " + std::string(_numbersname) +
|
||||
", value: " + std::string(_value));
|
||||
if (!flowctrl.UpdatePrevalue(_value, _numbersname, true)) {
|
||||
sReturnMessage = "E93: Update request rejected. Please check device logs for more details";
|
||||
httpd_resp_send(req, sReturnMessage.c_str(), sReturnMessage.length());
|
||||
return ESP_FAIL;
|
||||
}
|
||||
|
||||
sReturnMessage = flowctrl.GetPrevalue(std::string(_numbersname));
|
||||
|
||||
if (sReturnMessage.empty()) {
|
||||
sReturnMessage = "E94: Numbers name not found";
|
||||
httpd_resp_send(req, sReturnMessage.c_str(), sReturnMessage.length());
|
||||
return ESP_FAIL;
|
||||
}
|
||||
}
|
||||
|
||||
httpd_resp_send(req, sReturnMessage.c_str(), sReturnMessage.length());
|
||||
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
LogFile.WriteHeapInfo("handler_prevalue - End");
|
||||
@@ -863,7 +933,7 @@ void task_autodoFlow(void *pvParameter)
|
||||
|
||||
if (!isPlannedReboot && (esp_reset_reason() == ESP_RST_PANIC))
|
||||
{
|
||||
tfliteflow.setActStatus("Initialization (delayed)");
|
||||
flowctrl.setActStatus("Initialization (delayed)");
|
||||
//#ifdef ENABLE_MQTT
|
||||
//MQTTPublish(mqttServer_getMainTopic() + "/" + "status", "Initialization (delayed)", false); // Right now, not possible -> MQTT Service is going to be started later
|
||||
//#endif //ENABLE_MQTT
|
||||
@@ -873,13 +943,13 @@ void task_autodoFlow(void *pvParameter)
|
||||
ESP_LOGD(TAG, "task_autodoFlow: start");
|
||||
doInit();
|
||||
|
||||
auto_isrunning = tfliteflow.isAutoStart(auto_interval);
|
||||
auto_isrunning = flowctrl.isAutoStart(auto_interval);
|
||||
|
||||
if (isSetupModusActive())
|
||||
{
|
||||
auto_isrunning = false;
|
||||
std::string zw_time = getCurrentTimeString(LOGFILE_TIME_FORMAT);
|
||||
tfliteflow.doFlowTakeImageOnly(zw_time);
|
||||
flowctrl.doFlowTakeImageOnly(zw_time);
|
||||
}
|
||||
|
||||
while (auto_isrunning)
|
||||
@@ -944,13 +1014,19 @@ void task_autodoFlow(void *pvParameter)
|
||||
vTaskDelay( xDelay );
|
||||
}
|
||||
}
|
||||
|
||||
while(1) // Keep flow task running to handle necessary sub tasks like reboot handler, etc..
|
||||
{
|
||||
vTaskDelay(2000 / portTICK_PERIOD_MS);
|
||||
}
|
||||
|
||||
vTaskDelete(NULL); //Delete this task if it exits from the loop above
|
||||
xHandletask_autodoFlow = NULL;
|
||||
ESP_LOGD(TAG, "task_autodoFlow: end");
|
||||
}
|
||||
|
||||
|
||||
void TFliteDoAutoStart()
|
||||
void StartMainFlowTask()
|
||||
{
|
||||
BaseType_t xReturned;
|
||||
|
||||
@@ -967,17 +1043,9 @@ void TFliteDoAutoStart()
|
||||
}
|
||||
|
||||
|
||||
#ifdef ENABLE_MQTT
|
||||
std::string GetMQTTMainTopic()
|
||||
void register_server_main_flow_task_uri(httpd_handle_t server)
|
||||
{
|
||||
return tfliteflow.GetMQTTMainTopic();
|
||||
}
|
||||
#endif//ENABLE_MQTT
|
||||
|
||||
|
||||
void register_server_tflite_uri(httpd_handle_t server)
|
||||
{
|
||||
ESP_LOGI(TAG, "server_part_camera - Registering URI handlers");
|
||||
ESP_LOGI(TAG, "server_main_flow_task - Registering URI handlers");
|
||||
|
||||
httpd_uri_t camuri = { };
|
||||
camuri.method = HTTP_GET;
|
||||
@@ -1071,4 +1139,10 @@ void register_server_tflite_uri(httpd_handle_t server)
|
||||
camuri.handler = handler_get_heap;
|
||||
camuri.user_ctx = (void*) "Heap";
|
||||
httpd_register_uri_handler(server, &camuri);
|
||||
|
||||
camuri.uri = "/stream";
|
||||
camuri.handler = handler_stream;
|
||||
camuri.user_ctx = (void*) "stream";
|
||||
httpd_register_uri_handler(server, &camuri);
|
||||
|
||||
}
|
||||
@@ -1,7 +1,7 @@
|
||||
#pragma once
|
||||
|
||||
#ifndef SERVERTFLITE_H
|
||||
#define SERVERTFLITE_H
|
||||
#ifndef MAINFLOWCONTROL_H
|
||||
#define MAINFLOWCONTROL_H
|
||||
|
||||
#include <esp_log.h>
|
||||
#include <string>
|
||||
@@ -10,25 +10,25 @@
|
||||
#include "CImageBasis.h"
|
||||
#include "ClassFlowControll.h"
|
||||
|
||||
//#include "ClassControllCamera.h"
|
||||
extern ClassFlowControll flowctrl;
|
||||
|
||||
extern ClassFlowControll tfliteflow;
|
||||
void register_server_tflite_uri(httpd_handle_t server);
|
||||
|
||||
void KillTFliteTasks();
|
||||
void TFliteDoAutoStart();
|
||||
bool isSetupModusActive();
|
||||
int getCountFlowRounds();
|
||||
void register_server_main_flow_task_uri(httpd_handle_t server);
|
||||
|
||||
void CheckIsPlannedReboot();
|
||||
bool getIsPlannedReboot();
|
||||
|
||||
esp_err_t GetJPG(std::string _filename, httpd_req_t *req);
|
||||
esp_err_t GetRawJPG(httpd_req_t *req);
|
||||
void StartMainFlowTask();
|
||||
void DeleteMainFlowTask();
|
||||
bool isSetupModusActive();
|
||||
|
||||
int getCountFlowRounds();
|
||||
|
||||
#ifdef ENABLE_MQTT
|
||||
std::string GetMQTTMainTopic();
|
||||
esp_err_t MQTTCtrlFlowStart(std::string);
|
||||
esp_err_t MQTTCtrlFlowStart(std::string _topic);
|
||||
#endif //ENABLE_MQTT
|
||||
|
||||
#endif //SERVERTFLITE_H
|
||||
esp_err_t GetRawJPG(httpd_req_t *req);
|
||||
esp_err_t GetJPG(std::string _filename, httpd_req_t *req);
|
||||
|
||||
#endif //MAINFLOWCONTROL_H
|
||||
@@ -2,6 +2,6 @@ FILE(GLOB_RECURSE app_sources ${CMAKE_CURRENT_SOURCE_DIR}/*.*)
|
||||
|
||||
idf_component_register(SRCS ${app_sources}
|
||||
INCLUDE_DIRS "."
|
||||
REQUIRES tflite-lib jomjol_logfile fatfs sdmmc)
|
||||
REQUIRES esp_timer tflite-lib jomjol_logfile fatfs sdmmc)
|
||||
|
||||
|
||||
|
||||
@@ -23,6 +23,8 @@ extern "C" {
|
||||
|
||||
#include <string.h>
|
||||
#include <esp_log.h>
|
||||
#include <esp_mac.h>
|
||||
#include <esp_timer.h>
|
||||
#include "../../include/defines.h"
|
||||
|
||||
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
#ifdef DEBUG_ENABLE_SYSINFO
|
||||
|
||||
#include "esp_sys.h"
|
||||
#include "esp_chip_info.h"
|
||||
|
||||
#include <string>
|
||||
|
||||
@@ -121,7 +122,7 @@ std::string get_device_info()
|
||||
}
|
||||
|
||||
#ifdef USE_HIMEM_IF_AVAILABLE
|
||||
sprintf(aMsgBuf,"spiram size %u\n", esp_spiram_get_size());
|
||||
sprintf(aMsgBuf,"spiram size %u\n", esp_psram_get_size());
|
||||
espInfoResultStr += std::string(aMsgBuf);
|
||||
sprintf(aMsgBuf,"himem free %u\n", esp_himem_get_free_size());
|
||||
espInfoResultStr += std::string(aMsgBuf);
|
||||
|
||||
@@ -16,9 +16,9 @@
|
||||
#include <esp_spi_flash.h>
|
||||
#include <esp_heap_caps.h>
|
||||
|
||||
// for esp_spiram_get_size
|
||||
// for esp_psram_get_size
|
||||
extern "C" {
|
||||
#include <esp32/spiram.h>
|
||||
#include "esp_psram.h"
|
||||
#ifdef USE_HIMEM_IF_AVAILABLE
|
||||
#include <esp32/himem.h>
|
||||
#endif
|
||||
|
||||
@@ -1,11 +1,128 @@
|
||||
#include "ClassLogFile.h"
|
||||
#include "esp_heap_caps.h"
|
||||
#include "../../include/defines.h"
|
||||
#include "psram.h"
|
||||
|
||||
static const char* TAG = "PSRAM";
|
||||
|
||||
using namespace std;
|
||||
|
||||
|
||||
void *shared_region = NULL;
|
||||
uint32_t allocatedBytesForSTBI = 0;
|
||||
|
||||
|
||||
/** Reserve a large block in the PSRAM which will be shared between the different steps.
|
||||
* Each step uses it differently but only wiuthin itself. */
|
||||
bool reserve_psram_shared_region(void) {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Allocating shared PSRAM region (" +
|
||||
std::to_string(TENSOR_ARENA_SIZE + MAX_MODEL_SIZE) + " bytes)...");
|
||||
shared_region = malloc_psram_heap("Shared PSRAM region", TENSOR_ARENA_SIZE + MAX_MODEL_SIZE,
|
||||
MALLOC_CAP_SPIRAM | MALLOC_CAP_8BIT);
|
||||
|
||||
if (shared_region == NULL) {
|
||||
LogFile.WriteToFile(ESP_LOG_ERROR, TAG, "Failed to allocating shared PSRAM region!");
|
||||
return false;
|
||||
}
|
||||
else {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*******************************************************************
|
||||
* Memory used in Take Image (STBI)
|
||||
*******************************************************************/
|
||||
void psram_init_shared_memory_for_take_image_step(void) {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Init shared memory for step 'Take Image' (STBI buffers)");
|
||||
allocatedBytesForSTBI = 0;
|
||||
}
|
||||
|
||||
|
||||
void *psram_reserve_shared_stbi_memory(size_t size) {
|
||||
/* Only large buffers should be placed in the shared PSRAM
|
||||
* If we also place all smaller STBI buffers here, we get artefacts for some reasons. */
|
||||
if (size >= 100000) {
|
||||
if ((allocatedBytesForSTBI + size) > TENSOR_ARENA_SIZE + MAX_MODEL_SIZE) { // Check if it still fits in the shared region
|
||||
LogFile.WriteToFile(ESP_LOG_ERROR, TAG, "Shared memory in PSRAM too small (STBI) to fit additional " +
|
||||
std::to_string(size) + "bytes! Available: " + std::to_string(TENSOR_ARENA_SIZE + MAX_MODEL_SIZE - allocatedBytesForSTBI) + " bytes!");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Allocating memory (" + std::to_string(size) + " bytes) for STBI (use shared memory in PSRAM)...");
|
||||
allocatedBytesForSTBI += size;
|
||||
return (uint8_t *)shared_region + allocatedBytesForSTBI - size;
|
||||
}
|
||||
else { // Normal PSRAM
|
||||
return malloc_psram_heap("STBI", size, MALLOC_CAP_SPIRAM);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void *psram_reallocate_shared_stbi_memory(void *ptr, size_t newsize) {
|
||||
char buf[20];
|
||||
sprintf(buf, "%p", ptr);
|
||||
LogFile.WriteToFile(ESP_LOG_ERROR, TAG, "STBI requested realloc for " + std::string(buf) + " but this is currently unsupported!");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
void psram_free_shared_stbi_memory(void *p) {
|
||||
if ((p >= shared_region) && (p <= ((uint8_t *)shared_region + allocatedBytesForSTBI))) { // was allocated inside the shared memory
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Part of shared memory used for STBI (PSRAM, part of shared memory) is free again");
|
||||
}
|
||||
else { // Normal PSRAM
|
||||
free_psram_heap("STBI", p);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*******************************************************************
|
||||
* Memory used in Aligning Step
|
||||
* During this step we only use the shared part of the PSRAM
|
||||
* for the tmpImage.
|
||||
*******************************************************************/
|
||||
void *psram_reserve_shared_tmp_image_memory(void) {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Allocating tmpImage (" + std::to_string(IMAGE_SIZE) + " bytes, use shared memory in PSRAM)...");
|
||||
return shared_region; // Use 1th part of the shared memory for the tmpImage (only user)
|
||||
}
|
||||
|
||||
|
||||
void psram_free_shared_temp_image_memory(void) {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Shared memory used for tmpImage (PSRAM, part of shared memory) is free again");
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*******************************************************************
|
||||
* Memory used in Digitalization Steps
|
||||
* During this step we only use the shared part of the PSRAM for the
|
||||
* Tensor Arena and one of the Models.
|
||||
* The shared memory is large enough for the largest model and the
|
||||
* Tensor Arena. Therefore we do not need to monitor the usage.
|
||||
*******************************************************************/
|
||||
void *psram_get_shared_tensor_arena_memory(void) {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Allocating Tensor Arena (" + std::to_string(TENSOR_ARENA_SIZE) + " bytes, use shared memory in PSRAM)...");
|
||||
return shared_region; // Use 1th part of the shared memory for Tensor
|
||||
}
|
||||
|
||||
|
||||
void *psram_get_shared_model_memory(void) {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Allocating Model memory (" + std::to_string(MAX_MODEL_SIZE) + " bytes, use shared memory in PSRAM)...");
|
||||
return (uint8_t *)shared_region + TENSOR_ARENA_SIZE; // Use 2nd part of the shared memory (after Tensor Arena) for the model
|
||||
}
|
||||
|
||||
|
||||
void psram_free_shared_tensor_arena_and_model_memory(void) {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Shared memory used for Tensor Arena and model (PSRAM, part of shared memory) is free again");
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*******************************************************************
|
||||
* General
|
||||
*******************************************************************/
|
||||
void *malloc_psram_heap(std::string name, size_t size, uint32_t caps) {
|
||||
void *ptr;
|
||||
|
||||
@@ -21,12 +138,25 @@ void *malloc_psram_heap(std::string name, size_t size, uint32_t caps) {
|
||||
}
|
||||
|
||||
|
||||
void *realloc_psram_heap(std::string name, void *ptr, size_t size, uint32_t caps) {
|
||||
ptr = heap_caps_realloc(ptr, size, caps);
|
||||
if (ptr != NULL) {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Reallocated " + to_string(size) + " bytes in PSRAM for '" + name + "'");
|
||||
}
|
||||
else {
|
||||
LogFile.WriteToFile(ESP_LOG_ERROR, TAG, "Failed to reallocate " + to_string(size) + " bytes in PSRAM for '" + name + "'!");
|
||||
}
|
||||
|
||||
return ptr;
|
||||
}
|
||||
|
||||
|
||||
void *calloc_psram_heap(std::string name, size_t n, size_t size, uint32_t caps) {
|
||||
void *ptr;
|
||||
|
||||
ptr = heap_caps_calloc(n, size, caps);
|
||||
if (ptr != NULL) {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Allocated " + to_string(size) + " bytes in PSRAM for '" + name + "'");
|
||||
LogFile.WriteToFile(ESP_LOG_INFO, TAG, "Allocated " + to_string(size) + " bytes in PSRAM for '" + name + "'");
|
||||
}
|
||||
else {
|
||||
LogFile.WriteToFile(ESP_LOG_ERROR, TAG, "Failed to allocate " + to_string(size) + " bytes in PSRAM for '" + name + "'!");
|
||||
@@ -39,4 +169,4 @@ void *calloc_psram_heap(std::string name, size_t n, size_t size, uint32_t caps)
|
||||
void free_psram_heap(std::string name, void *ptr) {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Freeing memory in PSRAM used for '" + name + "'...");
|
||||
heap_caps_free(ptr);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,7 +1,34 @@
|
||||
#pragma once
|
||||
#ifndef PSRAM_h
|
||||
#define PSRAM_h
|
||||
|
||||
#include "esp_heap_caps.h"
|
||||
|
||||
|
||||
bool reserve_psram_shared_region(void);
|
||||
|
||||
|
||||
/* Memory used in Take Image Step */
|
||||
void psram_init_shared_memory_for_take_image_step(void);
|
||||
void *psram_reserve_shared_stbi_memory(size_t size);
|
||||
void *psram_reallocate_shared_stbi_memory(void *ptr, size_t newsize);
|
||||
void psram_free_shared_stbi_memory(void *p);
|
||||
|
||||
|
||||
/* Memory used in Aligning Step */
|
||||
void *psram_reserve_shared_tmp_image_memory(void);
|
||||
void psram_free_shared_temp_image_memory(void);
|
||||
|
||||
/* Memory used in Digitalization Steps */
|
||||
void *psram_get_shared_tensor_arena_memory(void);
|
||||
void *psram_get_shared_model_memory(void);
|
||||
void psram_free_shared_tensor_arena_and_model_memory(void);
|
||||
|
||||
/* General */
|
||||
void *malloc_psram_heap(std::string name, size_t size, uint32_t caps);
|
||||
void *realloc_psram_heap(std::string name, void *ptr, size_t size, uint32_t caps);
|
||||
void *calloc_psram_heap(std::string name, size_t n, size_t size, uint32_t caps);
|
||||
|
||||
void free_psram_heap(std::string name, void *ptr);
|
||||
void free_psram_heap(std::string name, void *ptr);
|
||||
|
||||
#endif // PSRAM_h
|
||||
|
||||
@@ -7,6 +7,11 @@
|
||||
#include "ClassLogFile.h"
|
||||
#include "../../include/defines.h"
|
||||
|
||||
// define `gpio_pad_select_gpip` for newer versions of IDF
|
||||
#if (ESP_IDF_VERSION >= ESP_IDF_VERSION_VAL(4, 3, 0))
|
||||
#include "esp_rom_gpio.h"
|
||||
#define gpio_pad_select_gpio esp_rom_gpio_pad_select_gpio
|
||||
#endif
|
||||
|
||||
static const char* TAG = "STATUSLED";
|
||||
|
||||
|
||||
@@ -477,7 +477,13 @@ CImageBasis::CImageBasis(string _name, CImageBasis *_copyfrom)
|
||||
|
||||
memsize = width * height * channels;
|
||||
|
||||
rgb_image = (unsigned char*)malloc_psram_heap(std::string(TAG) + "->CImageBasis (" + name + ")", memsize, MALLOC_CAP_SPIRAM);
|
||||
|
||||
if (name == "tmpImage") {
|
||||
rgb_image = (unsigned char*)psram_reserve_shared_tmp_image_memory();
|
||||
}
|
||||
else {
|
||||
rgb_image = (unsigned char*)malloc_psram_heap(std::string(TAG) + "->CImageBasis (" + name + ")", memsize, MALLOC_CAP_SPIRAM);
|
||||
}
|
||||
|
||||
if (rgb_image == NULL)
|
||||
{
|
||||
@@ -618,9 +624,20 @@ CImageBasis::~CImageBasis()
|
||||
{
|
||||
RGBImageLock();
|
||||
|
||||
|
||||
if (!externalImage) {
|
||||
//stbi_image_free(rgb_image);
|
||||
free_psram_heap(std::string(TAG) + "->CImageBasis (" + name + ", " + to_string(memsize) + ")", rgb_image);
|
||||
if (name == "tmpImage") { // This image should be placed in the shared part of PSRAM
|
||||
psram_free_shared_temp_image_memory();
|
||||
}
|
||||
else { // All other images are much smaller and can go into the normal PSRAM region
|
||||
//stbi_image_free(rgb_image);
|
||||
if (memsize == 0) {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Not freeing (" + name + " as there was never PSRAM allocated for it)");
|
||||
}
|
||||
else {
|
||||
free_psram_heap(std::string(TAG) + "->CImageBasis (" + name + ", " + to_string(memsize) + ")", rgb_image);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
RGBImageRelease();
|
||||
|
||||
@@ -11,9 +11,9 @@
|
||||
|
||||
#include <math.h>
|
||||
|
||||
#include "stb_image.h"
|
||||
#include "stb_image_write.h"
|
||||
#include "stb_image_resize.h"
|
||||
#include "../stb/stb_image.h"
|
||||
#include "../stb/stb_image_write.h"
|
||||
#include "../stb/stb_image_resize.h"
|
||||
|
||||
#include "esp_heap_caps.h"
|
||||
|
||||
|
||||
@@ -1,13 +1,28 @@
|
||||
#include <stdint.h>
|
||||
#include <string>
|
||||
#include "psram.h"
|
||||
|
||||
#include "../../include/defines.h"
|
||||
|
||||
|
||||
#define USE_SHARED_PSRAM_FOR_STBI
|
||||
|
||||
#ifdef USE_SHARED_PSRAM_FOR_STBI
|
||||
#define STBI_MALLOC(sz) psram_reserve_shared_stbi_memory(sz)
|
||||
#define STBI_REALLOC(p,newsz) psram_reallocate_shared_stbi_memory(p, newsz)
|
||||
#define STBI_FREE(p) psram_free_shared_stbi_memory(p)
|
||||
#else // Use normal PSRAM
|
||||
#define STBI_MALLOC(sz) malloc_psram_heap("STBI", sz, MALLOC_CAP_SPIRAM)
|
||||
#define STBI_REALLOC(p,newsz) realloc_psram_heap("STBI", p, newsz, MALLOC_CAP_SPIRAM)
|
||||
#define STBI_FREE(p) free_psram_heap("STBI", p)
|
||||
#endif
|
||||
|
||||
|
||||
#define STB_IMAGE_IMPLEMENTATION
|
||||
#include "stb_image.h"
|
||||
#include "../stb/stb_image.h"
|
||||
|
||||
#define STB_IMAGE_WRITE_IMPLEMENTATION
|
||||
#include "stb_image_write.h"
|
||||
#include "../stb/stb_image_write.h"
|
||||
|
||||
#define STB_IMAGE_RESIZE_IMPLEMENTATION
|
||||
#include "stb_image_resize.h"
|
||||
#include "../stb/stb_image_resize.h"
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -1,214 +0,0 @@
|
||||
#ifdef ENABLE_INFLUXDB
|
||||
#include "interface_influxdb.h"
|
||||
|
||||
#include "esp_log.h"
|
||||
#include <time.h>
|
||||
#include "ClassLogFile.h"
|
||||
#include "esp_http_client.h"
|
||||
#include "../../include/defines.h"
|
||||
|
||||
|
||||
static const char *TAG = "INFLUXDB";
|
||||
|
||||
std::string _influxDBURI;
|
||||
std::string _influxDBDatabase;
|
||||
std::string _influxDBMeasurement;
|
||||
std::string _influxDBUser;
|
||||
std::string _influxDBPassword;
|
||||
|
||||
static esp_err_t http_event_handler(esp_http_client_event_t *evt)
|
||||
{
|
||||
switch(evt->event_id)
|
||||
{
|
||||
case HTTP_EVENT_ERROR:
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "HTTP Client Error encountered");
|
||||
break;
|
||||
case HTTP_EVENT_ON_CONNECTED:
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "HTTP Client Error encountered");
|
||||
ESP_LOGI(TAG, "HTTP Client Connected");
|
||||
break;
|
||||
case HTTP_EVENT_HEADERS_SENT:
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "HTTP Client sent all request headers");
|
||||
break;
|
||||
case HTTP_EVENT_ON_HEADER:
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Header: key=" + std::string(evt->header_key) + ", value=" + std::string(evt->header_value));
|
||||
break;
|
||||
case HTTP_EVENT_ON_DATA:
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "HTTP Client data recevied: len=" + std::to_string(evt->data_len));
|
||||
break;
|
||||
case HTTP_EVENT_ON_FINISH:
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "HTTP Client finished");
|
||||
break;
|
||||
case HTTP_EVENT_DISCONNECTED:
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "HTTP Client Disconnected");
|
||||
break;
|
||||
}
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
void InfluxDBPublish(std::string _key, std::string _content, std::string _timestamp) {
|
||||
char response_buffer[MAX_HTTP_OUTPUT_BUFFER] = {0};
|
||||
esp_http_client_config_t http_config = {
|
||||
.user_agent = "ESP32 Meter reader",
|
||||
.method = HTTP_METHOD_POST,
|
||||
.event_handler = http_event_handler,
|
||||
.buffer_size = MAX_HTTP_OUTPUT_BUFFER,
|
||||
.user_data = response_buffer
|
||||
};
|
||||
|
||||
if (_influxDBUser.length() && _influxDBPassword.length()){
|
||||
http_config.username = _influxDBUser.c_str();
|
||||
http_config.password = _influxDBPassword.c_str();
|
||||
http_config.auth_type = HTTP_AUTH_TYPE_BASIC;
|
||||
}
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "InfluxDBPublish - Key: " + _key + ", Content: " + _content + ", Timestamp: " + _timestamp);
|
||||
|
||||
char nowTimestamp[21];
|
||||
std::string payload;
|
||||
|
||||
if (_timestamp.length() > 0)
|
||||
{
|
||||
struct tm tm;
|
||||
strptime(_timestamp.c_str(), PREVALUE_TIME_FORMAT_OUTPUT, &tm);
|
||||
time_t t = mktime(&tm); // Time in Localtime (looks like timezone is not used by strptime)
|
||||
|
||||
struct tm * ptm;
|
||||
ptm = gmtime ( &t );
|
||||
time_t utc = mktime(ptm);
|
||||
utc = 2*t - utc; // Take care of timezone (looks difficult, but is easy: t = t + (t - utc), weil t-utc = timezone)
|
||||
|
||||
sprintf(nowTimestamp,"%ld000000000", (long) utc); // UTC
|
||||
|
||||
payload = _influxDBMeasurement + " " + _key + "=" + _content + " " + nowTimestamp;
|
||||
// payload = _influxDBMeasurement + " " + _key + "=774 " + nowTimestamp;
|
||||
}
|
||||
else
|
||||
{
|
||||
payload = _influxDBMeasurement + " " + _key + "=" + _content;
|
||||
}
|
||||
|
||||
payload.shrink_to_fit();
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_INFO, TAG, "sending line to influxdb:" + payload);
|
||||
|
||||
|
||||
// use the default retention policy of the database
|
||||
std::string apiURI = _influxDBURI + "/api/v2/write?bucket=" + _influxDBDatabase + "/";
|
||||
apiURI.shrink_to_fit();
|
||||
http_config.url = apiURI.c_str();
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_INFO, TAG, "API URI: " + apiURI);
|
||||
|
||||
esp_http_client_handle_t http_client = esp_http_client_init(&http_config);
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "client is initialized");
|
||||
|
||||
esp_http_client_set_header(http_client, "Content-Type", "text/plain");
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "header is set");
|
||||
|
||||
ESP_ERROR_CHECK(esp_http_client_set_post_field(http_client, payload.c_str(), payload.length()));
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "post payload is set");
|
||||
|
||||
esp_err_t err = ESP_ERROR_CHECK_WITHOUT_ABORT(esp_http_client_perform(http_client));
|
||||
|
||||
if( err == ESP_OK ) {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "HTTP request was performed");
|
||||
int status_code = esp_http_client_get_status_code(http_client);
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "HTTP status code" + std::to_string(status_code));
|
||||
} else {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "HTTP request failed");
|
||||
}
|
||||
esp_http_client_cleanup(http_client);
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*
|
||||
void InfluxDBPublish(std::string _key, std::string _content, std::string _timestamp) {
|
||||
char response_buffer[MAX_HTTP_OUTPUT_BUFFER] = {0};
|
||||
esp_http_client_config_t http_config = {
|
||||
.user_agent = "ESP32 Meter reader",
|
||||
.method = HTTP_METHOD_POST,
|
||||
.event_handler = http_event_handler,
|
||||
.buffer_size = MAX_HTTP_OUTPUT_BUFFER,
|
||||
.user_data = response_buffer
|
||||
};
|
||||
|
||||
if (_influxDBUser.length() && _influxDBPassword.length()){
|
||||
http_config.username = _influxDBUser.c_str();
|
||||
http_config.password = _influxDBPassword.c_str();
|
||||
http_config.auth_type = HTTP_AUTH_TYPE_BASIC;
|
||||
}
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "InfluxDBPublish - Key: " + _key + ", Content: " + _content + ", Timestamp: " + _timestamp);
|
||||
|
||||
// Format: #define PREVALUE_TIME_FORMAT_OUTPUT "%Y-%m-%dT%H:%M:%S%z"
|
||||
struct tm tm;
|
||||
strptime(_timestamp.c_str(), PREVALUE_TIME_FORMAT_OUTPUT, &tm);
|
||||
time_t t = mktime(&tm); // t is now your desired time_t
|
||||
|
||||
struct tm * ptm;
|
||||
ptm = gmtime ( &t );
|
||||
time_t utc = mktime(ptm);
|
||||
|
||||
// time_t now;
|
||||
// time(&now);
|
||||
char nowTimestamp[21];
|
||||
// pad with zeroes to get nanoseconds
|
||||
// sprintf(nowTimestamp,"%ld000000000", (long) now);
|
||||
// sprintf(nowTimestamp,"%ld000000000", (long) t); // Localtime
|
||||
sprintf(nowTimestamp,"%ld000000000", (long) utc); // UTC
|
||||
|
||||
|
||||
// LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Test Time Conversion - t: " + std::to_string(t) + ", utc: " + std::to_string(utc));
|
||||
// LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Test Time Conversion - now: " + std::to_string(now) + ", timestamp: " + std::to_string(t) + "(correct time not used yet)");
|
||||
|
||||
std::string payload = _influxDBMeasurement + " " + _key + "=" + _content + " " + nowTimestamp;
|
||||
payload.shrink_to_fit();
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_INFO, TAG, "sending line to influxdb:" + payload);
|
||||
|
||||
|
||||
// use the default retention policy of the database
|
||||
std::string apiURI = _influxDBURI + "/api/v2/write?bucket=" + _influxDBDatabase + "/";
|
||||
apiURI.shrink_to_fit();
|
||||
http_config.url = apiURI.c_str();
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_INFO, TAG, "API URI: " + apiURI);
|
||||
|
||||
esp_http_client_handle_t http_client = esp_http_client_init(&http_config);
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "client is initialized");
|
||||
|
||||
esp_http_client_set_header(http_client, "Content-Type", "text/plain");
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "header is set");
|
||||
|
||||
ESP_ERROR_CHECK(esp_http_client_set_post_field(http_client, payload.c_str(), payload.length()));
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "post payload is set");
|
||||
|
||||
esp_err_t err = ESP_ERROR_CHECK_WITHOUT_ABORT(esp_http_client_perform(http_client));
|
||||
|
||||
if( err == ESP_OK ) {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "HTTP request was performed");
|
||||
int status_code = esp_http_client_get_status_code(http_client);
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "HTTP status code" + std::to_string(status_code));
|
||||
} else {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "HTTP request failed");
|
||||
}
|
||||
esp_http_client_cleanup(http_client);
|
||||
}
|
||||
*/
|
||||
|
||||
|
||||
void InfluxDBInit(std::string _uri, std::string _database, std::string _measurement, std::string _user, std::string _password){
|
||||
_influxDBURI = _uri;
|
||||
_influxDBDatabase = _database;
|
||||
_influxDBMeasurement = _measurement;
|
||||
_influxDBUser = _user;
|
||||
_influxDBPassword = _password;
|
||||
|
||||
}
|
||||
|
||||
void InfluxDBdestroy() {
|
||||
}
|
||||
|
||||
#endif //ENABLE_INFLUXDB
|
||||
@@ -1,24 +0,0 @@
|
||||
#ifdef ENABLE_INFLUXDB
|
||||
|
||||
#pragma once
|
||||
#ifndef INTERFACE_INFLUXDB_H
|
||||
#define INTERFACE_INFLUXDB_H
|
||||
|
||||
#include <string>
|
||||
#include <map>
|
||||
#include <functional>
|
||||
|
||||
// Interface to InfluxDB v1.x
|
||||
void InfluxDBInit(std::string _influxDBURI, std::string _database, std::string _measurement, std::string _user, std::string _password);
|
||||
void InfluxDBPublish(std::string _key, std::string _content, std::string _timestamp);
|
||||
|
||||
// Interface to InfluxDB v2.x
|
||||
void InfluxDB_V2_Init(std::string _uri, std::string _database, std::string _measurement, std::string _org, std::string _token);
|
||||
void InfluxDB_V2_Publish(std::string _key, std::string _content, std::string _timestamp);
|
||||
|
||||
|
||||
|
||||
void InfluxDBdestroy();
|
||||
|
||||
#endif //INTERFACE_INFLUXDB_H
|
||||
#endif //ENABLE_INFLUXDB
|
||||
@@ -12,28 +12,25 @@ static const char *TAG = "INFLUXDB";
|
||||
|
||||
std::string _influxDBURI;
|
||||
std::string _influxDBDatabase;
|
||||
std::string _influxDBMeasurement;
|
||||
std::string _influxDBUser;
|
||||
std::string _influxDBPassword;
|
||||
|
||||
std::string _influxDB_V2_URI;
|
||||
std::string _influxDB_V2_Database;
|
||||
std::string _influxDB_V2_Measurement;
|
||||
std::string _influxDB_V2_Token;
|
||||
std::string _influxDB_V2_Org;
|
||||
|
||||
static esp_err_t http_event_handler(esp_http_client_event_t *evt);
|
||||
|
||||
void InfluxDB_V2_Init(std::string _uri, std::string _database, std::string _measurement, std::string _org, std::string _token)
|
||||
void InfluxDB_V2_Init(std::string _uri, std::string _database, std::string _org, std::string _token)
|
||||
{
|
||||
_influxDB_V2_URI = _uri;
|
||||
_influxDB_V2_Database = _database;
|
||||
_influxDB_V2_Measurement = _measurement;
|
||||
_influxDB_V2_Org = _org;
|
||||
_influxDB_V2_Token = _token;
|
||||
}
|
||||
|
||||
void InfluxDB_V2_Publish(std::string _key, std::string _content, std::string _timestamp)
|
||||
void InfluxDB_V2_Publish(std::string _measurement, std::string _key, std::string _content, std::string _timestamp)
|
||||
{
|
||||
char response_buffer[MAX_HTTP_OUTPUT_BUFFER] = {0};
|
||||
esp_http_client_config_t http_config = {
|
||||
@@ -46,10 +43,8 @@ void InfluxDB_V2_Publish(std::string _key, std::string _content, std::string _ti
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "InfluxDB_V2_Publish - Key: " + _key + ", Content: " + _content + ", Timestamp: " + _timestamp);
|
||||
|
||||
// Format: #define PREVALUE_TIME_FORMAT_OUTPUT "%Y-%m-%dT%H:%M:%S%z"
|
||||
|
||||
char nowTimestamp[21];
|
||||
std::string payload;
|
||||
char nowTimestamp[21];
|
||||
|
||||
if (_timestamp.length() > 0)
|
||||
{
|
||||
@@ -57,20 +52,22 @@ void InfluxDB_V2_Publish(std::string _key, std::string _content, std::string _ti
|
||||
strptime(_timestamp.c_str(), PREVALUE_TIME_FORMAT_OUTPUT, &tm);
|
||||
time_t t = mktime(&tm); // Time in Localtime (looks like timezone is not used by strptime)
|
||||
|
||||
struct tm * ptm;
|
||||
ptm = gmtime ( &t );
|
||||
time_t utc = mktime(ptm);
|
||||
utc = 2*t - utc; // Take care of timezone (looks difficult, but is easy: t = t + (t - utc), weil t-utc = timezone)
|
||||
// struct tm * ptm;
|
||||
// ptm = gmtime ( &t );
|
||||
// time_t utc = mktime(ptm);
|
||||
|
||||
sprintf(nowTimestamp,"%ld000000000", (long) utc); // UTC
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Use handover timestamp: " + _timestamp + " converted GMT timestamp: " + std::to_string(t));
|
||||
|
||||
payload = _influxDB_V2_Measurement + " " + _key + "=" + _content + " " + nowTimestamp;
|
||||
// payload = _influxDB_V2_Measurement + " " + _key + "=774 " + nowTimestamp;
|
||||
// utc = 2*t - utc; // Take care of timezone (looks difficult, but is easy: t = t + (t - utc), weil t-utc = timezone)
|
||||
// LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "time conversion utc after: " + std::to_string(utc));
|
||||
|
||||
sprintf(nowTimestamp,"%ld000000000", (long) t); // UTC
|
||||
|
||||
payload = _measurement + " " + _key + "=" + _content + " " + nowTimestamp;
|
||||
}
|
||||
else
|
||||
{
|
||||
payload = _influxDB_V2_Measurement + " " + _key + "=" + _content;
|
||||
// payload = _influxDB_V2_Measurement + " " + _key + "=774";
|
||||
payload = _measurement + " " + _key + "=" + _content;
|
||||
}
|
||||
|
||||
payload.shrink_to_fit();
|
||||
@@ -137,11 +134,14 @@ static esp_err_t http_event_handler(esp_http_client_event_t *evt)
|
||||
case HTTP_EVENT_DISCONNECTED:
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "HTTP Client Disconnected");
|
||||
break;
|
||||
case HTTP_EVENT_REDIRECT:
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "HTTP Redirect");
|
||||
break;
|
||||
}
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
void InfluxDBPublish(std::string _key, std::string _content, std::string _timestamp) {
|
||||
void InfluxDBPublish(std::string _measurement, std::string _key, std::string _content, std::string _timestamp) {
|
||||
char response_buffer[MAX_HTTP_OUTPUT_BUFFER] = {0};
|
||||
esp_http_client_config_t http_config = {
|
||||
.user_agent = "ESP32 Meter reader",
|
||||
@@ -157,10 +157,10 @@ void InfluxDBPublish(std::string _key, std::string _content, std::string _timest
|
||||
http_config.auth_type = HTTP_AUTH_TYPE_BASIC;
|
||||
}
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "InfluxDBPublish - Key: " + _key + ", Content: " + _content + ", Timestamp: " + _timestamp);
|
||||
|
||||
char nowTimestamp[21];
|
||||
std::string payload;
|
||||
char nowTimestamp[21];
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "InfluxDBPublish - Key: " + _key + ", Content: " + _content + ", Timestamp: " + _timestamp);
|
||||
|
||||
if (_timestamp.length() > 0)
|
||||
{
|
||||
@@ -168,19 +168,22 @@ void InfluxDBPublish(std::string _key, std::string _content, std::string _timest
|
||||
strptime(_timestamp.c_str(), PREVALUE_TIME_FORMAT_OUTPUT, &tm);
|
||||
time_t t = mktime(&tm); // Time in Localtime (looks like timezone is not used by strptime)
|
||||
|
||||
struct tm * ptm;
|
||||
ptm = gmtime ( &t );
|
||||
time_t utc = mktime(ptm);
|
||||
utc = 2*t - utc; // Take care of timezone (looks difficult, but is easy: t = t + (t - utc), weil t-utc = timezone)
|
||||
// struct tm * ptm;
|
||||
// ptm = gmtime ( &t );
|
||||
// time_t utc = mktime(ptm);
|
||||
|
||||
sprintf(nowTimestamp,"%ld000000000", (long) utc); // UTC
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Use handover timestamp: " + _timestamp + " converted GMT timestamp: " + std::to_string(t));
|
||||
|
||||
payload = _influxDBMeasurement + " " + _key + "=" + _content + " " + nowTimestamp;
|
||||
// payload = _influxDBMeasurement + " " + _key + "=774 " + nowTimestamp;
|
||||
// utc = 2*t - utc; // Take care of timezone (looks difficult, but is easy: t = t + (t - utc), weil t-utc = timezone)
|
||||
// LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "time conversion utc after: " + std::to_string(utc));
|
||||
|
||||
sprintf(nowTimestamp,"%ld000000000", (long) t); // UTC
|
||||
|
||||
payload = _measurement + " " + _key + "=" + _content + " " + nowTimestamp;
|
||||
}
|
||||
else
|
||||
{
|
||||
payload = _influxDBMeasurement + " " + _key + "=" + _content;
|
||||
payload = _measurement + " " + _key + "=" + _content;
|
||||
}
|
||||
|
||||
payload.shrink_to_fit();
|
||||
@@ -189,7 +192,9 @@ void InfluxDBPublish(std::string _key, std::string _content, std::string _timest
|
||||
|
||||
|
||||
// use the default retention policy of the database
|
||||
std::string apiURI = _influxDBURI + "/write?db=" + _influxDBDatabase + "/";
|
||||
std::string apiURI = _influxDBURI + "/write?db=" + _influxDBDatabase;
|
||||
// std::string apiURI = _influxDBURI + "/api/v2/write?bucket=" + _influxDBDatabase + "/";
|
||||
|
||||
apiURI.shrink_to_fit();
|
||||
http_config.url = apiURI.c_str();
|
||||
|
||||
@@ -217,10 +222,9 @@ void InfluxDBPublish(std::string _key, std::string _content, std::string _timest
|
||||
}
|
||||
|
||||
|
||||
void InfluxDBInit(std::string _uri, std::string _database, std::string _measurement, std::string _user, std::string _password){
|
||||
void InfluxDBInit(std::string _uri, std::string _database, std::string _user, std::string _password){
|
||||
_influxDBURI = _uri;
|
||||
_influxDBDatabase = _database;
|
||||
_influxDBMeasurement = _measurement;
|
||||
_influxDBUser = _user;
|
||||
_influxDBPassword = _password;
|
||||
|
||||
|
||||
@@ -9,12 +9,12 @@
|
||||
#include <functional>
|
||||
|
||||
// Interface to InfluxDB v1.x
|
||||
void InfluxDBInit(std::string _influxDBURI, std::string _database, std::string _measurement, std::string _user, std::string _password);
|
||||
void InfluxDBPublish(std::string _key, std::string _content, std::string _timestamp);
|
||||
void InfluxDBInit(std::string _influxDBURI, std::string _database, std::string _user, std::string _password);
|
||||
void InfluxDBPublish(std::string _measurement, std::string _key, std::string _content, std::string _timestamp);
|
||||
|
||||
// Interface to InfluxDB v2.x
|
||||
void InfluxDB_V2_Init(std::string _uri, std::string _database, std::string _measurement, std::string _org, std::string _token);
|
||||
void InfluxDB_V2_Publish(std::string _key, std::string _content, std::string _timestamp);
|
||||
void InfluxDB_V2_Init(std::string _uri, std::string _database, std::string _org, std::string _token);
|
||||
void InfluxDB_V2_Publish(std::string _measurement, std::string _key, std::string _content, std::string _timestamp);
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -2,4 +2,4 @@ FILE(GLOB_RECURSE app_sources ${CMAKE_CURRENT_SOURCE_DIR}/*.*)
|
||||
|
||||
idf_component_register(SRCS ${app_sources}
|
||||
INCLUDE_DIRS "."
|
||||
REQUIRES tflite-lib mqtt jomjol_tfliteclass jomjol_helper jomjol_mqtt jomjol_wlan)
|
||||
REQUIRES esp_timer tflite-lib mqtt jomjol_tfliteclass jomjol_helper jomjol_mqtt jomjol_wlan json)
|
||||
|
||||
@@ -5,7 +5,8 @@
|
||||
#include "connect_wlan.h"
|
||||
#include "mqtt_client.h"
|
||||
#include "ClassLogFile.h"
|
||||
#include "server_tflite.h"
|
||||
#include "MainFlowControl.h"
|
||||
#include "cJSON.h"
|
||||
#include "../../include/defines.h"
|
||||
|
||||
static const char *TAG = "MQTT IF";
|
||||
@@ -185,7 +186,7 @@ static esp_err_t mqtt_event_handler_cb(esp_mqtt_event_handle_t event) {
|
||||
|
||||
|
||||
static void mqtt_event_handler(void *handler_args, esp_event_base_t base, int32_t event_id, void *event_data) {
|
||||
ESP_LOGD(TAG, "Event dispatched from event loop base=%s, event_id=%d", base, event_id);
|
||||
ESP_LOGD(TAG, "Event dispatched from event loop base=%s, event_id=%d", base, (int)event_id);
|
||||
mqtt_event_handler_cb((esp_mqtt_event_handle_t) event_data);
|
||||
}
|
||||
|
||||
@@ -247,24 +248,24 @@ int MQTT_Init() {
|
||||
LogFile.WriteToFile(ESP_LOG_INFO, TAG, "Init");
|
||||
MQTTdestroy_client(false);
|
||||
|
||||
esp_mqtt_client_config_t mqtt_cfg = {
|
||||
.uri = uri.c_str(),
|
||||
.client_id = client_id.c_str(),
|
||||
.lwt_topic = lwt_topic.c_str(),
|
||||
.lwt_msg = lwt_disconnected.c_str(),
|
||||
.lwt_retain = 1,
|
||||
.lwt_msg_len = (int)(lwt_disconnected.length()),
|
||||
.keepalive = keepalive,
|
||||
.disable_auto_reconnect = false, // Reconnection routine active (Default: false)
|
||||
.buffer_size = 1536, // size of MQTT send/receive buffer (Default: 1024)
|
||||
.reconnect_timeout_ms = 15000, // Try to reconnect to broker (Default: 10000ms)
|
||||
.network_timeout_ms = 20000, // Network Timeout (Default: 10000ms)
|
||||
.message_retransmit_timeout = 3000 // Time after message resent when broker not acknowledged (QoS1, QoS2)
|
||||
};
|
||||
esp_mqtt_client_config_t mqtt_cfg = { };
|
||||
|
||||
mqtt_cfg.broker.address.uri = uri.c_str();
|
||||
mqtt_cfg.credentials.client_id = client_id.c_str();
|
||||
mqtt_cfg.network.disable_auto_reconnect = false; // Reconnection routine active (Default: false)
|
||||
mqtt_cfg.network.reconnect_timeout_ms = 15000; // Try to reconnect to broker (Default: 10000ms)
|
||||
mqtt_cfg.network.timeout_ms = 20000; // Network Timeout (Default: 10000ms)
|
||||
mqtt_cfg.session.message_retransmit_timeout = 3000; // Time after message resent when broker not acknowledged (QoS1, QoS2)
|
||||
mqtt_cfg.session.last_will.topic = lwt_topic.c_str();
|
||||
mqtt_cfg.session.last_will.retain = 1;
|
||||
mqtt_cfg.session.last_will.msg = lwt_disconnected.c_str();
|
||||
mqtt_cfg.session.last_will.msg_len = (int)(lwt_disconnected.length());
|
||||
mqtt_cfg.session.keepalive = keepalive;
|
||||
mqtt_cfg.buffer.size = 1536; // size of MQTT send/receive buffer (Default: 1024)
|
||||
|
||||
if (user.length() && password.length()){
|
||||
mqtt_cfg.username = user.c_str();
|
||||
mqtt_cfg.password = password.c_str();
|
||||
mqtt_cfg.credentials.username = user.c_str();
|
||||
mqtt_cfg.credentials.authentication.password = password.c_str();
|
||||
}
|
||||
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
@@ -336,17 +337,54 @@ bool getMQTTisConnected() {
|
||||
}
|
||||
|
||||
|
||||
bool mqtt_handler_flow_start(std::string _topic, char* _data, int _data_len) {
|
||||
bool mqtt_handler_flow_start(std::string _topic, char* _data, int _data_len)
|
||||
{
|
||||
ESP_LOGD(TAG, "Handler called: topic %s, data %.*s", _topic.c_str(), _data_len, _data);
|
||||
|
||||
if (_data_len > 0) {
|
||||
MQTTCtrlFlowStart(_topic);
|
||||
}
|
||||
else {
|
||||
LogFile.WriteToFile(ESP_LOG_WARN, TAG, "handler_flow_start: handler called, but no data");
|
||||
}
|
||||
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
|
||||
bool mqtt_handler_set_prevalue(std::string _topic, char* _data, int _data_len)
|
||||
{
|
||||
//ESP_LOGD(TAG, "Handler called: topic %s, data %.*s", _topic.c_str(), _data_len, _data);
|
||||
//example: {"numbersname": "main", "value": 12345.1234567}
|
||||
|
||||
if (_data_len > 0) { // Check if data length > 0
|
||||
cJSON *jsonData = cJSON_Parse(_data);
|
||||
cJSON *numbersname = cJSON_GetObjectItemCaseSensitive(jsonData, "numbersname");
|
||||
cJSON *value = cJSON_GetObjectItemCaseSensitive(jsonData, "value");
|
||||
|
||||
if (cJSON_IsString(numbersname) && (numbersname->valuestring != NULL)) { // Check if numbersname is valid
|
||||
if (cJSON_IsNumber(value)) { // Check if value is a number
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "handler_set_prevalue called: numbersname: " + std::string(numbersname->valuestring) +
|
||||
", value: " + std::to_string(value->valuedouble));
|
||||
if (flowctrl.UpdatePrevalue(std::to_string(value->valuedouble), std::string(numbersname->valuestring), true))
|
||||
return ESP_OK;
|
||||
}
|
||||
else {
|
||||
LogFile.WriteToFile(ESP_LOG_WARN, TAG, "handler_set_prevalue: value not a valid number (\"value\": 12345.12345)");
|
||||
}
|
||||
}
|
||||
else {
|
||||
LogFile.WriteToFile(ESP_LOG_WARN, TAG, "handler_set_prevalue: numbersname not a valid string (\"numbersname\": \"main\")");
|
||||
}
|
||||
}
|
||||
else {
|
||||
LogFile.WriteToFile(ESP_LOG_WARN, TAG, "handler_set_prevalue: handler called, but no data received");
|
||||
}
|
||||
|
||||
return ESP_FAIL;
|
||||
}
|
||||
|
||||
|
||||
void MQTTconnected(){
|
||||
if (mqtt_connected) {
|
||||
LogFile.WriteToFile(ESP_LOG_INFO, TAG, "Connected to broker");
|
||||
@@ -358,9 +396,14 @@ void MQTTconnected(){
|
||||
}
|
||||
}
|
||||
|
||||
/* Subcribe to topics */
|
||||
std::function<bool(std::string topic, char* data, int data_len)> subHandler = mqtt_handler_flow_start;
|
||||
MQTTregisterSubscribeFunction(maintopic + "/ctrl/flow_start", subHandler); // subcribe to maintopic/ctrl/flow_start
|
||||
// Subcribe to topics
|
||||
// Note: Further subsriptions are handled in GPIO class
|
||||
//*****************************************
|
||||
std::function<bool(std::string topic, char* data, int data_len)> subHandler1 = mqtt_handler_flow_start;
|
||||
MQTTregisterSubscribeFunction(maintopic + "/ctrl/flow_start", subHandler1); // subcribe to maintopic/ctrl/flow_start
|
||||
|
||||
std::function<bool(std::string topic, char* data, int data_len)> subHandler2 = mqtt_handler_set_prevalue;
|
||||
MQTTregisterSubscribeFunction(maintopic + "/ctrl/set_prevalue", subHandler2); // subcribe to maintopic/ctrl/set_prevalue
|
||||
|
||||
if (subscribeFunktionMap != NULL) {
|
||||
for(std::map<std::string, std::function<bool(std::string, char*, int)>>::iterator it = subscribeFunktionMap->begin(); it != subscribeFunktionMap->end(); ++it) {
|
||||
|
||||
@@ -2,6 +2,6 @@ FILE(GLOB_RECURSE app_sources ${CMAKE_CURRENT_SOURCE_DIR}/*.*)
|
||||
|
||||
idf_component_register(SRCS ${app_sources}
|
||||
INCLUDE_DIRS "."
|
||||
REQUIRES jomjol_image_proc jomjol_logfile esp_http_server esp32-camera jomjol_controlcamera jomjol_flowcontroll jomjol_helper)
|
||||
REQUIRES jomjol_image_proc jomjol_logfile jomjol_flowcontroll jomjol_helper)
|
||||
|
||||
|
||||
|
||||
@@ -243,15 +243,22 @@ bool CTfLiteClass::ReadFileToModel(std::string _fn)
|
||||
|
||||
if (size == -1)
|
||||
{
|
||||
ESP_LOGE(TAG, "CTfLiteClass::ReadFileToModel: Model file doesn't exist: %s", _fn.c_str());
|
||||
LogFile.WriteToFile(ESP_LOG_ERROR, TAG, "Model file doesn't exist: " + _fn + "!");
|
||||
return false;
|
||||
}
|
||||
else if(size > MAX_MODEL_SIZE) {
|
||||
LogFile.WriteToFile(ESP_LOG_ERROR, TAG, "Unable to load model '" + _fn + "'! It does not fit in the reserved shared memory in PSRAM!");
|
||||
return false;
|
||||
}
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Loading Model " + _fn + " /size: " + std::to_string(size) + " bytes...");
|
||||
|
||||
|
||||
#ifdef DEBUG_DETAIL_ON
|
||||
LogFile.WriteHeapInfo("CTLiteClass::Alloc modelfile start");
|
||||
#endif
|
||||
|
||||
modelfile = (unsigned char*)malloc_psram_heap(std::string(TAG) + "->modelfile", size, MALLOC_CAP_SPIRAM);
|
||||
modelfile = (unsigned char*)psram_get_shared_model_memory();
|
||||
|
||||
if(modelfile != NULL)
|
||||
{
|
||||
@@ -304,9 +311,9 @@ CTfLiteClass::CTfLiteClass()
|
||||
this->modelfile = NULL;
|
||||
this->interpreter = nullptr;
|
||||
this->input = nullptr;
|
||||
this->output = nullptr;
|
||||
this->kTensorArenaSize = 800 * 1024; /// according to testfile: 108000 - so far 600;; 2021-09-11: 200 * 1024
|
||||
this->tensor_arena = (uint8_t*)malloc_psram_heap(std::string(TAG) + "->tensor_arena", kTensorArenaSize, MALLOC_CAP_SPIRAM);
|
||||
this->output = nullptr;
|
||||
this->kTensorArenaSize = TENSOR_ARENA_SIZE;
|
||||
this->tensor_arena = (uint8_t*)psram_get_shared_tensor_arena_memory();
|
||||
}
|
||||
|
||||
|
||||
@@ -315,8 +322,7 @@ CTfLiteClass::~CTfLiteClass()
|
||||
delete this->interpreter;
|
||||
delete this->error_reporter;
|
||||
|
||||
free_psram_heap(std::string(TAG) + "->modelfile", modelfile);
|
||||
free_psram_heap(std::string(TAG) + "->tensor_arena", this->tensor_arena);
|
||||
psram_free_shared_tensor_arena_and_model_memory();
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -7,7 +7,6 @@
|
||||
#include "freertos/task.h"
|
||||
#include "freertos/event_groups.h"
|
||||
#include "esp_system.h"
|
||||
#include "esp_event.h"
|
||||
#include "esp_log.h"
|
||||
#include "esp_attr.h"
|
||||
#include "esp_sleep.h"
|
||||
@@ -72,6 +71,24 @@ void time_sync_notification_cb(struct timeval *tv)
|
||||
}
|
||||
|
||||
|
||||
bool time_manual_reset_sync(void)
|
||||
{
|
||||
sntp_restart();
|
||||
// sntp_init();
|
||||
int retry = 0;
|
||||
const int retry_count = 10;
|
||||
while (sntp_get_sync_status() == SNTP_SYNC_STATUS_RESET && ++retry < retry_count) {
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Waiting for system time to be set... " + std::to_string(retry) + "/" + std::to_string(retry_count));
|
||||
vTaskDelay(2000 / portTICK_PERIOD_MS);
|
||||
}
|
||||
if (retry >= retry_count)
|
||||
return false;
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Waiting for system time successfull with " + std::to_string(retry) + "/" + std::to_string(retry_count));
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
void setTimeZone(std::string _tzstring)
|
||||
{
|
||||
setenv("TZ", _tzstring.c_str(), 1);
|
||||
@@ -220,11 +237,16 @@ bool setupTime() {
|
||||
LogFile.WriteToFile(ESP_LOG_INFO, TAG, "Configuring NTP Client...");
|
||||
sntp_setoperatingmode(SNTP_OPMODE_POLL);
|
||||
sntp_setservername(0, timeServer.c_str());
|
||||
sntp_init();
|
||||
|
||||
sntp_set_time_sync_notification_cb(time_sync_notification_cb);
|
||||
|
||||
setTimeZone(timeZone);
|
||||
|
||||
sntp_init();
|
||||
/*
|
||||
if (!wait_for_timesync())
|
||||
{
|
||||
LogFile.WriteToFile(ESP_LOG_INFO, TAG, "Timesync at startup failed.");
|
||||
}
|
||||
*/
|
||||
}
|
||||
|
||||
|
||||
@@ -250,3 +272,5 @@ bool setupTime() {
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -11,7 +11,6 @@
|
||||
#include "freertos/task.h"
|
||||
#include "freertos/event_groups.h"
|
||||
#include "esp_system.h"
|
||||
#include "esp_event.h"
|
||||
#include "esp_log.h"
|
||||
#include "esp_attr.h"
|
||||
#include "esp_sleep.h"
|
||||
@@ -27,4 +26,7 @@ bool getTimeWasNotSetAtBoot(void);
|
||||
bool getUseNtp(void);
|
||||
bool setupTime();
|
||||
|
||||
bool time_manual_reset_sync(void);
|
||||
|
||||
|
||||
#endif //TIMESNTP_H
|
||||
@@ -2,6 +2,6 @@ FILE(GLOB_RECURSE app_sources ${CMAKE_CURRENT_SOURCE_DIR}/*.*)
|
||||
|
||||
idf_component_register(SRCS ${app_sources}
|
||||
INCLUDE_DIRS "."
|
||||
REQUIRES nvs_flash jomjol_helper jomjol_mqtt wpa_supplicant)
|
||||
REQUIRES esp_wifi nvs_flash jomjol_helper jomjol_mqtt wpa_supplicant)
|
||||
|
||||
|
||||
|
||||
@@ -19,7 +19,7 @@
|
||||
#include "esp_mbo.h"
|
||||
#include "esp_mac.h"
|
||||
#include "esp_netif.h"
|
||||
#include "esp_event.h"
|
||||
#include <netdb.h>
|
||||
#include "esp_log.h"
|
||||
#include "nvs_flash.h"
|
||||
|
||||
@@ -36,6 +36,20 @@
|
||||
|
||||
#include "../../include/defines.h"
|
||||
|
||||
#if (ESP_IDF_VERSION_MAJOR >= 5)
|
||||
#include "soc/periph_defs.h"
|
||||
#include "esp_private/periph_ctrl.h"
|
||||
#include "soc/gpio_sig_map.h"
|
||||
#include "soc/gpio_periph.h"
|
||||
#include "soc/io_mux_reg.h"
|
||||
#include "esp_rom_gpio.h"
|
||||
#define gpio_pad_select_gpio esp_rom_gpio_pad_select_gpio
|
||||
#define gpio_matrix_in(a,b,c) esp_rom_gpio_connect_in_signal(a,b,c)
|
||||
#define gpio_matrix_out(a,b,c,d) esp_rom_gpio_connect_out_signal(a,b,c,d)
|
||||
#define ets_delay_us(a) esp_rom_delay_us(a)
|
||||
#endif
|
||||
|
||||
esp_netif_t *sta_netif = NULL;
|
||||
|
||||
static const char *TAG = "WIFI";
|
||||
|
||||
@@ -173,7 +187,7 @@ static char * get_btm_neighbor_list(uint8_t *report, size_t report_len)
|
||||
pos += s_len;
|
||||
}
|
||||
|
||||
ESP_LOGI(TAG, "Roaming: RMM neigbor report bssid=" MACSTR
|
||||
ESP_LOGI(TAG, "Roaming: RMM neighbor report bssid=" MACSTR
|
||||
" info=0x%x op_class=%u chan=%u phy_type=%u%s%s%s%s",
|
||||
MAC2STR(nr), WPA_GET_LE32(nr + ETH_ALEN),
|
||||
nr[ETH_ALEN + 4], nr[ETH_ALEN + 5],
|
||||
@@ -182,7 +196,7 @@ static char * get_btm_neighbor_list(uint8_t *report, size_t report_len)
|
||||
civic[0] ? " civic=" : "", civic);
|
||||
|
||||
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Roaming: RMM neigbor report BSSID: " + BssidToString((char*)nr) +
|
||||
LogFile.WriteToFile(ESP_LOG_DEBUG, TAG, "Roaming: RMM neighbor report BSSID: " + BssidToString((char*)nr) +
|
||||
", Channel: " + std::to_string(nr[ETH_ALEN + 5]));
|
||||
|
||||
/* neighbor start */
|
||||
@@ -365,7 +379,7 @@ void wifi_scan(void)
|
||||
else {
|
||||
if (esp_wifi_scan_get_ap_records(&max_number_of_ap_found, wifi_ap_records) != ESP_OK) { // Retrieve results (and free internal heap)
|
||||
LogFile.WriteToFile(ESP_LOG_ERROR, TAG, "wifi_scan: esp_wifi_scan_get_ap_records: Error retrieving datasets");
|
||||
free(wifi_ap_records);
|
||||
delete wifi_ap_records;
|
||||
return;
|
||||
}
|
||||
}
|
||||
@@ -388,7 +402,7 @@ void wifi_scan(void)
|
||||
APWithBetterRSSI = true;
|
||||
}
|
||||
}
|
||||
free(wifi_ap_records);
|
||||
delete wifi_ap_records;
|
||||
}
|
||||
|
||||
|
||||
@@ -636,7 +650,7 @@ esp_err_t wifi_init_sta(void)
|
||||
|
||||
if (!wlan_config.hostname.empty())
|
||||
{
|
||||
retval = tcpip_adapter_set_hostname(TCPIP_ADAPTER_IF_STA , wlan_config.hostname.c_str());
|
||||
retval = esp_netif_set_hostname(my_sta, wlan_config.hostname.c_str());
|
||||
if(retval != ESP_OK ) {
|
||||
LogFile.WriteToFile(ESP_LOG_ERROR, TAG, "Failed to set hostname! Error: " + std::to_string(retval));
|
||||
}
|
||||
|
||||
@@ -1,6 +0,0 @@
|
||||
FILE(GLOB_RECURSE app_sources ${CMAKE_CURRENT_SOURCE_DIR}/*.*)
|
||||
|
||||
idf_component_register(SRCS ${app_sources}
|
||||
INCLUDE_DIRS "." "../../include")
|
||||
|
||||
|
||||
1
code/components/stb
Submodule
1
code/components/stb
Submodule
Submodule code/components/stb added at 5736b15f7e
Reference in New Issue
Block a user