3 Commits
v1.0.6 ... dev

Author SHA1 Message Date
19e895a195 Version 1.0.9
Changed WiFi protocol.
Reduced interval for availability_check_task.
Reduced time threshold for checking device availability.
Added processing of node messages about offline mode.
2024-07-19 19:17:46 +03:00
67aa396262 Version 1.0.8
Fixed bug with duplicate messages in Syslog.
2024-07-16 12:07:22 +03:00
7166625595 Version 1.0.7
Added sending of system messages to the Syslog server.
Some initial mandatory settings converted to optional settings.
Updated components.
2024-07-16 10:03:51 +03:00
11 changed files with 346 additions and 73 deletions

5
.gitmodules vendored
View File

@ -12,4 +12,7 @@
url = https://github.com/aZholtikov/zh_config url = https://github.com/aZholtikov/zh_config
[submodule "components/zh_espnow"] [submodule "components/zh_espnow"]
path = components/zh_espnow path = components/zh_espnow
url = https://github.com/aZholtikov/zh_espnow url = https://github.com/aZholtikov/zh_espnow
[submodule "components/zh_syslog"]
path = components/zh_syslog
url = https://github.com/aZholtikov/zh_syslog

View File

@ -8,20 +8,22 @@ Gateway for ESP32 ESP-IDF for data exchange between ESP-NOW devices and MQTT bro
## Features ## Features
1. Automatically adds gateway configuration to Home Assistan via MQTT discovery as a binary_sensor. 1. LAN or WiFi connection to router.
2. Automatically adds supported devices configurations to Home Assistan via MQTT discovery. 2. Direct or mesh work mode.
3. Update firmware from HTTPS server via OTA. 3. Automatically adds gateway configuration to Home Assistan via MQTT discovery as a binary_sensor.
4. Update firmware of supported devices from HTTPS server via ESP-NOW. 4. Automatically adds supported devices configurations to Home Assistan via MQTT discovery.
5. LAN or WiFi connection to router. 5. Update firmware from HTTPS server via OTA (optional).
6. Direct or mesh work mode. 6. Update firmware of supported devices from HTTPS server via ESP-NOW (optional).
7. Receive time from NTP server and transmit it to supported devices (optional).
8. Transmitting system information to Syslog server (optional).
## Notes ## Notes
1. All devices on the network must have the same work mode. 1. All devices on the network must have the same work mode.
2. ESP-NOW mesh network based on the [zh_network](https://github.com/aZholtikov/zh_network). 2. ESP-NOW mesh network based on the [zh_network](https://github.com/aZholtikov/zh_network).
3. For initial settings use "menuconfig -> ZH Gateway Configuration". After first boot all settings (except work mode) will be stored in NVS memory for prevente change during OTA firmware update. 3. For initial settings use "menuconfig -> ZH Gateway Configuration". After first boot all settings (except work mode) will be stored in NVS memory for prevente change during OTA firmware update. But it is highly recommended to set up the configuration via menuconfig before updating.
4. To restart the gateway, send the "restart" command to the root topic of the gateway (example - "homeassistant/gateway/70-03-9F-44-BE-F7"). 4. To restart the gateway, send the "restart" command to the root topic of the gateway (example - "homeassistant/gateway/70-03-9F-44-BE-F7").
5. To update the gateway firmware, send the "update" command to the root topic of the gateway (example - "homeassistant/gateway/70-03-9F-44-BE-F7"). The update path should be like as "https://your_server/zh_gateway_esp32.bin". The online status of the update is displayed in the root gateway topic. 5. To update the gateway firmware, send the "update" command to the root topic of the gateway (example - "homeassistant/gateway/70-03-9F-44-BE-F7"). The update path should be like as "https://your_server/zh_gateway_esp32.bin". The online status of the update is displayed in the root gateway topic and Syslog server (if enabled).
## Build and flash ## Build and flash

1
components/zh_syslog Submodule

Submodule components/zh_syslog added at 912eea58dd

View File

@ -48,19 +48,55 @@ menu "ZH Gateway Configuration"
help help
MQTT topic prefix. MQTT topic prefix.
config SYSLOG_SERVER_USING
bool "Enable using Syslog server"
default true
help
Enable using Syslog server.
config SYSLOG_SERVER_IP
depends on SYSLOG_SERVER_USING
string "Syslog server IP"
default "192.168.1.2"
help
Syslog server IP.
config SYSLOG_SERVER_PORT
depends on SYSLOG_SERVER_USING
int "Syslog server port"
range 0 65635
default 514
help
Syslog server port.
config NTP_SERVER_USING
bool "Enable using NTP server"
default true
help
Enable using NTP server.
config NTP_SERVER_URL config NTP_SERVER_URL
depends on NTP_SERVER_USING
string "NTP server url" string "NTP server url"
default "ntpserver.com" default "ntpserver.com"
help help
NTP server url. NTP server url.
config NTP_TIME_ZONE config NTP_TIME_ZONE
depends on NTP_SERVER_USING
string "NTP time zone" string "NTP time zone"
default "UTC-3" default "UTC-3"
help help
NTP time zone. NTP time zone.
config FIRMWARE_UPGRADE_SERVER_USING
bool "Enable using OTA update"
default true
help
Enable using OTA update.
config FIRMWARE_UPGRADE_URL config FIRMWARE_UPGRADE_URL
depends on FIRMWARE_UPGRADE_SERVER_USING
string "Firmware upgrade url" string "Firmware upgrade url"
default "https://yourserver.com" default "https://yourserver.com"
help help

View File

@ -36,7 +36,7 @@ void app_main(void)
wifi_init_config_t wifi_init_config = WIFI_INIT_CONFIG_DEFAULT(); wifi_init_config_t wifi_init_config = WIFI_INIT_CONFIG_DEFAULT();
esp_wifi_init(&wifi_init_config); esp_wifi_init(&wifi_init_config);
esp_wifi_set_mode(WIFI_MODE_STA); esp_wifi_set_mode(WIFI_MODE_STA);
esp_wifi_set_protocol(WIFI_IF_STA, WIFI_PROTOCOL_11B); esp_wifi_set_protocol(WIFI_IF_STA, WIFI_PROTOCOL_11B | WIFI_PROTOCOL_11G | WIFI_PROTOCOL_11N | WIFI_PROTOCOL_LR);
esp_wifi_start(); esp_wifi_start();
esp_read_mac(gateway_config->self_mac, ESP_MAC_WIFI_STA); esp_read_mac(gateway_config->self_mac, ESP_MAC_WIFI_STA);
} }
@ -49,7 +49,7 @@ void app_main(void)
memcpy(wifi_config.sta.ssid, gateway_config->software_config.ssid_name, strlen(gateway_config->software_config.ssid_name)); memcpy(wifi_config.sta.ssid, gateway_config->software_config.ssid_name, strlen(gateway_config->software_config.ssid_name));
memcpy(wifi_config.sta.password, gateway_config->software_config.ssid_password, strlen(gateway_config->software_config.ssid_password)); memcpy(wifi_config.sta.password, gateway_config->software_config.ssid_password, strlen(gateway_config->software_config.ssid_password));
esp_wifi_set_mode(WIFI_MODE_APSTA); esp_wifi_set_mode(WIFI_MODE_APSTA);
esp_wifi_set_protocol(WIFI_IF_AP, WIFI_PROTOCOL_11B); esp_wifi_set_protocol(WIFI_IF_AP, WIFI_PROTOCOL_11B | WIFI_PROTOCOL_11G | WIFI_PROTOCOL_11N | WIFI_PROTOCOL_LR);
esp_wifi_set_config(WIFI_IF_STA, &wifi_config); esp_wifi_set_config(WIFI_IF_STA, &wifi_config);
esp_event_handler_instance_register(WIFI_EVENT, ESP_EVENT_ANY_ID, &zh_wifi_event_handler, gateway_config, NULL); esp_event_handler_instance_register(WIFI_EVENT, ESP_EVENT_ANY_ID, &zh_wifi_event_handler, gateway_config, NULL);
esp_event_handler_instance_register(IP_EVENT, IP_EVENT_STA_GOT_IP, &zh_wifi_event_handler, gateway_config, NULL); esp_event_handler_instance_register(IP_EVENT, IP_EVENT_STA_GOT_IP, &zh_wifi_event_handler, gateway_config, NULL);
@ -99,10 +99,11 @@ void zh_load_config(gateway_config_t *gateway_config)
{ {
nvs_set_u8(nvs_handle, "present", 0xFE); nvs_set_u8(nvs_handle, "present", 0xFE);
nvs_close(nvs_handle); nvs_close(nvs_handle);
SETUP_INITIAL_SETTINGS:
#ifdef CONFIG_CONNECTION_TYPE_LAN #ifdef CONFIG_CONNECTION_TYPE_LAN
gateway_config->software_config.is_lan_mode = true; gateway_config->software_config.is_lan_mode = true;
strcpy(gateway_config->software_config.ssid_name, "ssid"); strcpy(gateway_config->software_config.ssid_name, "NULL");
strcpy(gateway_config->software_config.ssid_password, "password"); strcpy(gateway_config->software_config.ssid_password, "NULL");
#else #else
gateway_config->software_config.is_lan_mode = false; gateway_config->software_config.is_lan_mode = false;
strcpy(gateway_config->software_config.ssid_name, CONFIG_WIFI_SSID_NAME); strcpy(gateway_config->software_config.ssid_name, CONFIG_WIFI_SSID_NAME);
@ -110,29 +111,62 @@ void zh_load_config(gateway_config_t *gateway_config)
#endif #endif
strcpy(gateway_config->software_config.mqtt_broker_url, CONFIG_MQTT_BROKER_URL); strcpy(gateway_config->software_config.mqtt_broker_url, CONFIG_MQTT_BROKER_URL);
strcpy(gateway_config->software_config.mqtt_topic_prefix, CONFIG_MQTT_TOPIC_PREFIX); strcpy(gateway_config->software_config.mqtt_topic_prefix, CONFIG_MQTT_TOPIC_PREFIX);
#ifdef CONFIG_SYSLOG_SERVER_USING
gateway_config->software_config.is_syslog_server_usage = true;
strcpy(gateway_config->software_config.syslog_server_ip, CONFIG_SYSLOG_SERVER_IP);
gateway_config->software_config.syslog_server_port = CONFIG_SYSLOG_SERVER_PORT;
#else
gateway_config->software_config.is_syslog_server_usage = false;
strcpy(gateway_config->software_config.syslog_server_ip, "NULL");
gateway_config->software_config.syslog_server_port = 0;
#endif
#ifdef CONFIG_NTP_SERVER_USING
gateway_config->software_config.is_ntp_server_usage = true;
strcpy(gateway_config->software_config.ntp_server_url, CONFIG_NTP_SERVER_URL); strcpy(gateway_config->software_config.ntp_server_url, CONFIG_NTP_SERVER_URL);
strcpy(gateway_config->software_config.ntp_time_zone, CONFIG_NTP_TIME_ZONE); strcpy(gateway_config->software_config.ntp_time_zone, CONFIG_NTP_TIME_ZONE);
#else
gateway_config->software_config.is_ntp_server_usage = false;
strcpy(gateway_config->software_config.ntp_server_url, "NULL");
strcpy(gateway_config->software_config.ntp_time_zone, "NULL");
#endif
#ifdef CONFIG_FIRMWARE_UPGRADE_SERVER_USING
gateway_config->software_config.is_ota_server_usage = true;
strcpy(gateway_config->software_config.firmware_upgrade_url, CONFIG_FIRMWARE_UPGRADE_URL); strcpy(gateway_config->software_config.firmware_upgrade_url, CONFIG_FIRMWARE_UPGRADE_URL);
#else
gateway_config->software_config.is_ota_server_usage = false;
strcpy(gateway_config->software_config.firmware_upgrade_url, "NULL");
#endif
zh_save_config(gateway_config); zh_save_config(gateway_config);
return; return;
} }
nvs_get_u8(nvs_handle, "lan_mode", (uint8_t *)&gateway_config->software_config.is_lan_mode); esp_err_t err = ESP_OK;
size_t size = 0; size_t size = 0;
nvs_get_str(nvs_handle, "ssid_name", NULL, &size); err += nvs_get_u8(nvs_handle, "lan_mode", (uint8_t *)&gateway_config->software_config.is_lan_mode);
nvs_get_str(nvs_handle, "ssid_name", gateway_config->software_config.ssid_name, &size); err += nvs_get_str(nvs_handle, "ssid_name", NULL, &size);
nvs_get_str(nvs_handle, "ssid_password", NULL, &size); err += nvs_get_str(nvs_handle, "ssid_name", gateway_config->software_config.ssid_name, &size);
nvs_get_str(nvs_handle, "ssid_password", gateway_config->software_config.ssid_password, &size); err += nvs_get_str(nvs_handle, "ssid_password", NULL, &size);
nvs_get_str(nvs_handle, "mqtt_url", NULL, &size); err += nvs_get_str(nvs_handle, "ssid_password", gateway_config->software_config.ssid_password, &size);
nvs_get_str(nvs_handle, "mqtt_url", gateway_config->software_config.mqtt_broker_url, &size); err += nvs_get_str(nvs_handle, "mqtt_url", NULL, &size);
nvs_get_str(nvs_handle, "topic_prefix", NULL, &size); err += nvs_get_str(nvs_handle, "mqtt_url", gateway_config->software_config.mqtt_broker_url, &size);
nvs_get_str(nvs_handle, "topic_prefix", gateway_config->software_config.mqtt_topic_prefix, &size); err += nvs_get_str(nvs_handle, "topic_prefix", NULL, &size);
nvs_get_str(nvs_handle, "ntp_url", NULL, &size); err += nvs_get_str(nvs_handle, "topic_prefix", gateway_config->software_config.mqtt_topic_prefix, &size);
nvs_get_str(nvs_handle, "ntp_url", gateway_config->software_config.ntp_server_url, &size); err += nvs_get_u8(nvs_handle, "syslog_usage", (uint8_t *)&gateway_config->software_config.is_syslog_server_usage);
nvs_get_str(nvs_handle, "time_zone", NULL, &size); err += nvs_get_str(nvs_handle, "syslog_ip", NULL, &size);
nvs_get_str(nvs_handle, "time_zone", gateway_config->software_config.ntp_time_zone, &size); err += nvs_get_str(nvs_handle, "syslog_ip", gateway_config->software_config.syslog_server_ip, &size);
nvs_get_str(nvs_handle, "upgrade_url", NULL, &size); err += nvs_get_u32(nvs_handle, "syslog_port", &gateway_config->software_config.syslog_server_port);
nvs_get_str(nvs_handle, "upgrade_url", gateway_config->software_config.firmware_upgrade_url, &size); err += nvs_get_u8(nvs_handle, "ntp_usage", (uint8_t *)&gateway_config->software_config.is_ntp_server_usage);
err += nvs_get_str(nvs_handle, "ntp_url", NULL, &size);
err += nvs_get_str(nvs_handle, "ntp_url", gateway_config->software_config.ntp_server_url, &size);
err += nvs_get_str(nvs_handle, "time_zone", NULL, &size);
err += nvs_get_str(nvs_handle, "time_zone", gateway_config->software_config.ntp_time_zone, &size);
err += nvs_get_u8(nvs_handle, "ota_usage", (uint8_t *)&gateway_config->software_config.is_ota_server_usage);
err += nvs_get_str(nvs_handle, "upgrade_url", NULL, &size);
err += nvs_get_str(nvs_handle, "upgrade_url", gateway_config->software_config.firmware_upgrade_url, &size);
nvs_close(nvs_handle); nvs_close(nvs_handle);
if (err != ESP_OK)
{
goto SETUP_INITIAL_SETTINGS;
}
} }
void zh_save_config(const gateway_config_t *gateway_config) void zh_save_config(const gateway_config_t *gateway_config)
@ -144,8 +178,13 @@ void zh_save_config(const gateway_config_t *gateway_config)
nvs_set_str(nvs_handle, "ssid_password", gateway_config->software_config.ssid_password); nvs_set_str(nvs_handle, "ssid_password", gateway_config->software_config.ssid_password);
nvs_set_str(nvs_handle, "mqtt_url", gateway_config->software_config.mqtt_broker_url); nvs_set_str(nvs_handle, "mqtt_url", gateway_config->software_config.mqtt_broker_url);
nvs_set_str(nvs_handle, "topic_prefix", gateway_config->software_config.mqtt_topic_prefix); nvs_set_str(nvs_handle, "topic_prefix", gateway_config->software_config.mqtt_topic_prefix);
nvs_set_u8(nvs_handle, "syslog_usage", gateway_config->software_config.is_syslog_server_usage);
nvs_set_str(nvs_handle, "syslog_ip", gateway_config->software_config.syslog_server_ip);
nvs_set_u32(nvs_handle, "syslog_port", gateway_config->software_config.syslog_server_port);
nvs_set_u8(nvs_handle, "ntp_usage", gateway_config->software_config.is_ntp_server_usage);
nvs_set_str(nvs_handle, "ntp_url", gateway_config->software_config.ntp_server_url); nvs_set_str(nvs_handle, "ntp_url", gateway_config->software_config.ntp_server_url);
nvs_set_str(nvs_handle, "time_zone", gateway_config->software_config.ntp_time_zone); nvs_set_str(nvs_handle, "time_zone", gateway_config->software_config.ntp_time_zone);
nvs_set_u8(nvs_handle, "ota_usage", gateway_config->software_config.is_ota_server_usage);
nvs_set_str(nvs_handle, "upgrade_url", gateway_config->software_config.firmware_upgrade_url); nvs_set_str(nvs_handle, "upgrade_url", gateway_config->software_config.firmware_upgrade_url);
nvs_close(nvs_handle); nvs_close(nvs_handle);
} }
@ -161,11 +200,22 @@ void zh_eth_event_handler(void *arg, esp_event_base_t event_base, int32_t event_
esp_mqtt_client_stop(gateway_config->mqtt_client); esp_mqtt_client_stop(gateway_config->mqtt_client);
gateway_config->mqtt_is_enable = false; gateway_config->mqtt_is_enable = false;
} }
if (gateway_config->sntp_is_enable == true) if (gateway_config->software_config.is_ntp_server_usage == true)
{ {
esp_sntp_stop(); if (gateway_config->sntp_is_enable == true)
gateway_config->sntp_is_enable = false; {
vTaskDelete(gateway_config->gateway_current_time_task); esp_sntp_stop();
gateway_config->sntp_is_enable = false;
vTaskDelete(gateway_config->gateway_current_time_task);
}
}
if (gateway_config->software_config.is_syslog_server_usage == true)
{
if (gateway_config->syslog_is_enable == true)
{
zh_syslog_deinit();
gateway_config->syslog_is_enable = false;
}
} }
break; break;
case IP_EVENT_ETH_GOT_IP: case IP_EVENT_ETH_GOT_IP:
@ -179,14 +229,25 @@ void zh_eth_event_handler(void *arg, esp_event_base_t event_base, int32_t event_
esp_mqtt_client_start(gateway_config->mqtt_client); esp_mqtt_client_start(gateway_config->mqtt_client);
gateway_config->mqtt_is_enable = true; gateway_config->mqtt_is_enable = true;
} }
if (gateway_config->sntp_is_enable == false) if (gateway_config->software_config.is_ntp_server_usage == true)
{ {
esp_sntp_setoperatingmode(SNTP_OPMODE_POLL); if (gateway_config->sntp_is_enable == false)
sntp_set_sync_mode(SNTP_SYNC_MODE_SMOOTH); {
esp_sntp_setservername(0, gateway_config->software_config.ntp_server_url); esp_sntp_setoperatingmode(SNTP_OPMODE_POLL);
esp_sntp_init(); sntp_set_sync_mode(SNTP_SYNC_MODE_SMOOTH);
gateway_config->sntp_is_enable = true; esp_sntp_setservername(0, gateway_config->software_config.ntp_server_url);
xTaskCreatePinnedToCore(&zh_send_espnow_current_time_task, "NULL", ZH_SNTP_STACK_SIZE, gateway_config, ZH_SNTP_TASK_PRIORITY, (TaskHandle_t *)&gateway_config->gateway_current_time_task, tskNO_AFFINITY); esp_sntp_init();
gateway_config->sntp_is_enable = true;
xTaskCreatePinnedToCore(&zh_send_espnow_current_time_task, "NULL", ZH_SNTP_STACK_SIZE, gateway_config, ZH_SNTP_TASK_PRIORITY, (TaskHandle_t *)&gateway_config->gateway_current_time_task, tskNO_AFFINITY);
}
}
if (gateway_config->software_config.is_syslog_server_usage == true)
{
zh_syslog_init_config_t syslog_init_config = ZH_SYSLOG_INIT_CONFIG_DEFAULT();
memcpy(syslog_init_config.syslog_ip, gateway_config->software_config.syslog_server_ip, strlen(gateway_config->software_config.syslog_server_ip));
syslog_init_config.syslog_port = gateway_config->software_config.syslog_server_port;
zh_syslog_init(&syslog_init_config);
gateway_config->syslog_is_enable = true;
} }
break; break;
default: default:
@ -208,11 +269,22 @@ void zh_wifi_event_handler(void *arg, esp_event_base_t event_base, int32_t event
esp_mqtt_client_stop(gateway_config->mqtt_client); esp_mqtt_client_stop(gateway_config->mqtt_client);
gateway_config->mqtt_is_enable = false; gateway_config->mqtt_is_enable = false;
} }
if (gateway_config->sntp_is_enable == true) if (gateway_config->software_config.is_ntp_server_usage == true)
{ {
esp_sntp_stop(); if (gateway_config->sntp_is_enable == true)
gateway_config->sntp_is_enable = false; {
vTaskDelete(gateway_config->gateway_current_time_task); esp_sntp_stop();
gateway_config->sntp_is_enable = false;
vTaskDelete(gateway_config->gateway_current_time_task);
}
}
if (gateway_config->software_config.is_syslog_server_usage == true)
{
if (gateway_config->syslog_is_enable == true)
{
zh_syslog_deinit();
gateway_config->syslog_is_enable = false;
}
} }
if (gateway_config->wifi_reconnect_retry_num < ZH_WIFI_MAXIMUM_RETRY) if (gateway_config->wifi_reconnect_retry_num < ZH_WIFI_MAXIMUM_RETRY)
{ {
@ -240,14 +312,25 @@ void zh_wifi_event_handler(void *arg, esp_event_base_t event_base, int32_t event
esp_mqtt_client_start(gateway_config->mqtt_client); esp_mqtt_client_start(gateway_config->mqtt_client);
gateway_config->mqtt_is_enable = true; gateway_config->mqtt_is_enable = true;
} }
if (gateway_config->sntp_is_enable == false) if (gateway_config->software_config.is_ntp_server_usage == true)
{ {
esp_sntp_setoperatingmode(SNTP_OPMODE_POLL); if (gateway_config->sntp_is_enable == false)
sntp_set_sync_mode(SNTP_SYNC_MODE_SMOOTH); {
esp_sntp_setservername(0, gateway_config->software_config.ntp_server_url); esp_sntp_setoperatingmode(SNTP_OPMODE_POLL);
esp_sntp_init(); sntp_set_sync_mode(SNTP_SYNC_MODE_SMOOTH);
gateway_config->sntp_is_enable = true; esp_sntp_setservername(0, gateway_config->software_config.ntp_server_url);
xTaskCreatePinnedToCore(&zh_send_espnow_current_time_task, "NULL", ZH_SNTP_STACK_SIZE, gateway_config, ZH_SNTP_TASK_PRIORITY, (TaskHandle_t *)&gateway_config->gateway_current_time_task, tskNO_AFFINITY); esp_sntp_init();
gateway_config->sntp_is_enable = true;
xTaskCreatePinnedToCore(&zh_send_espnow_current_time_task, "NULL", ZH_SNTP_STACK_SIZE, gateway_config, ZH_SNTP_TASK_PRIORITY, (TaskHandle_t *)&gateway_config->gateway_current_time_task, tskNO_AFFINITY);
}
}
if (gateway_config->software_config.is_syslog_server_usage == true)
{
zh_syslog_init_config_t syslog_init_config = ZH_SYSLOG_INIT_CONFIG_DEFAULT();
memcpy(syslog_init_config.syslog_ip, gateway_config->software_config.syslog_server_ip, strlen(gateway_config->software_config.syslog_server_ip));
syslog_init_config.syslog_port = gateway_config->software_config.syslog_server_port;
zh_syslog_init(&syslog_init_config);
gateway_config->syslog_is_enable = true;
} }
break; break;
default: default:
@ -287,20 +370,40 @@ void zh_espnow_event_handler(void *arg, esp_event_base_t event_base, int32_t eve
case ZHPT_KEEP_ALIVE: case ZHPT_KEEP_ALIVE:
if (xSemaphoreTake(gateway_config->device_check_in_progress_mutex, portTICK_PERIOD_MS) == pdTRUE) if (xSemaphoreTake(gateway_config->device_check_in_progress_mutex, portTICK_PERIOD_MS) == pdTRUE)
{ {
bool is_found = false;
for (uint16_t i = 0; i < zh_vector_get_size(&gateway_config->available_device_vector); ++i) for (uint16_t i = 0; i < zh_vector_get_size(&gateway_config->available_device_vector); ++i)
{ {
available_device_t *available_device = zh_vector_get_item(&gateway_config->available_device_vector, i); available_device_t *available_device = zh_vector_get_item(&gateway_config->available_device_vector, i);
if (memcmp(recv_data->mac_addr, available_device->mac_addr, 6) == 0) if (memcmp(recv_data->mac_addr, available_device->mac_addr, 6) == 0)
{ {
zh_vector_delete_item(&gateway_config->available_device_vector, i); zh_vector_delete_item(&gateway_config->available_device_vector, i);
is_found = true;
} }
} }
available_device_t available_device = {0}; char *mac = (char *)heap_caps_malloc(18, MALLOC_CAP_8BIT);
available_device.device_type = data->device_type; memset(mac, 0, 18);
memcpy(available_device.mac_addr, recv_data->mac_addr, 6); sprintf(mac, "" MAC_STR "", MAC2STR(recv_data->mac_addr));
available_device.frequency = data->payload_data.keep_alive_message.message_frequency; if (data->payload_data.keep_alive_message.online_status == ZH_ONLINE)
available_device.time = esp_timer_get_time() / 1000000; {
zh_vector_push_back(&gateway_config->available_device_vector, &available_device); available_device_t available_device = {0};
available_device.device_type = data->device_type;
memcpy(available_device.mac_addr, recv_data->mac_addr, 6);
available_device.frequency = data->payload_data.keep_alive_message.message_frequency;
available_device.time = esp_timer_get_time() / 1000000;
zh_vector_push_back(&gateway_config->available_device_vector, &available_device);
if (gateway_config->syslog_is_enable == true && is_found == false)
{
zh_syslog_send(ZH_USER, ZH_INFO, mac, zh_get_device_type_value_name(data->device_type), "Connected to gateway.");
}
}
else
{
if (gateway_config->syslog_is_enable == true)
{
zh_syslog_send(ZH_USER, ZH_WARNING, mac, zh_get_device_type_value_name(data->device_type), "Disconnected from gateway.");
}
}
heap_caps_free(mac);
xSemaphoreGive(gateway_config->device_check_in_progress_mutex); xSemaphoreGive(gateway_config->device_check_in_progress_mutex);
} }
zh_espnow_send_mqtt_json_keep_alive_message(data, recv_data->mac_addr, gateway_config); zh_espnow_send_mqtt_json_keep_alive_message(data, recv_data->mac_addr, gateway_config);
@ -378,9 +481,35 @@ void zh_espnow_event_handler(void *arg, esp_event_base_t event_base, int32_t eve
break; break;
case ZHPT_UPDATE_FAIL: case ZHPT_UPDATE_FAIL:
esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_fail", 0, 2, true); esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_fail", 0, 2, true);
if (gateway_config->syslog_is_enable == true)
{
char *mac = (char *)heap_caps_malloc(18, MALLOC_CAP_8BIT);
memset(mac, 0, 18);
sprintf(mac, "" MAC_STR "", MAC2STR(recv_data->mac_addr));
zh_syslog_send(ZH_USER, ZH_ERR, mac, zh_get_device_type_value_name(data->device_type), "Firmware update fail. Incorrect bin file.");
heap_caps_free(mac);
}
break; break;
case ZHPT_UPDATE_SUCCESS: case ZHPT_UPDATE_SUCCESS:
esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_success", 0, 2, true); esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_success", 0, 2, true);
if (gateway_config->syslog_is_enable == true)
{
char *mac = (char *)heap_caps_malloc(18, MALLOC_CAP_8BIT);
memset(mac, 0, 18);
sprintf(mac, "" MAC_STR "", MAC2STR(recv_data->mac_addr));
zh_syslog_send(ZH_USER, ZH_INFO, mac, zh_get_device_type_value_name(data->device_type), "Firmware update success.");
heap_caps_free(mac);
}
break;
case ZHPT_ERROR:
if (gateway_config->syslog_is_enable == true)
{
char *mac = (char *)heap_caps_malloc(18, MALLOC_CAP_8BIT);
memset(mac, 0, 18);
sprintf(mac, "" MAC_STR "", MAC2STR(recv_data->mac_addr));
zh_syslog_send(ZH_USER, ZH_ERR, mac, zh_get_device_type_value_name(data->device_type), data->payload_data.status_message.error_message.message);
heap_caps_free(mac);
}
break; break;
default: default:
break; break;
@ -413,6 +542,14 @@ void zh_mqtt_event_handler(void *arg, esp_event_base_t event_base, int32_t event
case MQTT_EVENT_CONNECTED: case MQTT_EVENT_CONNECTED:
if (gateway_config->mqtt_is_connected == false) if (gateway_config->mqtt_is_connected == false)
{ {
if (gateway_config->syslog_is_enable == true)
{
char *mac = (char *)heap_caps_malloc(18, MALLOC_CAP_8BIT);
memset(mac, 0, 18);
sprintf(mac, "" MAC_STR "", MAC2STR(gateway_config->self_mac));
zh_syslog_send(ZH_USER, ZH_INFO, mac, zh_get_device_type_value_name(ZHDT_GATEWAY), "Connected to MQTT.");
heap_caps_free(mac);
}
char *topic_for_subscribe = NULL; char *topic_for_subscribe = NULL;
char *supported_device_type = NULL; char *supported_device_type = NULL;
for (zh_device_type_t i = 1; i <= ZHDT_MAX; ++i) for (zh_device_type_t i = 1; i <= ZHDT_MAX; ++i)
@ -434,6 +571,14 @@ void zh_mqtt_event_handler(void *arg, esp_event_base_t event_base, int32_t event
case MQTT_EVENT_DISCONNECTED: case MQTT_EVENT_DISCONNECTED:
if (gateway_config->mqtt_is_connected == true) if (gateway_config->mqtt_is_connected == true)
{ {
if (gateway_config->syslog_is_enable == true)
{
char *mac = (char *)heap_caps_malloc(18, MALLOC_CAP_8BIT);
memset(mac, 0, 18);
sprintf(mac, "" MAC_STR "", MAC2STR(gateway_config->self_mac));
zh_syslog_send(ZH_USER, ZH_INFO, mac, zh_get_device_type_value_name(ZHDT_GATEWAY), "Disconnected from MQTT.");
heap_caps_free(mac);
}
vTaskDelete(gateway_config->gateway_attributes_message_task); vTaskDelete(gateway_config->gateway_attributes_message_task);
vTaskDelete(gateway_config->gateway_keep_alive_message_task); vTaskDelete(gateway_config->gateway_keep_alive_message_task);
vTaskDelete(gateway_config->device_availability_check_task); vTaskDelete(gateway_config->device_availability_check_task);
@ -500,7 +645,7 @@ void zh_mqtt_event_handler(void *arg, esp_event_base_t event_base, int32_t event
{ {
if (memcmp(gateway_config->self_mac, incoming_data_mac, 6) == 0) if (memcmp(gateway_config->self_mac, incoming_data_mac, 6) == 0)
{ {
if (strncmp(incoming_payload, "update", strlen(incoming_payload) + 1) == 0) if (strncmp(incoming_payload, "update", strlen(incoming_payload) + 1) == 0 && gateway_config->software_config.is_ota_server_usage == true)
{ {
if (xSemaphoreTake(gateway_config->self_ota_in_progress_mutex, portTICK_PERIOD_MS) == pdTRUE) if (xSemaphoreTake(gateway_config->self_ota_in_progress_mutex, portTICK_PERIOD_MS) == pdTRUE)
{ {
@ -510,8 +655,6 @@ void zh_mqtt_event_handler(void *arg, esp_event_base_t event_base, int32_t event
} }
else if (strncmp(incoming_payload, "restart", strlen(incoming_payload) + 1) == 0) else if (strncmp(incoming_payload, "restart", strlen(incoming_payload) + 1) == 0)
{ {
zh_espnow_data_t data = {0};
data.device_type = ZHDT_GATEWAY;
data.payload_type = ZHPT_KEEP_ALIVE; data.payload_type = ZHPT_KEEP_ALIVE;
data.payload_data.keep_alive_message.online_status = ZH_OFFLINE; data.payload_data.keep_alive_message.online_status = ZH_OFFLINE;
zh_send_message(NULL, (uint8_t *)&data, sizeof(zh_espnow_data_t)); zh_send_message(NULL, (uint8_t *)&data, sizeof(zh_espnow_data_t));
@ -529,7 +672,7 @@ void zh_mqtt_event_handler(void *arg, esp_event_base_t event_base, int32_t event
switch (incoming_data_payload_type) switch (incoming_data_payload_type)
{ {
case ZHPT_NONE: case ZHPT_NONE:
if (strncmp(incoming_payload, "update", strlen(incoming_payload) + 1) == 0) if (strncmp(incoming_payload, "update", strlen(incoming_payload) + 1) == 0 && gateway_config->software_config.is_ota_server_usage == true)
{ {
data.payload_type = ZHPT_UPDATE; data.payload_type = ZHPT_UPDATE;
zh_send_message(incoming_data_mac, (uint8_t *)&data, sizeof(zh_espnow_data_t)); zh_send_message(incoming_data_mac, (uint8_t *)&data, sizeof(zh_espnow_data_t));
@ -617,6 +760,12 @@ void zh_mqtt_event_handler(void *arg, esp_event_base_t event_base, int32_t event
break; break;
} }
data.payload_data.config_message.switch_hardware_config_message.sensor_type = zh_sensor_type_check(atoi(extracted_hardware_data)); data.payload_data.config_message.switch_hardware_config_message.sensor_type = zh_sensor_type_check(atoi(extracted_hardware_data));
extracted_hardware_data = strtok(NULL, ","); // Extract sensor measurement frequency value.
if (extracted_hardware_data == NULL)
{
break;
}
data.payload_data.config_message.switch_hardware_config_message.measurement_frequency = zh_uint16_value_check(atoi(extracted_hardware_data));
data.payload_type = ZHPT_HARDWARE; data.payload_type = ZHPT_HARDWARE;
zh_send_message(incoming_data_mac, (uint8_t *)&data, sizeof(zh_espnow_data_t)); zh_send_message(incoming_data_mac, (uint8_t *)&data, sizeof(zh_espnow_data_t));
break; break;
@ -628,7 +777,7 @@ void zh_mqtt_event_handler(void *arg, esp_event_base_t event_base, int32_t event
switch (incoming_data_payload_type) switch (incoming_data_payload_type)
{ {
case ZHPT_NONE: case ZHPT_NONE:
if (strncmp(incoming_payload, "update", strlen(incoming_payload) + 1) == 0) if (strncmp(incoming_payload, "update", strlen(incoming_payload) + 1) == 0 && gateway_config->software_config.is_ota_server_usage == true)
{ {
data.payload_type = ZHPT_UPDATE; data.payload_type = ZHPT_UPDATE;
zh_send_message(incoming_data_mac, (uint8_t *)&data, sizeof(zh_espnow_data_t)); zh_send_message(incoming_data_mac, (uint8_t *)&data, sizeof(zh_espnow_data_t));
@ -735,7 +884,7 @@ void zh_mqtt_event_handler(void *arg, esp_event_base_t event_base, int32_t event
switch (incoming_data_payload_type) switch (incoming_data_payload_type)
{ {
case ZHPT_NONE: case ZHPT_NONE:
if (strncmp(incoming_payload, "update", strlen(incoming_payload) + 1) == 0) if (strncmp(incoming_payload, "update", strlen(incoming_payload) + 1) == 0 && gateway_config->software_config.is_ota_server_usage == true)
{ {
data.payload_type = ZHPT_UPDATE; data.payload_type = ZHPT_UPDATE;
zh_send_message(incoming_data_mac, (uint8_t *)&data, sizeof(zh_espnow_data_t)); zh_send_message(incoming_data_mac, (uint8_t *)&data, sizeof(zh_espnow_data_t));
@ -798,7 +947,7 @@ void zh_mqtt_event_handler(void *arg, esp_event_base_t event_base, int32_t event
switch (incoming_data_payload_type) switch (incoming_data_payload_type)
{ {
case ZHPT_NONE: case ZHPT_NONE:
if (strncmp(incoming_payload, "update", strlen(incoming_payload) + 1) == 0) if (strncmp(incoming_payload, "update", strlen(incoming_payload) + 1) == 0 && gateway_config->software_config.is_ota_server_usage == true)
{ {
data.payload_type = ZHPT_UPDATE; data.payload_type = ZHPT_UPDATE;
zh_send_message(incoming_data_mac, (uint8_t *)&data, sizeof(zh_espnow_data_t)); zh_send_message(incoming_data_mac, (uint8_t *)&data, sizeof(zh_espnow_data_t));
@ -827,6 +976,9 @@ void zh_mqtt_event_handler(void *arg, esp_event_base_t event_base, int32_t event
void zh_self_ota_update_task(void *pvParameter) void zh_self_ota_update_task(void *pvParameter)
{ {
gateway_config_t *gateway_config = pvParameter; gateway_config_t *gateway_config = pvParameter;
char *mac = (char *)heap_caps_malloc(18, MALLOC_CAP_8BIT);
memset(mac, 0, 18);
sprintf(mac, "" MAC_STR "", MAC2STR(gateway_config->self_mac));
xSemaphoreTake(gateway_config->self_ota_in_progress_mutex, portMAX_DELAY); xSemaphoreTake(gateway_config->self_ota_in_progress_mutex, portMAX_DELAY);
char *topic = (char *)heap_caps_malloc(strlen(gateway_config->software_config.mqtt_topic_prefix) + strlen(zh_get_device_type_value_name(ZHDT_GATEWAY)) + 20, MALLOC_CAP_8BIT); char *topic = (char *)heap_caps_malloc(strlen(gateway_config->software_config.mqtt_topic_prefix) + strlen(zh_get_device_type_value_name(ZHDT_GATEWAY)) + 20, MALLOC_CAP_8BIT);
memset(topic, 0, strlen(gateway_config->software_config.mqtt_topic_prefix) + strlen(zh_get_device_type_value_name(ZHDT_GATEWAY)) + 20); memset(topic, 0, strlen(gateway_config->software_config.mqtt_topic_prefix) + strlen(zh_get_device_type_value_name(ZHDT_GATEWAY)) + 20);
@ -835,6 +987,10 @@ void zh_self_ota_update_task(void *pvParameter)
esp_ota_handle_t update_handle = {0}; esp_ota_handle_t update_handle = {0};
const esp_partition_t *update_partition = NULL; const esp_partition_t *update_partition = NULL;
esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_begin", 0, 2, true); esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_begin", 0, 2, true);
if (gateway_config->syslog_is_enable == true)
{
zh_syslog_send(ZH_USER, ZH_INFO, mac, zh_get_device_type_value_name(ZHDT_GATEWAY), "Firmware update begin.");
}
const esp_app_desc_t *app_info = esp_app_get_description(); const esp_app_desc_t *app_info = esp_app_get_description();
char *app_name = (char *)heap_caps_malloc(strlen(gateway_config->software_config.firmware_upgrade_url) + strlen(app_info->project_name) + 6, MALLOC_CAP_8BIT); char *app_name = (char *)heap_caps_malloc(strlen(gateway_config->software_config.firmware_upgrade_url) + strlen(app_info->project_name) + 6, MALLOC_CAP_8BIT);
memset(app_name, 0, strlen(gateway_config->software_config.firmware_upgrade_url) + strlen(app_info->project_name) + 6); memset(app_name, 0, strlen(gateway_config->software_config.firmware_upgrade_url) + strlen(app_info->project_name) + 6);
@ -852,6 +1008,10 @@ void zh_self_ota_update_task(void *pvParameter)
esp_http_client_fetch_headers(https_client); esp_http_client_fetch_headers(https_client);
update_partition = esp_ota_get_next_update_partition(NULL); update_partition = esp_ota_get_next_update_partition(NULL);
esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_progress", 0, 2, true); esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_progress", 0, 2, true);
if (gateway_config->syslog_is_enable == true)
{
zh_syslog_send(ZH_USER, ZH_INFO, mac, zh_get_device_type_value_name(ZHDT_GATEWAY), "Firmware update progress.");
}
esp_ota_begin(update_partition, OTA_WITH_SEQUENTIAL_WRITES, &update_handle); esp_ota_begin(update_partition, OTA_WITH_SEQUENTIAL_WRITES, &update_handle);
for (;;) for (;;)
{ {
@ -861,7 +1021,12 @@ void zh_self_ota_update_task(void *pvParameter)
esp_http_client_close(https_client); esp_http_client_close(https_client);
esp_http_client_cleanup(https_client); esp_http_client_cleanup(https_client);
esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_error_data_size", 0, 2, true); esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_error_data_size", 0, 2, true);
if (gateway_config->syslog_is_enable == true)
{
zh_syslog_send(ZH_USER, ZH_ERR, mac, zh_get_device_type_value_name(ZHDT_GATEWAY), "Firmware update error. Incorrect size of read data.");
}
heap_caps_free(topic); heap_caps_free(topic);
heap_caps_free(mac);
xSemaphoreGive(gateway_config->self_ota_in_progress_mutex); xSemaphoreGive(gateway_config->self_ota_in_progress_mutex);
vTaskDelete(NULL); vTaskDelete(NULL);
} }
@ -879,7 +1044,12 @@ void zh_self_ota_update_task(void *pvParameter)
esp_http_client_close(https_client); esp_http_client_close(https_client);
esp_http_client_cleanup(https_client); esp_http_client_cleanup(https_client);
esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_fail", 0, 2, true); esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_fail", 0, 2, true);
if (gateway_config->syslog_is_enable == true)
{
zh_syslog_send(ZH_USER, ZH_ERR, mac, zh_get_device_type_value_name(ZHDT_GATEWAY), "Firmware update fail. Incorrect bin file.");
}
heap_caps_free(topic); heap_caps_free(topic);
heap_caps_free(mac);
xSemaphoreGive(gateway_config->self_ota_in_progress_mutex); xSemaphoreGive(gateway_config->self_ota_in_progress_mutex);
vTaskDelete(NULL); vTaskDelete(NULL);
} }
@ -887,7 +1057,12 @@ void zh_self_ota_update_task(void *pvParameter)
esp_http_client_close(https_client); esp_http_client_close(https_client);
esp_http_client_cleanup(https_client); esp_http_client_cleanup(https_client);
esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_success", 0, 2, true); esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_success", 0, 2, true);
if (gateway_config->syslog_is_enable == true)
{
zh_syslog_send(ZH_USER, ZH_INFO, mac, zh_get_device_type_value_name(ZHDT_GATEWAY), "Firmware update success.");
}
heap_caps_free(topic); heap_caps_free(topic);
heap_caps_free(mac);
zh_espnow_data_t data = {0}; zh_espnow_data_t data = {0};
data.device_type = ZHDT_GATEWAY; data.device_type = ZHDT_GATEWAY;
data.payload_type = ZHPT_KEEP_ALIVE; data.payload_type = ZHPT_KEEP_ALIVE;
@ -900,6 +1075,9 @@ void zh_self_ota_update_task(void *pvParameter)
void zh_espnow_ota_update_task(void *pvParameter) void zh_espnow_ota_update_task(void *pvParameter)
{ {
gateway_config_t *gateway_config = pvParameter; gateway_config_t *gateway_config = pvParameter;
char *mac = (char *)heap_caps_malloc(18, MALLOC_CAP_8BIT);
memset(mac, 0, 18);
sprintf(mac, "" MAC_STR "", MAC2STR(gateway_config->espnow_ota_data.mac_addr));
xSemaphoreTake(gateway_config->espnow_ota_in_progress_mutex, portMAX_DELAY); xSemaphoreTake(gateway_config->espnow_ota_in_progress_mutex, portMAX_DELAY);
zh_espnow_data_t data = {0}; zh_espnow_data_t data = {0};
data.device_type = ZHDT_GATEWAY; data.device_type = ZHDT_GATEWAY;
@ -907,6 +1085,10 @@ void zh_espnow_ota_update_task(void *pvParameter)
memset(topic, 0, strlen(gateway_config->software_config.mqtt_topic_prefix) + strlen(zh_get_device_type_value_name(gateway_config->espnow_ota_data.device_type)) + 20); memset(topic, 0, strlen(gateway_config->software_config.mqtt_topic_prefix) + strlen(zh_get_device_type_value_name(gateway_config->espnow_ota_data.device_type)) + 20);
sprintf(topic, "%s/%s/" MAC_STR, gateway_config->software_config.mqtt_topic_prefix, zh_get_device_type_value_name(gateway_config->espnow_ota_data.device_type), MAC2STR(gateway_config->espnow_ota_data.mac_addr)); sprintf(topic, "%s/%s/" MAC_STR, gateway_config->software_config.mqtt_topic_prefix, zh_get_device_type_value_name(gateway_config->espnow_ota_data.device_type), MAC2STR(gateway_config->espnow_ota_data.mac_addr));
esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_begin", 0, 2, true); esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_begin", 0, 2, true);
if (gateway_config->syslog_is_enable == true)
{
zh_syslog_send(ZH_USER, ZH_INFO, mac, zh_get_device_type_value_name(gateway_config->espnow_ota_data.device_type), "Firmware update begin.");
}
char espnow_ota_write_data[sizeof(data.payload_data.ota_message.espnow_ota_message.data) + 1] = {0}; char espnow_ota_write_data[sizeof(data.payload_data.ota_message.espnow_ota_message.data) + 1] = {0};
char *app_name = (char *)heap_caps_malloc(strlen(gateway_config->software_config.firmware_upgrade_url) + strlen(gateway_config->espnow_ota_data.app_name) + 6, MALLOC_CAP_8BIT); char *app_name = (char *)heap_caps_malloc(strlen(gateway_config->software_config.firmware_upgrade_url) + strlen(gateway_config->espnow_ota_data.app_name) + 6, MALLOC_CAP_8BIT);
memset(app_name, 0, strlen(gateway_config->software_config.firmware_upgrade_url) + strlen(gateway_config->espnow_ota_data.app_name) + 6); memset(app_name, 0, strlen(gateway_config->software_config.firmware_upgrade_url) + strlen(gateway_config->espnow_ota_data.app_name) + 6);
@ -931,11 +1113,20 @@ void zh_espnow_ota_update_task(void *pvParameter)
data.payload_type = ZHPT_UPDATE_ERROR; data.payload_type = ZHPT_UPDATE_ERROR;
zh_send_message(gateway_config->espnow_ota_data.mac_addr, (uint8_t *)&data, sizeof(zh_espnow_data_t)); zh_send_message(gateway_config->espnow_ota_data.mac_addr, (uint8_t *)&data, sizeof(zh_espnow_data_t));
esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_error_begin_timeout", 0, 2, true); esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_error_begin_timeout", 0, 2, true);
if (gateway_config->syslog_is_enable == true)
{
zh_syslog_send(ZH_USER, ZH_ERR, mac, zh_get_device_type_value_name(gateway_config->espnow_ota_data.device_type), "Firmware update error. Timeout exceed.");
}
heap_caps_free(mac);
heap_caps_free(topic); heap_caps_free(topic);
xSemaphoreGive(gateway_config->espnow_ota_in_progress_mutex); xSemaphoreGive(gateway_config->espnow_ota_in_progress_mutex);
vTaskDelete(NULL); vTaskDelete(NULL);
} }
esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_progress", 0, 2, true); esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_progress", 0, 2, true);
if (gateway_config->syslog_is_enable == true)
{
zh_syslog_send(ZH_USER, ZH_INFO, mac, zh_get_device_type_value_name(gateway_config->espnow_ota_data.device_type), "Firmware update progress.");
}
for (;;) for (;;)
{ {
int data_read_size = esp_http_client_read(https_client, espnow_ota_write_data, sizeof(data.payload_data.ota_message.espnow_ota_message.data)); int data_read_size = esp_http_client_read(https_client, espnow_ota_write_data, sizeof(data.payload_data.ota_message.espnow_ota_message.data));
@ -944,6 +1135,11 @@ void zh_espnow_ota_update_task(void *pvParameter)
esp_http_client_close(https_client); esp_http_client_close(https_client);
esp_http_client_cleanup(https_client); esp_http_client_cleanup(https_client);
esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_error_data_size", 0, 2, true); esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_error_data_size", 0, 2, true);
if (gateway_config->syslog_is_enable == true)
{
zh_syslog_send(ZH_USER, ZH_ERR, mac, zh_get_device_type_value_name(gateway_config->espnow_ota_data.device_type), "Firmware update error. Incorrect size of read data.");
}
heap_caps_free(mac);
heap_caps_free(topic); heap_caps_free(topic);
xSemaphoreGive(gateway_config->espnow_ota_in_progress_mutex); xSemaphoreGive(gateway_config->espnow_ota_in_progress_mutex);
vTaskDelete(NULL); vTaskDelete(NULL);
@ -962,6 +1158,11 @@ void zh_espnow_ota_update_task(void *pvParameter)
data.payload_type = ZHPT_UPDATE_ERROR; data.payload_type = ZHPT_UPDATE_ERROR;
zh_send_message(gateway_config->espnow_ota_data.mac_addr, (uint8_t *)&data, sizeof(zh_espnow_data_t)); zh_send_message(gateway_config->espnow_ota_data.mac_addr, (uint8_t *)&data, sizeof(zh_espnow_data_t));
esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_error_progress_timeout", 0, 2, true); esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_error_progress_timeout", 0, 2, true);
if (gateway_config->syslog_is_enable == true)
{
zh_syslog_send(ZH_USER, ZH_ERR, mac, zh_get_device_type_value_name(gateway_config->espnow_ota_data.device_type), "Firmware update error. Timeout exceed.");
}
heap_caps_free(mac);
heap_caps_free(topic); heap_caps_free(topic);
xSemaphoreGive(gateway_config->espnow_ota_in_progress_mutex); xSemaphoreGive(gateway_config->espnow_ota_in_progress_mutex);
vTaskDelete(NULL); vTaskDelete(NULL);
@ -974,6 +1175,11 @@ void zh_espnow_ota_update_task(void *pvParameter)
data.payload_type = ZHPT_UPDATE_END; data.payload_type = ZHPT_UPDATE_END;
zh_send_message(gateway_config->espnow_ota_data.mac_addr, (uint8_t *)&data, sizeof(zh_espnow_data_t)); zh_send_message(gateway_config->espnow_ota_data.mac_addr, (uint8_t *)&data, sizeof(zh_espnow_data_t));
esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_end", 0, 2, true); esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "update_end", 0, 2, true);
if (gateway_config->syslog_is_enable == true)
{
zh_syslog_send(ZH_USER, ZH_INFO, mac, zh_get_device_type_value_name(gateway_config->espnow_ota_data.device_type), "Firmware update end.");
}
heap_caps_free(mac);
heap_caps_free(topic); heap_caps_free(topic);
xSemaphoreGive(gateway_config->espnow_ota_in_progress_mutex); xSemaphoreGive(gateway_config->espnow_ota_in_progress_mutex);
vTaskDelete(NULL); vTaskDelete(NULL);
@ -988,6 +1194,14 @@ void zh_send_espnow_current_time_task(void *pvParameter)
{ {
vTaskDelay(5000 / portTICK_PERIOD_MS); vTaskDelay(5000 / portTICK_PERIOD_MS);
} }
if (gateway_config->syslog_is_enable == true)
{
char *mac = (char *)heap_caps_malloc(18, MALLOC_CAP_8BIT);
memset(mac, 0, 18);
sprintf(mac, "" MAC_STR "", MAC2STR(gateway_config->self_mac));
zh_syslog_send(ZH_USER, ZH_INFO, mac, zh_get_device_type_value_name(ZHDT_GATEWAY), "Connected to NTP.");
heap_caps_free(mac);
}
time_t now; time_t now;
setenv("TZ", gateway_config->software_config.ntp_time_zone, 1); setenv("TZ", gateway_config->software_config.ntp_time_zone, 1);
tzset(); tzset();
@ -1014,19 +1228,27 @@ void zh_device_availability_check_task(void *pvParameter)
{ {
break; break;
} }
if (esp_timer_get_time() / 1000000 > available_device->time + (available_device->frequency * 3)) if (esp_timer_get_time() / 1000000 > available_device->time + (available_device->frequency * 1.50)) // + 50% just in case.
{ {
char *topic = (char *)heap_caps_malloc(strlen(gateway_config->software_config.mqtt_topic_prefix) + strlen(zh_get_device_type_value_name(available_device->device_type)) + 27, MALLOC_CAP_8BIT); char *topic = (char *)heap_caps_malloc(strlen(gateway_config->software_config.mqtt_topic_prefix) + strlen(zh_get_device_type_value_name(available_device->device_type)) + 27, MALLOC_CAP_8BIT);
memset(topic, 0, strlen(gateway_config->software_config.mqtt_topic_prefix) + strlen(zh_get_device_type_value_name(available_device->device_type)) + 27); memset(topic, 0, strlen(gateway_config->software_config.mqtt_topic_prefix) + strlen(zh_get_device_type_value_name(available_device->device_type)) + 27);
sprintf(topic, "%s/%s/" MAC_STR "/status", gateway_config->software_config.mqtt_topic_prefix, zh_get_device_type_value_name(available_device->device_type), MAC2STR(available_device->mac_addr)); sprintf(topic, "%s/%s/" MAC_STR "/status", gateway_config->software_config.mqtt_topic_prefix, zh_get_device_type_value_name(available_device->device_type), MAC2STR(available_device->mac_addr));
esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "offline", 0, 2, true); esp_mqtt_client_publish(gateway_config->mqtt_client, topic, "offline", 0, 2, true);
heap_caps_free(topic); heap_caps_free(topic);
if (gateway_config->syslog_is_enable == true)
{
char *mac = (char *)heap_caps_malloc(18, MALLOC_CAP_8BIT);
memset(mac, 0, 18);
sprintf(mac, "" MAC_STR "", MAC2STR(available_device->mac_addr));
zh_syslog_send(ZH_USER, ZH_WARNING, mac, zh_get_device_type_value_name(available_device->device_type), "Disconnected from gateway.");
heap_caps_free(mac);
}
zh_vector_delete_item(&gateway_config->available_device_vector, i); zh_vector_delete_item(&gateway_config->available_device_vector, i);
goto CHECK; // Since the vector is shifted after item deletion, the item needs to be re-checked. goto CHECK; // Since the vector is shifted after item deletion, the item needs to be re-checked.
} }
} }
xSemaphoreGive(gateway_config->device_check_in_progress_mutex); xSemaphoreGive(gateway_config->device_check_in_progress_mutex);
vTaskDelay(10000 / portTICK_PERIOD_MS); vTaskDelay(1000 / portTICK_PERIOD_MS);
} }
vTaskDelete(NULL); vTaskDelete(NULL);
} }
@ -1089,7 +1311,7 @@ void zh_gateway_send_mqtt_json_config_message(const gateway_config_t *gateway_co
data.payload_data.config_message.binary_sensor_config_message.binary_sensor_device_class = HABSDC_CONNECTIVITY; data.payload_data.config_message.binary_sensor_config_message.binary_sensor_device_class = HABSDC_CONNECTIVITY;
data.payload_data.config_message.binary_sensor_config_message.payload_on = HAONOFT_CONNECT; data.payload_data.config_message.binary_sensor_config_message.payload_on = HAONOFT_CONNECT;
data.payload_data.config_message.binary_sensor_config_message.payload_off = HAONOFT_NONE; data.payload_data.config_message.binary_sensor_config_message.payload_off = HAONOFT_NONE;
data.payload_data.config_message.binary_sensor_config_message.expire_after = 30; data.payload_data.config_message.binary_sensor_config_message.expire_after = ZH_GATEWAY_KEEP_ALIVE_MESSAGE_TIME * 1.50; // + 50% just in case.
data.payload_data.config_message.binary_sensor_config_message.enabled_by_default = true; data.payload_data.config_message.binary_sensor_config_message.enabled_by_default = true;
data.payload_data.config_message.binary_sensor_config_message.force_update = true; data.payload_data.config_message.binary_sensor_config_message.force_update = true;
data.payload_data.config_message.binary_sensor_config_message.qos = 2; data.payload_data.config_message.binary_sensor_config_message.qos = 2;
@ -1111,7 +1333,7 @@ void zh_gateway_send_mqtt_json_keep_alive_message_task(void *pvParameter)
zh_send_message(NULL, (uint8_t *)&data, sizeof(zh_espnow_data_t)); zh_send_message(NULL, (uint8_t *)&data, sizeof(zh_espnow_data_t));
data.payload_type = ZHPT_STATE; data.payload_type = ZHPT_STATE;
zh_espnow_binary_sensor_send_mqtt_json_status_message(&data, gateway_config->self_mac, gateway_config); zh_espnow_binary_sensor_send_mqtt_json_status_message(&data, gateway_config->self_mac, gateway_config);
vTaskDelay(10000 / portTICK_PERIOD_MS); vTaskDelay(ZH_GATEWAY_KEEP_ALIVE_MESSAGE_TIME * 1000 / portTICK_PERIOD_MS);
} }
vTaskDelete(NULL); vTaskDelete(NULL);
} }
@ -1705,7 +1927,7 @@ void zh_espnow_sensor_send_mqtt_json_status_message(const zh_espnow_data_t *devi
case HAST_DHT: case HAST_DHT:
case HAST_AHT: case HAST_AHT:
case HAST_SHT: case HAST_SHT:
case HAST_HTU21D: case HAST_HTU:
case HAST_HDC1080: case HAST_HDC1080:
sprintf(temperature, "%f", device_data->payload_data.status_message.sensor_status_message.temperature); sprintf(temperature, "%f", device_data->payload_data.status_message.sensor_status_message.temperature);
zh_json_add(&json, "temperature", temperature); zh_json_add(&json, "temperature", temperature);

View File

@ -17,6 +17,7 @@
#include "mqtt_client.h" #include "mqtt_client.h"
#include "zh_json.h" #include "zh_json.h"
#include "zh_vector.h" #include "zh_vector.h"
#include "zh_syslog.h"
#include "zh_config.h" #include "zh_config.h"
#ifdef CONFIG_NETWORK_TYPE_DIRECT #ifdef CONFIG_NETWORK_TYPE_DIRECT
@ -63,6 +64,8 @@
#define ZH_MAX_GPIO_NUMBERS 48 // Maximum number of GPIOs on ESP modules. #define ZH_MAX_GPIO_NUMBERS 48 // Maximum number of GPIOs on ESP modules.
#define ZH_GATEWAY_KEEP_ALIVE_MESSAGE_TIME 10 // Frequency of sending a keep alive message (in seconds).
typedef struct // Structure of data exchange between tasks, functions and event handlers. typedef struct // Structure of data exchange between tasks, functions and event handlers.
{ {
struct // Storage structure of gateway configuration data. struct // Storage structure of gateway configuration data.
@ -72,11 +75,17 @@ typedef struct // Structure of data exchange between tasks, functions and event
char ssid_password[64]; // WiFi password. char ssid_password[64]; // WiFi password.
char mqtt_broker_url[64]; // MQTT broker url. char mqtt_broker_url[64]; // MQTT broker url.
char mqtt_topic_prefix[32]; // MQTT topic prefix. char mqtt_topic_prefix[32]; // MQTT topic prefix.
bool is_syslog_server_usage; // Syslog server usage flag.
char syslog_server_ip[16]; // Syslog server IP address.
uint32_t syslog_server_port; // Syslog server port.
bool is_ntp_server_usage; // NTP server usage flag.
char ntp_server_url[64]; // NTP server url. char ntp_server_url[64]; // NTP server url.
char ntp_time_zone[10]; // NTP time zone. char ntp_time_zone[10]; // NTP time zone.
bool is_ota_server_usage; // OTA server usage flag.
char firmware_upgrade_url[64]; // Firmware upgrade url. char firmware_upgrade_url[64]; // Firmware upgrade url.
} software_config; } software_config;
uint8_t self_mac[6]; // Gateway MAC address. @note Depends at WiFi operation mode. uint8_t self_mac[6]; // Gateway MAC address. @note Depends at WiFi operation mode.
bool syslog_is_enable; // Syslog client operation status flag. @note Used to control the Syslog functions when the network connection is established / lost.
bool sntp_is_enable; // SNTP client operation status flag. @note Used to control the SNTP functions when the network connection is established / lost. bool sntp_is_enable; // SNTP client operation status flag. @note Used to control the SNTP functions when the network connection is established / lost.
bool mqtt_is_enable; // MQTT client operation status flag. @note Used to control the MQTT functions when the network connection is established / lost. bool mqtt_is_enable; // MQTT client operation status flag. @note Used to control the MQTT functions when the network connection is established / lost.
bool mqtt_is_connected; // MQTT broker connection status flag. @note Used to control the gateway system tasks when the MQTT connection is established / lost. bool mqtt_is_connected; // MQTT broker connection status flag. @note Used to control the gateway system tasks when the MQTT connection is established / lost.

View File

@ -1 +1 @@
1.0.6 1.0.9