Added ability to set OTA password from within sketch

Adds second form of homeSpan.enableOTA(const char *pwd, boolean safeLoad=true)
This commit is contained in:
Gregg 2023-02-11 07:49:16 -06:00
parent 8114798cae
commit 22bd16e936
3 changed files with 50 additions and 36 deletions

View File

@ -40,14 +40,12 @@ void HAPClient::init(){
nvs_open("SRP",NVS_READWRITE,&srpNVS); // open SRP data namespace in NVS
nvs_open("HAP",NVS_READWRITE,&hapNVS); // open HAP data namespace in NVS
if(!nvs_get_str(homeSpan.otaNVS,"OTADATA",NULL,&len)){ // if found OTA data in NVS
nvs_get_str(homeSpan.otaNVS,"OTADATA",homeSpan.spanOTA.otaPwd,&len); // retrieve data
} else {
MD5Builder otaPwdHash;
otaPwdHash.begin();
otaPwdHash.add(DEFAULT_OTA_PASSWORD);
otaPwdHash.calculate();
otaPwdHash.getChars(homeSpan.spanOTA.otaPwd);
if(strlen(homeSpan.spanOTA.otaPwd)==0){ // OTA password has not been specified in sketch
if(!nvs_get_str(homeSpan.otaNVS,"OTADATA",NULL,&len)){ // if found OTA data in NVS...
nvs_get_str(homeSpan.otaNVS,"OTADATA",homeSpan.spanOTA.otaPwd,&len); // ...retrieve data.
} else { // otherwise...
homeSpan.spanOTA.setPassword(DEFAULT_OTA_PASSWORD); // ...use default password
}
}
if(strlen(homeSpan.pairingCodeCommand)){ // load verification setup code if provided

View File

@ -519,25 +519,20 @@ void Span::checkConnect(){
mdns_service_txt_item_set("_hap","_tcp","sh",setupHash); // Step 4: broadcast the resulting Setup Hash
if(spanOTA.enabled){
if(esp_ota_get_running_partition()!=esp_ota_get_next_update_partition(NULL)){
ArduinoOTA.setHostname(hostName);
ArduinoOTA.setHostname(hostName);
if(spanOTA.auth)
ArduinoOTA.setPasswordHash(spanOTA.otaPwd);
if(spanOTA.auth)
ArduinoOTA.setPasswordHash(spanOTA.otaPwd);
ArduinoOTA.onStart(spanOTA.start).onEnd(spanOTA.end).onProgress(spanOTA.progress).onError(spanOTA.error);
ArduinoOTA.onStart(spanOTA.start).onEnd(spanOTA.end).onProgress(spanOTA.progress).onError(spanOTA.error);
ArduinoOTA.begin();
Serial.print("Starting OTA Server: ");
Serial.print(displayName);
Serial.print(" at ");
Serial.print(WiFi.localIP());
Serial.print("\nAuthorization Password: ");
Serial.print(spanOTA.auth?"Enabled\n\n":"DISABLED!\n\n");
} else {
Serial.print("\n*** WARNING: Can't start OTA Server - Partition table used to compile this sketch is not configured for OTA.\n\n");
spanOTA.enabled=false;
}
ArduinoOTA.begin();
Serial.print("Starting OTA Server: ");
Serial.print(displayName);
Serial.print(" at ");
Serial.print(WiFi.localIP());
Serial.print("\nAuthorization Password: ");
Serial.print(spanOTA.auth?"Enabled\n\n":"DISABLED!\n\n");
}
mdns_service_txt_item_set("_hap","_tcp","ota",spanOTA.enabled?"yes":"no"); // OTA status (info only - NOT used by HAP)
@ -683,12 +678,7 @@ void Span::processSerialCommand(const char *c){
Serial.print(mask(textPwd,2));
Serial.print("\n");
MD5Builder otaPwdHash;
otaPwdHash.begin();
otaPwdHash.add(textPwd);
otaPwdHash.calculate();
otaPwdHash.getChars(spanOTA.otaPwd);
spanOTA.setPassword(textPwd);
nvs_set_str(otaNVS,"OTADATA",spanOTA.otaPwd); // update data
nvs_commit(otaNVS);
@ -2147,11 +2137,35 @@ void SpanWebLog::vLog(boolean sysMsg, const char *fmt, va_list ap){
// SpanOTA //
///////////////////////////////
void SpanOTA::init(boolean _auth, boolean _safeLoad){
int SpanOTA::init(boolean _auth, boolean _safeLoad, const char *pwd){
if(esp_ota_get_running_partition()==esp_ota_get_next_update_partition(NULL)){
Serial.print("\n*** WARNING: Can't start OTA Server - Partition table used to compile this sketch is not configured for OTA.\n\n");
return(-1);
}
enabled=true;
safeLoad=_safeLoad;
auth=_auth;
homeSpan.reserveSocketConnections(1);
if(pwd==NULL)
return(0);
return(setPassword(pwd));
}
///////////////////////////////
int SpanOTA::setPassword(const char *pwd){
if(strlen(pwd)<1 || strlen(pwd)>32){
Serial.printf("\n*** WARNING: Cannot change OTA password to '%s'. Password length must be between 1 and 32 characters.\n\n",pwd);
return(-1);
}
MD5Builder otaPwdHash;
otaPwdHash.begin();
otaPwdHash.add(pwd);
otaPwdHash.calculate();
otaPwdHash.getChars(homeSpan.spanOTA.otaPwd);
return(0);
}
///////////////////////////////

View File

@ -168,14 +168,15 @@ struct SpanWebLog{ // optional web status/log data
struct SpanOTA{ // manages OTA process
char otaPwd[33]; // MD5 Hash of OTA password, represented as a string of hexidecimal characters
char otaPwd[33]=""; // MD5 Hash of OTA password, represented as a string of hexidecimal characters
static boolean enabled; // enables OTA - default if not enabled
static boolean auth; // indicates whether OTA password is required
static int otaPercent;
static boolean safeLoad; // indicates whether OTA update should reject any application update that is not another HomeSpan sketch
void init(boolean auth, boolean safeLoad);
int init(boolean auth, boolean safeLoad, const char *pwd);
int setPassword(const char *pwd);
static void start();
static void end();
static void progress(uint32_t progress, uint32_t total);
@ -326,7 +327,8 @@ class Span{
void setPairingCode(const char *s){sprintf(pairingCodeCommand,"S %9s",s);} // sets the Pairing Code - use is NOT recommended. Use 'S' from CLI instead
void deleteStoredValues(){processSerialCommand("V");} // deletes stored Characteristic values from NVS
void enableOTA(boolean auth=true, boolean safeLoad=true){spanOTA.init(auth, safeLoad);} // enables Over-the-Air updates, with (auth=true) or without (auth=false) authorization password
int enableOTA(boolean auth=true, boolean safeLoad=true){return(spanOTA.init(auth, safeLoad, NULL));} // enables Over-the-Air updates, with (auth=true) or without (auth=false) authorization password
int enableOTA(const char *pwd, boolean safeLoad=true){return(spanOTA.init(true, safeLoad, pwd));} // enables Over-the-Air updates, with custom authorization password (overrides any password stored with the 'O' command)
void enableWebLog(uint16_t maxEntries=0, const char *serv=NULL, const char *tz="UTC", const char *url=DEFAULT_WEBLOG_URL){ // enable Web Logging
webLog.init(maxEntries, serv, tz, url);