firmware update progress added

This commit is contained in:
Bogdan Pilyugin 2023-01-23 16:50:35 +02:00
parent 0f75145a5f
commit a7340c1a35
7 changed files with 385 additions and 310 deletions

View File

@ -44,8 +44,11 @@ menu "WebGUIApp"
menu "OTA settings" menu "OTA settings"
config WEBGUIAPP_OTA_AUTOUPDATE_ENABLE config WEBGUIAPP_OTA_AUTOUPDATE_ENABLE
bool "Enabled OTA autoupdate firmware" bool "Enabled OTA autoupdate firmware"
default y default n
config WEBGUIAPP_OTA_RESET_ENABLE
bool "Enabled reset config on OTA update"
default n
config WEBGUIAPP_OTA_HOST config WEBGUIAPP_OTA_HOST
string "URL of firmware for OTA update" string "URL of firmware for OTA update"

View File

@ -100,6 +100,8 @@ void GetRFC3339Time(char *t);
void StartTimeGet(void); void StartTimeGet(void);
esp_err_t StartOTA(void); esp_err_t StartOTA(void);
char* GetAvailVersion();
char* GetUpdateStatus();
void StartSystemTimer(void); void StartSystemTimer(void);
uint32_t GetUpTime(void); uint32_t GetUpTime(void);

View File

