Programmation de l’ESP32 par le Wifi

L’ESP32 est un microcontrôleur très intéressant, car il regroupe des entrées sorties analogiques et numériques ainsi qu’un accès WIFI et Bluetooth. Une fois mis en place pour une application donnée, il peut être nécessaire de modifier son programme. Mais s’il se trouve éloigné ou inaccessible de votre PC servant à la programmation, il est possible de le modifier en passant par le Wifi. Cette technique est appelée OTA (Over The Air).

Choix de la carte ESP32

Il existe de nombreuses cartes sur le marché à base d’ESP32. Cela peut-être difficile parfois de trouver la définition des broches de sorties (GPIO). Ici on utilise une carte de développement AZ-Delivery avec un ESP32-Wroom et 2×19 broches. Achat possible chez Amazon.

IDE Arduino

La programmation de la carte se fait à l’aide de l’outil de développement IDE d’Arduino. Il faut dans les préférences faire appel au gestionnaire de carte de « Espressif » qui développe l’ESP32. Allez dans Fichier / Préférences et mettez l’adresse : https://dl.espressif.com/dl/package_esp32_index.json

Dans le gestionnaire de cartes, choisissez la votre. Dans notre cas ce sera « ESP 32 Dev Module ».

Basic OTA

Dans les exemples, sélectionnez le programme « Basic OTA ».

On va légèrement modifier le programme proposé pour imposer une adresse IP à l’ESP32.

#include <WiFi.h>
#include <ESPmDNS.h>
#include <WiFiUdp.h>
#include <ArduinoOTA.h>

const char* ssid = "YOUR SSID";
const char* password = "THE PASSWORD";

// Set your Static IP address
IPAddress local_IP(192, 168, 0, 208); //HERE DEFINE YOUR IP ADRESS
// Set your Gateway IP address
IPAddress gateway(192, 168, 0, 254);  //DEFINE THE GATEWAY

IPAddress subnet(255, 255, 255, 0);
IPAddress primaryDNS(8, 8, 8, 8);   //optional
IPAddress secondaryDNS(8, 8, 4, 4); //optional


void setup() {
  Serial.begin(115200);
  Serial.println("Booting");

  
 // Configures static IP address
  if (!WiFi.config(local_IP, gateway, subnet, primaryDNS, secondaryDNS)) {
    Serial.println("STA Failed to configure");
  }
  WiFi.begin(ssid, password);
  while (WiFi.waitForConnectResult() != WL_CONNECTED) {
    Serial.println("Connection Failed! Rebooting...");
    delay(5000);
    ESP.restart();
  }


  ArduinoOTA
    .onStart([]() {
      String type;
      if (ArduinoOTA.getCommand() == U_FLASH)
        type = "sketch";
      else // U_SPIFFS
        type = "filesystem";

      // NOTE: if updating SPIFFS this would be the place to unmount SPIFFS using SPIFFS.end()
      Serial.println("Start updating " + type);
    })
    .onEnd([]() {
      Serial.println("\nEnd");
    })
    .onProgress([](unsigned int progress, unsigned int total) {
      Serial.printf("Progress: %u%%\r", (progress / (total / 100)));
    })
    .onError([](ota_error_t error) {
      Serial.printf("Error[%u]: ", error);
      if (error == OTA_AUTH_ERROR) Serial.println("Auth Failed");
      else if (error == OTA_BEGIN_ERROR) Serial.println("Begin Failed");
      else if (error == OTA_CONNECT_ERROR) Serial.println("Connect Failed");
      else if (error == OTA_RECEIVE_ERROR) Serial.println("Receive Failed");
      else if (error == OTA_END_ERROR) Serial.println("End Failed");
    });

  ArduinoOTA.begin();

  Serial.println("Ready");
  Serial.print("IP address: ");
  Serial.println(WiFi.localIP());
}

void loop() {
  ArduinoOTA.handle();
}

Adaptez le code, « SSID du WIFI, Password et adresse IP.
Téléchargez ce code par la liaison série. Sur le moniteur, vous retrouverez l’adresse IP prise en compte. Un appui sur le bouton RST permet de bien tester l’ensemble. À ce stade, il vous sera possible de mettre à jour la programmation via le web en choisissant non plus le port série dans l’Ide Arduino, mais le port réseau, dans notre cas 192.168.0.208. Dans votre code, il faudra intégrer la partie ArduinoOTA afin de conserver cette possibilité.

Exemple avec « Debug »

En passant par le Wifi vous allez perdre la possibilité de debug par le port série. La biblothèque « RemoteDebug » va nous permettre de retrouver cette possibilité par une écoute Telnet sur le port 23. A titre d’exemple, on va faire un petit serveur web sur le port 80.

#include <WiFi.h>
#include <ESPmDNS.h>
#include <WiFiUdp.h>
#include <WiFiClient.h>
#include <WebServer.h>
#include <ArduinoOTA.h>
#include <RemoteDebug.h>

const char* ssid = "MyWIFI";
const char* password = "12345678";
RemoteDebug Debug;
unsigned long previousMillis;


// Set your Static IP address
IPAddress local_IP(192, 168, 0, 208);
// Set your Gateway IP address
IPAddress gateway(192, 168, 0, 254);

IPAddress subnet(255, 255, 255, 0);
IPAddress primaryDNS(8, 8, 8, 8);   //optional
IPAddress secondaryDNS(8, 8, 4, 4); //optional

WebServer server(80);
  

void handleRoot() {
  Debug.println(F("Client Web"));
  server.send(200, "text/plain", "Hello Client");
 
}

