Resume of OTA update

Stoimen
Posts: 1
Joined: Wed Mar 22, 2023 8:54 am

Resume of OTA update

Postby Stoimen » Wed Mar 22, 2023 9:38 am

Hello everybody,

I'm working on specific feature related to OTA updates using “esp_http_client” & “esp_ota_ops” libraries.

The use cases are the following:

1.Resuming of OTA update in case the connection was previously interrupted for some reason.
2.Resuming of OTA update after unexpected software reset ( for this we use NV parameter to store the number of bytes
downloaded so far. It’s used as an offset after the reset )

I managed to get the resume working for both use cases, however, it was necessary to modify some functions in “esp_ota_ops.c" to achieve resume of OTA update for use case #2.

Find below the modifications and the main reasons:

The first issue that I noticed was the following:

After unexpected software reset, we want to resume the update from where we were interrupted before. We won't to erase the sectors have been written before.
We pass the offset value (number of bytes downloaded so far and written to the corresponding partition ) to esp_ota_begin function as a second parameter. However, esp_ota_begin() is implemented to erase the bytes written before the reset as you can see in below the highlighted code line:

if (image_size != OTA_WITH_SEQUENTIAL_WRITES) {
// If input image size is 0 or OTA_SIZE_UNKNOWN, erase entire partition
if ((image_size == 0) || (image_size == OTA_SIZE_UNKNOWN)) {
ret = esp_partition_erase_range(partition, 0, partition->size);
} else {
const int aligned_erase_size = (image_size + SPI_FLASH_SEC_SIZE - 1) & ~(SPI_FLASH_SEC_SIZE - 1);
ret = esp_partition_erase_range(partition, 0, aligned_erase_size);
}
if (ret != ESP_OK) {
return ret;
}
}
the second argument of the function esp_partition_erase_range() is offset, I put there our offset value instead of "0" and managed to get it working completely with this fix. NOTE: I use esp_ota_write_with_offset() to finish OTA process completely.

The second issue that I noticed was the following:

If we call esp_ota_begin() with OTA_WITH_SEQUENTIAL_WRITES (as we usually want), there is a "need_erase" flag which is set.
After calling esp_ota_write_offset() with the corresponding offset ( the number of bytes downloaded so far ) it's getting failed, because inside of this function there is "assert(it->need_erase == 0 && "must erase the partition before writing to it")" if I comment out(disable) this assert the OTA passes completely.

What is your point of view about these points ? Is it really a bug that needs to be reported, or there is another way to achieve Resume of OTA update after unexpected software reset ?

Thanks for the attention.

Kind regards.

ESP_Sprite
Posts: 8921
Joined: Thu Nov 26, 2015 4:08 am

Re: Resume of OTA update

Postby ESP_Sprite » Thu Mar 23, 2023 3:43 am

With a requirement as specific as this, it may be better to roll your own OTA partition write procedure... you can get the partition an OTA would be written to using esp_ota_get_next_update_partition(), then use the SPI flash partition API to do the erase/writes in any way you want, and finally you can activate it using esp_ota_set_boot_partition() when the OTA is fully written.

Who is online

Users browsing this forum: Bing [Bot] and 103 guests