@ -45,6 +45,7 @@
char SysName[32]; ///< User Name char SysName[32]; ///< User Name
char SysPass[32]; ///< User Password char SysPass[32]; ///< User Password
char OTAURL[64]; ///< OTA URL char OTAURL[64]; ///< OTA URL
int OTAAutoInt;
char SN[11]; ///< String of serial number (decimal ID) char SN[11]; ///< String of serial number (decimal ID)
char ID[9]; ///< String of ID ( last 4 bytes of MAC) char ID[9]; ///< String of ID ( last 4 bytes of MAC)
@ -52,10 +53,10 @@
struct struct
{ {
char bIsOTAEnabled :1; char bIsOTAEnabled :1;
char bIsResetOTAEnabled :1;
char bIsLedsEnabled :1; ///< Indication LEDs enable char bIsLedsEnabled :1; ///< Indication LEDs enable
char bIsLoRaConfirm :1; ///< Enable send back confirmation in LoRa channel char bIsLoRaConfirm :1; ///< Enable send back confirmation in LoRa channel
char bIsTCPConfirm :1; ///< Enable send back confirmation in TCP channel char bIsTCPConfirm :1; ///< Enable send back confirmation in TCP channel
char bit4 :1;
char bit5 :1; char bit5 :1;
char bit6 :1; char bit6 :1;
char bit7 :1; char bit7 :1;

View File

@ -105,26 +105,26 @@ static HTTP_IO_RESULT HTTPPostAdaptersSettings(httpd_req_t *req, char *PostData)
if (httpd_query_key_value(PostData, "ethen", tmp, sizeof(tmp)) == ESP_OK) if (httpd_query_key_value(PostData, "ethen", tmp, sizeof(tmp)) == ESP_OK)
{ {
if (!strcmp((const char*) tmp, (const char*) "1")) if (!strcmp((const char*) tmp, (const char*) "1"))
TempIsETHEnabled = true; TempIsETHEnabled = true;
} }
if (httpd_query_key_value(PostData, "dhcp", tmp, sizeof(tmp)) == ESP_OK) if (httpd_query_key_value(PostData, "dhcp", tmp, sizeof(tmp)) == ESP_OK)
{ {
if (!strcmp((const char*) tmp, (const char*) "1")) if (!strcmp((const char*) tmp, (const char*) "1"))
TempIsETHDHCPEnabled = true; TempIsETHDHCPEnabled = true;
} }
if (httpd_query_key_value(PostData, "ipa", tmp, 15) == ESP_OK) if (httpd_query_key_value(PostData, "ipa", tmp, 15) == ESP_OK)
esp_netif_str_to_ip4(tmp, (esp_ip4_addr_t*) &GetSysConf()->ethSettings.IPAddr); esp_netif_str_to_ip4(tmp, (esp_ip4_addr_t*) &GetSysConf()->ethSettings.IPAddr);
if (httpd_query_key_value(PostData, "mas", tmp, 15) == ESP_OK) if (httpd_query_key_value(PostData, "mas", tmp, 15) == ESP_OK)
esp_netif_str_to_ip4(tmp, (esp_ip4_addr_t*) &GetSysConf()->ethSettings.Mask); esp_netif_str_to_ip4(tmp, (esp_ip4_addr_t*) &GetSysConf()->ethSettings.Mask);
if (httpd_query_key_value(PostData, "gte", tmp, 15) == ESP_OK) if (httpd_query_key_value(PostData, "gte", tmp, 15) == ESP_OK)
esp_netif_str_to_ip4(tmp, (esp_ip4_addr_t*) &GetSysConf()->ethSettings.Gateway); esp_netif_str_to_ip4(tmp, (esp_ip4_addr_t*) &GetSysConf()->ethSettings.Gateway);
if (httpd_query_key_value(PostData, "dns1", tmp, 15) == ESP_OK) if (httpd_query_key_value(PostData, "dns1", tmp, 15) == ESP_OK)
esp_netif_str_to_ip4(tmp, (esp_ip4_addr_t*) &GetSysConf()->ethSettings.DNSAddr1); esp_netif_str_to_ip4(tmp, (esp_ip4_addr_t*) &GetSysConf()->ethSettings.DNSAddr1);
if (httpd_query_key_value(PostData, "dns2", tmp, 15) == ESP_OK) if (httpd_query_key_value(PostData, "dns2", tmp, 15) == ESP_OK)
esp_netif_str_to_ip4(tmp, (esp_ip4_addr_t*) &GetSysConf()->ethSettings.DNSAddr2); esp_netif_str_to_ip4(tmp, (esp_ip4_addr_t*) &GetSysConf()->ethSettings.DNSAddr2);
if (httpd_query_key_value(PostData, "dns3", tmp, 15) == ESP_OK) if (httpd_query_key_value(PostData, "dns3", tmp, 15) == ESP_OK)
esp_netif_str_to_ip4(tmp, (esp_ip4_addr_t*) &GetSysConf()->ethSettings.DNSAddr3); esp_netif_str_to_ip4(tmp, (esp_ip4_addr_t*) &GetSysConf()->ethSettings.DNSAddr3);
#endif #endif
@ -297,29 +297,29 @@ static HTTP_IO_RESULT HTTPPostServicesSettings(httpd_req_t *req, char *PostData)
#if CONFIG_WEBGUIAPP_MQTT_CLIENTS_NUM == 2 #if CONFIG_WEBGUIAPP_MQTT_CLIENTS_NUM == 2
httpd_query_key_value(PostData, "mqurl2", GetSysConf()->mqttStation[1].ServerAddr, httpd_query_key_value(PostData, "mqurl2", GetSysConf()->mqttStation[1].ServerAddr,
sizeof(GetSysConf()->mqttStation[1].ServerAddr)); sizeof(GetSysConf()->mqttStation[1].ServerAddr));
httpd_query_key_value(PostData, "mqid2", GetSysConf()->mqttStation[1].ClientID, httpd_query_key_value(PostData, "mqid2", GetSysConf()->mqttStation[1].ClientID,
sizeof(GetSysConf()->mqttStation[1].ClientID)); sizeof(GetSysConf()->mqttStation[1].ClientID));
httpd_query_key_value(PostData, "mqsys2", GetSysConf()->mqttStation[1].SystemName, httpd_query_key_value(PostData, "mqsys2", GetSysConf()->mqttStation[1].SystemName,
sizeof(GetSysConf()->mqttStation[1].SystemName)); sizeof(GetSysConf()->mqttStation[1].SystemName));
httpd_query_key_value(PostData, "mqgrp2", GetSysConf()->mqttStation[1].GroupName, httpd_query_key_value(PostData, "mqgrp2", GetSysConf()->mqttStation[1].GroupName,
sizeof(GetSysConf()->mqttStation[1].GroupName)); sizeof(GetSysConf()->mqttStation[1].GroupName));
httpd_query_key_value(PostData, "mqname2", GetSysConf()->mqttStation[1].UserName, httpd_query_key_value(PostData, "mqname2", GetSysConf()->mqttStation[1].UserName,
sizeof(GetSysConf()->mqttStation[1].UserName)); sizeof(GetSysConf()->mqttStation[1].UserName));
if (httpd_query_key_value(PostData, "mqen2", tmp, sizeof(tmp)) == ESP_OK) if (httpd_query_key_value(PostData, "mqen2", tmp, sizeof(tmp)) == ESP_OK)
{ {
if (!strcmp((const char*) tmp, (const char*) "1")) if (!strcmp((const char*) tmp, (const char*) "1"))
TempIsMQTT2Enabled = true; TempIsMQTT2Enabled = true;
} }
if (httpd_query_key_value(PostData, "mqport2", tmp, sizeof(tmp)) == ESP_OK) if (httpd_query_key_value(PostData, "mqport2", tmp, sizeof(tmp)) == ESP_OK)
if (httpd_query_key_value(PostData, "mqport2", tmp, sizeof(tmp)) == ESP_OK) if (httpd_query_key_value(PostData, "mqport2", tmp, sizeof(tmp)) == ESP_OK)
{ {
uint16_t tp = atoi((const char*) tmp); uint16_t tp = atoi((const char*) tmp);
if (tp < 65535 && tp >= 1000) if (tp < 65535 && tp >= 1000)
GetSysConf()->mqttStation[1].ServerPort = tp; GetSysConf()->mqttStation[1].ServerPort = tp;
} }
if (httpd_query_key_value(PostData, "mqpass2", tmp, sizeof(tmp)) == ESP_OK && if (httpd_query_key_value(PostData, "mqpass2", tmp, sizeof(tmp)) == ESP_OK &&
strcmp(tmp, (const char*) "******")) strcmp(tmp, (const char*) "******"))
@ -379,7 +379,7 @@ static HTTP_IO_RESULT HTTPPostSystemSettings(httpd_req_t *req, char *PostData)
{ {
char tmp[64]; char tmp[64];
bool TempIsOTAEnabled = false; bool TempIsOTAEnabled = false;
bool TempIsRstEnabled = false;
if (httpd_query_key_value(PostData, "nam", tmp, sizeof(tmp)) == ESP_OK) if (httpd_query_key_value(PostData, "nam", tmp, sizeof(tmp)) == ESP_OK)
{ {
UnencodeURL(tmp); UnencodeURL(tmp);
@ -400,6 +400,19 @@ static HTTP_IO_RESULT HTTPPostSystemSettings(httpd_req_t *req, char *PostData)
TempIsOTAEnabled = true; TempIsOTAEnabled = true;
} }
if (httpd_query_key_value(PostData, "otarst", tmp, sizeof(tmp)) == ESP_OK)
{
if (!strcmp((const char*) tmp, (const char*) "1"))
TempIsRstEnabled = true;
}
if (httpd_query_key_value(PostData, "otaint", tmp, sizeof(tmp)) == ESP_OK)
{
uint16_t tp = atoi((const char*) tmp);
if (tp < 65535 && tp >= 1)
GetSysConf()->OTAAutoInt = tp;
}
if (httpd_query_key_value(PostData, "otaurl", tmp, sizeof(tmp)) == ESP_OK) if (httpd_query_key_value(PostData, "otaurl", tmp, sizeof(tmp)) == ESP_OK)
{ {
UnencodeURL(tmp); UnencodeURL(tmp);
@ -430,6 +443,7 @@ static HTTP_IO_RESULT HTTPPostSystemSettings(httpd_req_t *req, char *PostData)
if (!strcmp(tmp, (const char*) "syst")) if (!strcmp(tmp, (const char*) "syst"))
{ {
GetSysConf()->Flags1.bIsOTAEnabled = TempIsOTAEnabled; GetSysConf()->Flags1.bIsOTAEnabled = TempIsOTAEnabled;
GetSysConf()->Flags1.bIsResetOTAEnabled = TempIsRstEnabled;
} }
if (httpd_query_key_value(PostData, "apply", tmp, 5) == ESP_OK) if (httpd_query_key_value(PostData, "apply", tmp, 5) == ESP_OK)
@ -450,7 +464,7 @@ static HTTP_IO_RESULT HTTPPostSystemSettings(httpd_req_t *req, char *PostData)
{ {
if (!strcmp(tmp, (const char*) "1")) if (!strcmp(tmp, (const char*) "1"))
{ {
WiFiScan(); WiFiScan();
return HTTP_IO_DONE_NOREFRESH; return HTTP_IO_DONE_NOREFRESH;
} }
else if (!strcmp(tmp, (const char*) "2")) else if (!strcmp(tmp, (const char*) "2"))

View File

@ -152,6 +152,15 @@ static void HTTPPrint_ota(char *VarData, void *arg)
{ {
PrintCheckbox(VarData, arg, GetSysConf()->Flags1.bIsOTAEnabled); PrintCheckbox(VarData, arg, GetSysConf()->Flags1.bIsOTAEnabled);
} }
static void HTTPPrint_otarst(char *VarData, void *arg)
{
PrintCheckbox(VarData, arg, GetSysConf()->Flags1.bIsResetOTAEnabled);
}
static void HTTPPrint_otaint(char *VarData, void *arg)
{
snprintf(VarData, MAX_DYNVAR_LENGTH, "%d", GetSysConf()->OTAAutoInt);
}
static void HTTPPrint_serial(char *VarData, void *arg) static void HTTPPrint_serial(char *VarData, void *arg)
{ {
@ -170,6 +179,18 @@ static void HTTPPrint_fver(char *VarData, void *arg)
snprintf(VarData, MAX_DYNVAR_LENGTH, "%s", cur_app_info.version); snprintf(VarData, MAX_DYNVAR_LENGTH, "%s", cur_app_info.version);
} }
} }
static void HTTPPrint_fverav(char *VarData, void *arg)
{
snprintf(VarData, MAX_DYNVAR_LENGTH, "%s", GetAvailVersion());
}
static void HTTPPrint_updstat(char *VarData, void *arg)
{
snprintf(VarData, MAX_DYNVAR_LENGTH, "%s", GetUpdateStatus());
}
static void HTTPPrint_idfver(char *VarData, void *arg) static void HTTPPrint_idfver(char *VarData, void *arg)
{ {
esp_app_desc_t cur_app_info; esp_app_desc_t cur_app_info;
@ -668,7 +689,13 @@ dyn_var_handler_t HANDLERS_ARRAY[] = {
{ "login", sizeof("login") - 1, &HTTPPrint_login }, { "login", sizeof("login") - 1, &HTTPPrint_login },
{ "pass", sizeof("pass") - 1, &HTTPPrint_pass }, { "pass", sizeof("pass") - 1, &HTTPPrint_pass },
{ "ota", sizeof("ota") - 1, &HTTPPrint_ota }, { "ota", sizeof("ota") - 1, &HTTPPrint_ota },
{ "otarst", sizeof("otarst") - 1, &HTTPPrint_otarst },
{ "otaint", sizeof("otaint") - 1, &HTTPPrint_otaint },
{ "fver", sizeof("fver") - 1, &HTTPPrint_fver }, { "fver", sizeof("fver") - 1, &HTTPPrint_fver },
{ "fverav", sizeof("fverav") - 1, &HTTPPrint_fverav },
{ "updstat", sizeof("updstat") - 1, &HTTPPrint_updstat },
{ "idfver", sizeof("idfver") - 1, &HTTPPrint_idfver }, { "idfver", sizeof("idfver") - 1, &HTTPPrint_idfver },
{ "builddate", sizeof("builddate") - 1, &HTTPPrint_builddate }, { "builddate", sizeof("builddate") - 1, &HTTPPrint_builddate },
{ "serial", sizeof("serial") - 1, &HTTPPrint_serial }, { "serial", sizeof("serial") - 1, &HTTPPrint_serial },

585
src/OTA.c
View File

@ -1,285 +1,300 @@
/* Copyright 2022 Bogdan Pilyugin /* Copyright 2022 Bogdan Pilyugin
* *
* Licensed under the Apache License, Version 2.0 (the "License"); * Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License. * you may not use this file except in compliance with the License.
* You may obtain a copy of the License at * You may obtain a copy of the License at
* *
* http://www.apache.org/licenses/LICENSE-2.0 * http://www.apache.org/licenses/LICENSE-2.0
* *
* Unless required by applicable law or agreed to in writing, software * Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, * distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
* *
* File name: OTA.c * File name: OTA.c
* Project: ChargePointMainboard * Project: ChargePointMainboard
* Created on: 2022-07-21 * Created on: 2022-07-21
* Author: Bogdan Pilyugin * Author: Bogdan Pilyugin
* Description: * Description:
*/ */
#include "freertos/FreeRTOS.h" #include "freertos/FreeRTOS.h"
#include "freertos/task.h" #include "freertos/task.h"
#include "esp_system.h" #include "esp_system.h"
#include "esp_event.h" #include "esp_event.h"
#include "esp_log.h" #include "esp_log.h"
#include "esp_ota_ops.h" #include "esp_ota_ops.h"
#include "esp_http_client.h" #include "esp_http_client.h"
#include "esp_https_ota.h" #include "esp_https_ota.h"
#include <string.h> #include <string.h>
#include "sdkconfig.h" #include "sdkconfig.h"
#include "romfs.h" #include "romfs.h"
#include <sys/socket.h> #include <sys/socket.h>
#include <WebGUIAppMain.h> #include <WebGUIAppMain.h>
#include "NetTransport.h" #include "NetTransport.h"
TaskHandle_t ota_task_handle; TaskHandle_t ota_task_handle;
static const char *TAG = "OTAmodule"; static const char *TAG = "OTAmodule";
extern const uint8_t server_cert_pem_start[] asm("_binary_ca_cert_pem_start"); extern const uint8_t server_cert_pem_start[] asm("_binary_ca_cert_pem_start");
extern const uint8_t server_cert_pem_end[] asm("_binary_ca_cert_pem_end"); extern const uint8_t server_cert_pem_end[] asm("_binary_ca_cert_pem_end");
#define HASH_LEN 32 char AvailFwVersion[32] = "Unknown";
//#define CONFIG_FIRMWARE_UPGRADE_URL "https://iotronic.cloud:443/firmware/MStation2.bin" char FwUpdStatus[32] = "Updated";
#define REPORT_PACKETS_EVERY 100
#define HASH_LEN 32
esp_err_t _http_event_handler(esp_http_client_event_t *evt) #define REPORT_PACKETS_EVERY 100
{
switch (evt->event_id) esp_err_t _http_event_handler(esp_http_client_event_t *evt)
{ {
case HTTP_EVENT_ERROR: switch (evt->event_id)
ESP_LOGD(TAG, "HTTP_EVENT_ERROR"); {
break; case HTTP_EVENT_ERROR:
case HTTP_EVENT_ON_CONNECTED: ESP_LOGD(TAG, "HTTP_EVENT_ERROR");
ESP_LOGD(TAG, "HTTP_EVENT_ON_CONNECTED"); break;
break; case HTTP_EVENT_ON_CONNECTED:
case HTTP_EVENT_HEADER_SENT: ESP_LOGD(TAG, "HTTP_EVENT_ON_CONNECTED");
ESP_LOGD(TAG, "HTTP_EVENT_HEADER_SENT"); break;
break; case HTTP_EVENT_HEADER_SENT:
case HTTP_EVENT_ON_HEADER: ESP_LOGD(TAG, "HTTP_EVENT_HEADER_SENT");
ESP_LOGD(TAG, "HTTP_EVENT_ON_HEADER, key=%s, value=%s", evt->header_key, evt->header_value); break;
break; case HTTP_EVENT_ON_HEADER:
case HTTP_EVENT_ON_DATA: ESP_LOGD(TAG, "HTTP_EVENT_ON_HEADER, key=%s, value=%s", evt->header_key, evt->header_value);
ESP_LOGD(TAG, "HTTP_EVENT_ON_DATA, len=%d", evt->data_len); break;
break; case HTTP_EVENT_ON_DATA:
case HTTP_EVENT_ON_FINISH: ESP_LOGD(TAG, "HTTP_EVENT_ON_DATA, len=%d", evt->data_len);
ESP_LOGD(TAG, "HTTP_EVENT_ON_FINISH"); break;
break; case HTTP_EVENT_ON_FINISH:
case HTTP_EVENT_DISCONNECTED: ESP_LOGD(TAG, "HTTP_EVENT_ON_FINISH");
ESP_LOGD(TAG, "HTTP_EVENT_DISCONNECTED"); break;
break; case HTTP_EVENT_DISCONNECTED:
} ESP_LOGD(TAG, "HTTP_EVENT_DISCONNECTED");
return ESP_OK; break;
} }
return ESP_OK;
static void print_sha256(const uint8_t *image_hash, const char *label) }
{
char hash_print[HASH_LEN * 2 + 1]; static void print_sha256(const uint8_t *image_hash, const char *label)
hash_print[HASH_LEN * 2] = 0; {
for (int i = 0; i < HASH_LEN; ++i) char hash_print[HASH_LEN * 2 + 1];
{ hash_print[HASH_LEN * 2] = 0;
sprintf(&hash_print[i * 2], "%02x", image_hash[i]); for (int i = 0; i < HASH_LEN; ++i)
} {
ESP_LOGI(TAG, "%s %s", label, hash_print); sprintf(&hash_print[i * 2], "%02x", image_hash[i]);
} }
ESP_LOGI(TAG, "%s %s", label, hash_print);
static int GetBuildNumber(char *version) }
{
char *p = version; static int GetBuildNumber(char *version)
int C = 0, P = 0; {
while (*(p++) != 0x00 && ++C < 32) char *p = version;
{ int C = 0, P = 0;
if (*p == '.') while (*(p++) != 0x00 && ++C < 32)
++P; {
if (P == 3) if (*p == '.')
return atoi(++p); ++P;
} if (P == 3)
return 0; return atoi(++p);
} }
return 0;
esp_err_t my_esp_https_ota(const esp_http_client_config_t *config) }
{
esp_app_desc_t cur_app_info; esp_err_t my_esp_https_ota(const esp_http_client_config_t *config)
esp_app_desc_t new_app_info; {
esp_app_desc_t cur_app_info;
if (esp_ota_get_partition_description(esp_ota_get_running_partition(), &cur_app_info) == ESP_OK) esp_app_desc_t new_app_info;
{
ESP_LOGI(TAG, "Current firmware"); if (esp_ota_get_partition_description(esp_ota_get_running_partition(), &cur_app_info) == ESP_OK)
ESP_LOGI(TAG, "********************************"); {
print_sha256(cur_app_info.app_elf_sha256, "SHA-256 for current firmware: "); ESP_LOGI(TAG, "Current firmware");
ESP_LOGI(TAG, "IDF ver %s", cur_app_info.idf_ver); ESP_LOGI(TAG, "********************************");
ESP_LOGI(TAG, "Version %s", cur_app_info.version); print_sha256(cur_app_info.app_elf_sha256, "SHA-256 for current firmware: ");
ESP_LOGI(TAG, "Build date %s", cur_app_info.date); ESP_LOGI(TAG, "IDF ver %s", cur_app_info.idf_ver);
ESP_LOGI(TAG, "Build time %s", cur_app_info.time); ESP_LOGI(TAG, "Version %s", cur_app_info.version);
ESP_LOGI(TAG, "********************************"); ESP_LOGI(TAG, "Build date %s", cur_app_info.date);
} ESP_LOGI(TAG, "Build time %s", cur_app_info.time);
else ESP_LOGI(TAG, "********************************");
return ESP_FAIL; }
else
if (!config) return ESP_FAIL;
{
ESP_LOGE(TAG, "esp_http_client config not found"); if (!config)
return ESP_ERR_INVALID_ARG; {
} ESP_LOGE(TAG, "esp_http_client config not found");
return ESP_ERR_INVALID_ARG;
esp_https_ota_config_t ota_config = { }
.http_config = config,
}; esp_https_ota_config_t ota_config = {
.http_config = config,
esp_https_ota_handle_t https_ota_handle = NULL; };
esp_err_t err = esp_https_ota_begin(&ota_config, &https_ota_handle);
if (https_ota_handle == NULL) esp_https_ota_handle_t https_ota_handle = NULL;
{ esp_err_t err = esp_https_ota_begin(&ota_config, &https_ota_handle);
return ESP_FAIL; if (https_ota_handle == NULL)
} {
return ESP_FAIL;
int size = esp_https_ota_get_image_size(https_ota_handle); }
if (size < 0)
{ int size = esp_https_ota_get_image_size(https_ota_handle);
return ESP_FAIL; if (size < 0)
} {
ESP_LOGI(TAG, "Image size %d bytes", size); return ESP_FAIL;
}
err = esp_https_ota_get_img_desc(https_ota_handle, &new_app_info); ESP_LOGI(TAG, "Image size %d bytes", size);
if (err != ESP_OK)
{ err = esp_https_ota_get_img_desc(https_ota_handle, &new_app_info);
return ESP_FAIL; if (err != ESP_OK)
} {
ESP_LOGI(TAG, "********************************"); return ESP_FAIL;
ESP_LOGI(TAG, "New firmware"); }
print_sha256(new_app_info.app_elf_sha256, "SHA-256 for new firmware: "); ESP_LOGI(TAG, "********************************");
ESP_LOGI(TAG, "IDF ver %s", new_app_info.idf_ver); ESP_LOGI(TAG, "New firmware");
ESP_LOGI(TAG, "Version %s", new_app_info.version); print_sha256(new_app_info.app_elf_sha256, "SHA-256 for new firmware: ");
ESP_LOGI(TAG, "Build date %s", new_app_info.date); ESP_LOGI(TAG, "IDF ver %s", new_app_info.idf_ver);
ESP_LOGI(TAG, "Build time %s", new_app_info.time); ESP_LOGI(TAG, "Version %s", new_app_info.version);
ESP_LOGI(TAG, "********************************"); ESP_LOGI(TAG, "Build date %s", new_app_info.date);
ESP_LOGI(TAG, "Build time %s", new_app_info.time);
//Here compare new and old firmware and make decision of update needed ESP_LOGI(TAG, "********************************");
ESP_LOGI(TAG, "Compare versions: current build is %d, update build is :%d",
GetBuildNumber(cur_app_info.version), //Here compare new and old firmware and make decision of update needed
GetBuildNumber(new_app_info.version)); strcpy(AvailFwVersion, new_app_info.version);
bool need_to_update = GetBuildNumber(new_app_info.version) > GetBuildNumber(cur_app_info.version); ESP_LOGI(TAG, "Compare versions: current build is %d, update build is :%d",
GetBuildNumber(cur_app_info.version),
if (need_to_update) GetBuildNumber(new_app_info.version));
{ bool need_to_update = GetBuildNumber(new_app_info.version) > GetBuildNumber(cur_app_info.version);
ESP_LOGW(TAG, "New firmware has newer build, START update firmware");
int countPackets = 0; if (need_to_update)
while (1) {
{ ESP_LOGW(TAG, "New firmware has newer build, START update firmware");
err = esp_https_ota_perform(https_ota_handle); int countPackets = 0;
if (err != ESP_ERR_HTTPS_OTA_IN_PROGRESS) while (1)
{ {
break; err = esp_https_ota_perform(https_ota_handle);
} if (err != ESP_ERR_HTTPS_OTA_IN_PROGRESS)
if (++countPackets >= REPORT_PACKETS_EVERY) {
{ break;
ESP_LOGI(TAG, "Updated %d bytes", esp_https_ota_get_image_len_read(https_ota_handle)); }
countPackets = 0; if (++countPackets >= REPORT_PACKETS_EVERY)
} {
} sprintf(FwUpdStatus, "Updated %d bytes", esp_https_ota_get_image_len_read(https_ota_handle));
ESP_LOGI(TAG, "%s", FwUpdStatus);
if (err != ESP_OK) countPackets = 0;
{ }
esp_https_ota_abort(https_ota_handle); }
return err;
} if (err != ESP_OK)
} {
else esp_https_ota_abort(https_ota_handle);
{ strcpy(FwUpdStatus,"Error update");
ESP_LOGI(TAG, "New firmware has NOT newer build, SKIP update firmware"); return err;
} }
}
esp_err_t ota_finish_err = esp_https_ota_finish(https_ota_handle); else
if (ota_finish_err != ESP_OK) {
{ ESP_LOGI(TAG, "New firmware has NOT newer build, SKIP update firmware");
return ota_finish_err; strcpy(FwUpdStatus,"Updated actual");
} }
if (need_to_update)
{ esp_err_t ota_finish_err = esp_https_ota_finish(https_ota_handle);
ESP_LOGI(TAG, "Firmware updated and now restarting..."); if (ota_finish_err != ESP_OK)
esp_restart(); {
} return ota_finish_err;
return ESP_OK; }
} if (need_to_update)
{
static void OTATask(void *pvParameter) ESP_LOGI(TAG, "Firmware updated and now restarting...");
{
esp_restart();
espfs_file_t *file; }
struct espfs_stat_t stat; return ESP_OK;
}
//open file
file = espfs_fopen(fs, "res/ca_cert.pem"); static void OTATask(void *pvParameter)
if (!file) {
{
ESP_LOGE(TAG, "Failed to read certificate file"); espfs_file_t *file;
goto update_error; struct espfs_stat_t stat;
}
//get file info //open file
espfs_stat(fs, "res/ca_cert.pem", &stat); file = espfs_fopen(fs, "res/ca_cert.pem");
uint32_t fileSize; if (!file)
fileSize = stat.size; {
char *certbuf = (char*) malloc(fileSize); ESP_LOGE(TAG, "Failed to read certificate file");
if (certbuf) goto update_error;
{ }
espfs_fread(file, certbuf, fileSize); //get file info
} espfs_stat(fs, "res/ca_cert.pem", &stat);
else uint32_t fileSize;
{ fileSize = stat.size;
ESP_LOGE(TAG, "Failed to allocate memory"); char *certbuf = (char*) malloc(fileSize);
espfs_fclose(file); if (certbuf)
goto update_error; {
} espfs_fread(file, certbuf, fileSize);
}
esp_http_client_config_t config = { else
.url = GetSysConf()->OTAURL, {
.cert_pem = (char*) certbuf, ESP_LOGE(TAG, "Failed to allocate memory");
.event_handler = _http_event_handler, espfs_fclose(file);
.keep_alive_enable = true, goto update_error;
.skip_cert_common_name_check = true, }
};
esp_http_client_config_t config = {
#ifdef CONFIG_EXAMPLE_SKIP_COMMON_NAME_CHECK .url = GetSysConf()->OTAURL,
config.skip_cert_common_name_check = true; .cert_pem = (char*) certbuf,
#endif .event_handler = _http_event_handler,
esp_err_t ret = my_esp_https_ota(&config); .keep_alive_enable = true,
if (ret == ESP_OK) .skip_cert_common_name_check = true,
{ };
ESP_LOGI(TAG, "Firmware upgrade completed");
} #ifdef CONFIG_EXAMPLE_SKIP_COMMON_NAME_CHECK
else config.skip_cert_common_name_check = true;
{ #endif
ESP_LOGE(TAG, "Firmware upgrade failed"); esp_err_t ret = my_esp_https_ota(&config);
} if (ret == ESP_OK)
free(certbuf); {
espfs_fclose(file); ESP_LOGI(TAG, "Firmware upgrade completed");
update_error: }
else
{
vTaskDelete(NULL); ESP_LOGE(TAG, "Firmware upgrade failed");
} }
free(certbuf);
/** espfs_fclose(file);
* @file update_error:
* @brief Start OTA update task
*
* @pre Network is ready vTaskDelete(NULL);
* @post None }
* @return ESP_OK on success
* ESP_ERR_NOT_FINISHED on attempt rerun existing thread /**
*/ * @file
* @brief Start OTA update task
esp_err_t StartOTA(void) *
{ * @pre Network is ready
if (xTaskGetHandle("OTATask") != NULL) * @post None
{ * @return ESP_OK on success
ESP_LOGW(TAG, "OTA task is already running"); * ESP_ERR_NOT_FINISHED on attempt rerun existing thread
return ESP_ERR_NOT_FINISHED; */
}
ESP_LOGI(TAG, "Starting OTA Task"); esp_err_t StartOTA(void)
xTaskCreate(OTATask, "OTATask", 1024 * 8, (void*) 0, 3, NULL); {
return ESP_OK; if (xTaskGetHandle("OTATask") != NULL)
} {
ESP_LOGW(TAG, "OTA task is already running");
return ESP_ERR_NOT_FINISHED;
}
ESP_LOGI(TAG, "Starting OTA Task");
xTaskCreate(OTATask, "OTATask", 1024 * 8, (void*) 0, 3, NULL);
return ESP_OK;
}
char* GetAvailVersion()
{
return AvailFwVersion;
}
char* GetUpdateStatus()
{
return FwUpdStatus;
}

View File

@ -271,6 +271,19 @@ static void ResetSysConfig(SYS_CONFIG *Conf)
sizeof(CONFIG_WEBGUIAPP_USERPASS)); sizeof(CONFIG_WEBGUIAPP_USERPASS));
memcpy(Conf->OTAURL, CONFIG_WEBGUIAPP_OTA_HOST, sizeof(CONFIG_WEBGUIAPP_OTA_HOST)); memcpy(Conf->OTAURL, CONFIG_WEBGUIAPP_OTA_HOST, sizeof(CONFIG_WEBGUIAPP_OTA_HOST));
Conf->OTAAutoInt = CONFIG_WEBGUIAPP_OTA_AUTOUPDATE_PERIOD;
#if CONFIG_WEBGUIAPP_OTA_AUTOUPDATE_ENABLE
Conf->Flags1.bIsOTAEnabled = true;
#else
Conf->Flags1.bIsOTAEnabled = false;
#endif
#if CONFIG_WEBGUIAPP_OTA_RESET_ENABLE
Conf->Flags1.bIsResetOTAEnabled = true;
#else
Conf->Flags1.bIsResetOTAEnabled = false;
#endif
#if CONFIG_WEBGUIAPP_WIFI_ENABLE #if CONFIG_WEBGUIAPP_WIFI_ENABLE
Conf->wifiSettings.Flags1.bIsWiFiEnabled = CONFIG_WEBGUIAPP_WIFI_ON; Conf->wifiSettings.Flags1.bIsWiFiEnabled = CONFIG_WEBGUIAPP_WIFI_ON;