Skip to content

Commit b55215c

Browse files
feat(hosted): Implement OTA for esp-hosted co-processors (#12065)
* feat(hosted): Implement OTA for esp-hosted co-processors * feat(hosted): Add library to CMakeLists.txt * feat(hosted): Limit CI to run the example only on P4 * feat(hosted): Document inline the source code * feat(hosted): Add library to code owners * ci(pre-commit): Apply automatic fixes --------- Co-authored-by: pre-commit-ci-lite[bot] <117423508+pre-commit-ci-lite[bot]@users.noreply.github.com>
1 parent e7df08a commit b55215c

File tree

9 files changed

+326
-12
lines changed

9 files changed

+326
-12
lines changed

.github/CODEOWNERS

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@
5454
/libraries/ArduinoOTA/ @me-no-dev
5555
/libraries/AsyncUDP/ @me-no-dev
5656
/libraries/BLE/ @lucasssvaz @SuGlider
57+
/libraries/ESP_HostedOTA/ @me-no-dev
5758
/libraries/ESP_I2S/ @me-no-dev
5859
/libraries/ESP_NOW/ @P-R-O-C-H-Y @lucasssvaz
5960
/libraries/ESP_SR/ @me-no-dev

CMakeLists.txt

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -90,6 +90,7 @@ set(ARDUINO_ALL_LIBRARIES
9090
ESP_I2S
9191
ESP_NOW
9292
ESP_SR
93+
ESP_HostedOTA
9394
ESPmDNS
9495
Ethernet
9596
FFat
@@ -146,6 +147,9 @@ set(ARDUINO_LIBRARY_ESP_SR_SRCS
146147
libraries/ESP_SR/src/ESP_SR.cpp
147148
libraries/ESP_SR/src/esp32-hal-sr.c)
148149

150+
set(ARDUINO_LIBRARY_ESP_HostedOTA_SRCS
151+
libraries/ESP_HostedOTA/src/ESP_HostedOTA.cpp)
152+
149153
set(ARDUINO_LIBRARY_ESPmDNS_SRCS libraries/ESPmDNS/src/ESPmDNS.cpp)
150154

151155
set(ARDUINO_LIBRARY_Ethernet_SRCS libraries/Ethernet/src/ETH.cpp)

cores/esp32/esp32-hal-hosted.c

Lines changed: 58 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@
1717

1818
#include "esp32-hal-hosted.h"
1919
#include "esp32-hal-log.h"
20+
#include "esp32-hal.h"
2021
#include "pins_arduino.h"
2122

2223
#include "esp_hosted.h"
@@ -53,6 +54,9 @@ static esp_hosted_coprocessor_fwver_t host_version_struct = {
5354
.major1 = ESP_HOSTED_VERSION_MAJOR_1, .minor1 = ESP_HOSTED_VERSION_MINOR_1, .patch1 = ESP_HOSTED_VERSION_PATCH_1
5455
};
5556

57+
static bool hostedInit();
58+
static bool hostedDeinit();
59+
5660
void hostedGetHostVersion(uint32_t *major, uint32_t *minor, uint32_t *patch) {
5761
*major = host_version_struct.major1;
5862
*minor = host_version_struct.minor1;
@@ -66,6 +70,11 @@ void hostedGetSlaveVersion(uint32_t *major, uint32_t *minor, uint32_t *patch) {
6670
}
6771

6872
bool hostedHasUpdate() {
73+
if (!hosted_initialized) {
74+
log_e("ESP-Hosted is not initialized");
75+
return false;
76+
}
77+
6978
uint32_t host_version = ESP_HOSTED_VERSION_VAL(host_version_struct.major1, host_version_struct.minor1, host_version_struct.patch1);
7079
uint32_t slave_version = 0;
7180

@@ -106,6 +115,11 @@ char *hostedGetUpdateURL() {
106115
}
107116

108117
bool hostedBeginUpdate() {
118+
if (!hosted_initialized) {
119+
log_e("ESP-Hosted is not initialized");
120+
return false;
121+
}
122+
109123
esp_err_t err = esp_hosted_slave_ota_begin();
110124
if (err != ESP_OK) {
111125
log_e("Failed to begin Update: %s", esp_err_to_name(err));
@@ -114,6 +128,11 @@ bool hostedBeginUpdate() {
114128
}
115129

116130
bool hostedWriteUpdate(uint8_t *buf, uint32_t len) {
131+
if (!hosted_initialized) {
132+
log_e("ESP-Hosted is not initialized");
133+
return false;
134+
}
135+
117136
esp_err_t err = esp_hosted_slave_ota_write(buf, len);
118137
if (err != ESP_OK) {
119138
log_e("Failed to write Update: %s", esp_err_to_name(err));
@@ -122,6 +141,11 @@ bool hostedWriteUpdate(uint8_t *buf, uint32_t len) {
122141
}
123142

124143
bool hostedEndUpdate() {
144+
if (!hosted_initialized) {
145+
log_e("ESP-Hosted is not initialized");
146+
return false;
147+
}
148+
125149
esp_err_t err = esp_hosted_slave_ota_end();
126150
if (err != ESP_OK) {
127151
log_e("Failed to end Update: %s", esp_err_to_name(err));
@@ -130,16 +154,31 @@ bool hostedEndUpdate() {
130154
}
131155

132156
bool hostedActivateUpdate() {
157+
if (!hosted_initialized) {
158+
log_e("ESP-Hosted is not initialized");
159+
return false;
160+
}
161+
162+
// Activate can fail on older firmwares and that is not critical
163+
uint32_t slave_version = ESP_HOSTED_VERSION_VAL(slave_version_struct.major1, slave_version_struct.minor1, slave_version_struct.patch1);
164+
uint32_t min_version = ESP_HOSTED_VERSION_VAL(2, 6, 0);
165+
166+
if (slave_version < min_version) {
167+
// Silence messages caused by earlier versions
168+
esp_log_level_set("rpc_core", ESP_LOG_NONE);
169+
}
170+
133171
esp_err_t err = esp_hosted_slave_ota_activate();
134-
if (err != ESP_OK) {
172+
173+
// Any further communication will result in logged errors
174+
esp_log_level_set("sdmmc_io", ESP_LOG_NONE);
175+
esp_log_level_set("H_SDIO_DRV", ESP_LOG_NONE);
176+
177+
if (err != ESP_OK && slave_version >= min_version) {
135178
log_e("Failed to activate Update: %s", esp_err_to_name(err));
179+
return false;
136180
}
137-
// else {
138-
// hostedDeinit();
139-
// delay(1000);
140-
// hostedInit();
141-
// }
142-
return err == ESP_OK;
181+
return true;
143182
}
144183

145184
static bool hostedInit() {
@@ -158,15 +197,22 @@ static bool hostedInit() {
158197
conf.pin_d2.pin = sdio_pin_config.pin_d2;
159198
conf.pin_d3.pin = sdio_pin_config.pin_d3;
160199
conf.pin_reset.pin = sdio_pin_config.pin_reset;
161-
// esp_hosted_sdio_set_config() will fail on second attempt but here temporarily to not cause exception on reinit
162-
if (esp_hosted_sdio_set_config(&conf) != ESP_OK || esp_hosted_init() != ESP_OK) {
163-
log_e("esp_hosted_init failed!");
200+
esp_err_t err = esp_hosted_sdio_set_config(&conf);
201+
if (err != ESP_OK) { //&& err != ESP_ERR_NOT_ALLOWED) { // uncomment when second init is fixed
202+
log_e("esp_hosted_sdio_set_config failed: %s", esp_err_to_name(err));
203+
return false;
204+
}
205+
err = esp_hosted_init();
206+
if (err != ESP_OK) {
207+
log_e("esp_hosted_init failed: %s", esp_err_to_name(err));
164208
hosted_initialized = false;
165209
return false;
166210
}
167211
log_i("ESP-Hosted initialized!");
168-
if (esp_hosted_connect_to_slave() != ESP_OK) {
169-
log_e("Failed to connect to slave");
212+
err = esp_hosted_connect_to_slave();
213+
if (err != ESP_OK) {
214+
log_e("esp_hosted_connect_to_slave failed: %s", esp_err_to_name(err));
215+
hosted_initialized = false;
170216
return false;
171217
}
172218
hostedHasUpdate();
Lines changed: 66 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,66 @@
1+
/*
2+
* ESP-Hosted OTA Update Example
3+
*
4+
* This example demonstrates how to update the ESP-Hosted co-processor firmware
5+
* over-the-air (OTA). The ESP-Hosted solution allows an ESP32 to act as a WiFi
6+
* co-processor for other microcontrollers.
7+
*
8+
* Prerequisites:
9+
* - ESP32 with ESP-Hosted firmware configured as WiFi co-processor
10+
* - Network connectivity to download firmware updates
11+
* - Valid WiFi credentials
12+
*/
13+
14+
#include "WiFi.h" // WiFi library for network connectivity
15+
#include "ESP_HostedOTA.h" // ESP-Hosted OTA update functionality
16+
17+
// WiFi network credentials - CHANGE THESE TO YOUR NETWORK SETTINGS
18+
const char *ssid = "your-ssid"; // Replace with your WiFi network name
19+
const char *password = "your-password"; // Replace with your WiFi password
20+
21+
void setup() {
22+
// Step 1: Initialize serial communication for debugging output
23+
Serial.begin(115200);
24+
25+
// Step 2: Initialize the ESP-Hosted WiFi station mode
26+
// This prepares the ESP-Hosted co-processor for WiFi operations
27+
WiFi.STA.begin();
28+
29+
// Step 3: Display connection attempt information
30+
Serial.println();
31+
Serial.println("******************************************************");
32+
Serial.print("Connecting to ");
33+
Serial.println(ssid);
34+
35+
// Step 4: Attempt to connect to the specified WiFi network
36+
WiFi.STA.connect(ssid, password);
37+
38+
// Step 5: Wait for WiFi connection to be established
39+
// Display progress dots while connecting
40+
while (WiFi.STA.status() != WL_CONNECTED) {
41+
delay(500); // Wait 500ms between connection attempts
42+
Serial.print("."); // Show connection progress
43+
}
44+
Serial.println();
45+
46+
// Step 6: Display successful connection information
47+
Serial.println("WiFi connected");
48+
Serial.print("IP address: ");
49+
Serial.println(WiFi.STA.localIP());
50+
51+
// Step 7: Attempt to update the ESP-Hosted co-processor firmware
52+
// This function will:
53+
// - Check if ESP-Hosted is initialized
54+
// - Verify if an update is available
55+
// - Download and install the firmware update if needed
56+
if (updateEspHostedSlave()) {
57+
// Step 8: Restart the host ESP32 after successful update
58+
// This is currently required to properly activate the new firmware
59+
// on the ESP-Hosted co-processor
60+
ESP.restart();
61+
}
62+
}
63+
64+
void loop() {
65+
delay(1000);
66+
}
Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
requires:
2+
- CONFIG_ESP_WIFI_REMOTE_ENABLED=y
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
#######################################
2+
# Syntax Coloring Map For ESP_HostedOTA
3+
#######################################
4+
5+
#######################################
6+
# Datatypes (KEYWORD1)
7+
#######################################
8+
9+
#######################################
10+
# Methods and Functions (KEYWORD2)
11+
#######################################
12+
13+
updateEspHostedSlave KEYWORD2
14+
15+
#######################################
16+
# Constants (LITERAL1)
17+
#######################################
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
name=ESP_HostedOTA
2+
version=3.3.4
3+
author=me-no-dev
4+
maintainer=me-no-dev
5+
sentence=Library for updating the ESP-Hosted co-processor
6+
paragraph=Supports ESP32 Arduino platforms.
7+
category=Communication
8+
url=https://github.com/espressif/arduino-esp32/
9+
architectures=esp32

0 commit comments

Comments
 (0)