void handleNotFound() {
 Debug.println(F("File Not Found"));
  String message = "File Not Found\n\n";
  message += "URI: ";
  message += server.uri();
  message += "\nMethod: ";
  message += (server.method() == HTTP_GET) ? "GET" : "POST";
  message += "\nArguments: ";
  message += server.args();
  message += "\n";
  for (uint8_t i = 0; i < server.args(); i++) {
    message += " " + server.argName(i) + ": " + server.arg(i) + "\n";
  }
  server.send(404, "text/plain", message);
}

void setup() {
 // Configures static IP address
  if (!WiFi.config(local_IP, gateway, subnet, primaryDNS, secondaryDNS)) {
    Debug.println("STA Failed to configure");
  }

 WiFi.begin(ssid, password);
 while (WiFi.waitForConnectResult() != WL_CONNECTED) {
   Debug.println("Connection Failed! Rebooting...");
   delay(5000);
   ESP.restart();
 }
 // init remote debug
 Debug.begin("ESP32");  
 
 initOTA();
 Debug.println("Ready");
 Debug.print("IP address: ");
 Debug.println(WiFi.localIP());

server.on("/", handleRoot);

  server.on("/inline", []() {
    server.send(200, "text/plain", "this works as well");
  });

  server.onNotFound(handleNotFound);

  server.begin();
  Debug.println("HTTP server started");
 
}
void loop() {
 ArduinoOTA.handle();
 Debug.handle();
 server.handleClient();
 if (millis() - previousMillis >= 5000) {
   previousMillis = millis();
   Debug.println(F("Code has been update"));
 }
}
void initOTA() {
 // Port defaults to 3232
 // ArduinoOTA.setPort(3232);
 // Hostname defaults to esp3232-[MAC]
 ArduinoOTA.setHostname("ESP32");
 // No authentication by default
 // ArduinoOTA.setPassword("admin");
 // Password can be set with it's md5 value as well
 // MD5(admin) = 21232f297a57a5a743894a0e4a801fc3
 // ArduinoOTA.setPasswordHash("21232f297a57a5a743894a0e4a801fc3");
 ArduinoOTA
 .onStart([]() {
   String type;
   if (ArduinoOTA.getCommand() == U_FLASH)
     type = "sketch";
   else // U_SPIFFS
     type = "filesystem";
   // NOTE: if updating SPIFFS this would be the place to unmount SPIFFS using SPIFFS.end()
   Debug.println("Start updating " + type);
 })
 .onEnd([]() {
   Debug.println("\nEnd");
 })
 .onProgress([](unsigned int progress, unsigned int total) {
   Debug.printf("Progress: %u%%\r", (progress / (total / 100)));
 })
 .onError([](ota_error_t error) {
   Debug.printf("Error[%u]: ", error);
   if (error == OTA_AUTH_ERROR) Debug.println("Auth Failed");
   else if (error == OTA_BEGIN_ERROR) Debug.println("Begin Failed");
   else if (error == OTA_CONNECT_ERROR) Debug.println("Connect Failed");
   else if (error == OTA_RECEIVE_ERROR) Debug.println("Receive Failed");
   else if (error == OTA_END_ERROR) Debug.println("End Failed");
 });
 ArduinoOTA.begin();
}

Cette fois-ci, téléchargez le code via le réseau Wifi. En parallèle, ouvrez une session Telnet avec un programme comme Putty. Rentrez l’adresse IP de l’ESP32 et le port 23. Ouvrez votre navigateur web, et rentrez l’adresse IP de l’ESP.

Vous pouvez à présent vous inspirer de cette exemple pour votre application à mettre à jour via le Wifi.

Bugs IDE Arduino

En attendant des corrections, l’IDE Arduino a 2 désagréments :
– il demande un mot de passe pour télécharger en mode OTA bien que la programmation n’en impose pas. Il suffit de rentrer une lettre quelconque.
– parfois en fin de téléchargement la flèche reste orange. Il faut relancer l’IDE pour télécharger à nouveau.

5 réflexions sur « Programmation de l’ESP32 par le Wifi »

  1. Bonjour,
    A quoi correspond la ligne: IPAddress gateway(192, 168, 0, 254) par rapport a IPAddress local_IP(192, 168, 0, 208) qui est l’adresse local.
    Ou trouver ou comment déterminer IPAddress gateway.
    D’avance merci.

    1. Gateway, c’est la passerelle qui vous permet d’accéder au monde extérieur. En pratique c’est l’adresse IP de votre box internet sur le réseau interne à la maison. 192.168. et se termine souvent en 0.1 ou 0.254 ou 1.0 ou 1.254.

  2. Bonjour,
    Je viens de tester l’OTA.
    Avant chaque téléversement, il me demande un MP? Dans le doute j’ai saisie celui du MD5(admin) et cela fonctionne mais je ne comprends pas pourquoi vu que dans le sketch il est en commentaire?
    A la fin du téléchargement, l’IDE ne le détecte pas et l’animation de téléchargement continue. le bouton « téléverser » reste en jaune. Je dois fermer Arduino IDE pour pouvoir refaire un téléchargement!
    Vous avez une idée de la portée du WiFi?
    Prendre un ESP avec antenne externe est vraiment un plus?
    Merci d’avance pour vos réponses.

    1. Ce sont les petits désagréments de l’IDE d’Arduino.
      Pour le mot de passe, mettez n’importe quoi. Une lettre suffit.
      Pour le téléverser en jaune, je peste aussi. Mais certains jours cela marche. Je n’ai pas encore compris pourquoi.

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *