Fixed bug in setPairingCode() and added second "internal" argument
homeSpan.setPairingCode() operates silently if called from within a sketch, but will report error to Serial Monitor and HALT sketch if code is invalid. Otherwise, if called from 'S', or from AP, or as default during start-up, diagnostics are printed as usual and sketch will NOT halt if invalid code is provided
This commit is contained in:
parent
c17fabe326
commit
0d404ccf1b
17
src/HAP.cpp
17
src/HAP.cpp
|
|
@ -38,9 +38,6 @@ void HAPClient::init(){
|
|||
|
||||
size_t len; // not used but required to read blobs from NVS
|
||||
|
||||
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(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.
|
||||
|
|
@ -49,9 +46,6 @@ void HAPClient::init(){
|
|||
}
|
||||
}
|
||||
|
||||
if(nvs_get_blob(srpNVS,"VERIFYDATA",NULL,&len)) // if Pair-Setup verification code data not found in NVS
|
||||
homeSpan.setPairingCode(DEFAULT_SETUP_CODE); // create and save verification from using Pairing Setup Code
|
||||
|
||||
if(!strlen(homeSpan.qrID)){ // if Setup ID has not been specified in sketch
|
||||
if(!nvs_get_str(hapNVS,"SETUPID",NULL,&len)){ // check for saved value
|
||||
nvs_get_str(hapNVS,"SETUPID",homeSpan.qrID,&len); // retrieve data
|
||||
|
|
@ -60,6 +54,9 @@ void HAPClient::init(){
|
|||
}
|
||||
}
|
||||
|
||||
if(nvs_get_blob(homeSpan.srpNVS,"VERIFYDATA",NULL,&len)) // if Pair-Setup verification code data not found in NVS
|
||||
homeSpan.setPairingCode(DEFAULT_SETUP_CODE,false); // create and save verification from default Pairing Setup Code
|
||||
|
||||
if(!nvs_get_blob(hapNVS,"ACCESSORY",NULL,&len)){ // if found long-term Accessory data in NVS
|
||||
nvs_get_blob(hapNVS,"ACCESSORY",&accessory,&len); // retrieve data
|
||||
} else {
|
||||
|
|
@ -316,6 +313,8 @@ int HAPClient::unauthorizedError(){
|
|||
|
||||
int HAPClient::postPairSetupURL(uint8_t *content, size_t len){
|
||||
|
||||
static SRP6A *srp=NULL; // must persist across multiple calls to postPairSetupURL
|
||||
|
||||
HAPTLV iosTLV;
|
||||
HAPTLV responseTLV;
|
||||
HAPTLV subTLV;
|
||||
|
|
@ -378,7 +377,7 @@ int HAPClient::postPairSetupURL(uint8_t *content, size_t len){
|
|||
|
||||
TempBuffer<Verification> verifyData; // retrieve verification data (should already be stored in NVS)
|
||||
size_t len=verifyData.len();
|
||||
nvs_get_blob(srpNVS,"VERIFYDATA",verifyData,&len);
|
||||
nvs_get_blob(homeSpan.srpNVS,"VERIFYDATA",verifyData,&len);
|
||||
|
||||
responseTLV.add(kTLVType_Salt,16,verifyData.get()->salt); // write Salt from verification data into TLV
|
||||
|
||||
|
|
@ -542,6 +541,7 @@ int HAPClient::postPairSetupURL(uint8_t *content, size_t len){
|
|||
tlvRespond(responseTLV); // send response to client
|
||||
|
||||
delete srp; // delete SRP - no longer needed once pairing is completed
|
||||
srp=NULL; // reset to NULL
|
||||
|
||||
mdns_service_txt_item_set("_hap","_tcp","sf","0"); // broadcast new status
|
||||
|
||||
|
|
@ -1691,11 +1691,10 @@ void HapOut::HapStreamBuffer::printFormatted(char *buf, size_t nChars, size_t ns
|
|||
// instantiate all static HAP Client structures and data
|
||||
|
||||
nvs_handle HAPClient::hapNVS;
|
||||
nvs_handle HAPClient::srpNVS;
|
||||
HKDF HAPClient::hkdf;
|
||||
pairState HAPClient::pairStatus;
|
||||
Accessory HAPClient::accessory;
|
||||
list<Controller, Mallocator<Controller>> HAPClient::controllerList;
|
||||
SRP6A *HAPClient::srp=NULL;
|
||||
//SRP6A *HAPClient::srp=NULL;
|
||||
int HAPClient::conNum;
|
||||
|
||||
|
|
|
|||
|
|
@ -106,10 +106,9 @@ struct HAPClient {
|
|||
static const int MAX_ACCESSORIES=150; // maximum number of allowed Accessories (HAP limit=150)
|
||||
|
||||
static nvs_handle hapNVS; // handle for non-volatile-storage of HAP data
|
||||
static nvs_handle srpNVS; // handle for non-volatile-storage of SRP data
|
||||
static HKDF hkdf; // generates (and stores) HKDF-SHA-512 32-byte keys derived from an inputKey of arbitrary length, a salt string, and an info string
|
||||
static pairState pairStatus; // tracks pair-setup status
|
||||
static SRP6A *srp; // stores all SRP-6A keys used for Pair-Setup (must persist through multiple calls to Pair-Setup)
|
||||
// static SRP6A *srp; // stores all SRP-6A keys used for Pair-Setup (must persist through multiple calls to Pair-Setup)
|
||||
static Accessory accessory; // Accessory ID and Ed25519 public and secret keys- permanently stored
|
||||
static list<Controller, Mallocator<Controller>> controllerList; // linked-list of Paired Controller IDs and ED25519 long-term public keys - permanently stored
|
||||
static int conNum; // connection number - used to keep track of per-connection EV notifications
|
||||
|
|
|
|||
|
|
@ -45,15 +45,35 @@ const __attribute__((section(".rodata_custom_desc"))) SpanPartition spanPartitio
|
|||
|
||||
using namespace Utils;
|
||||
|
||||
HapOut hapOut; // Specialized output stream that can both print to serial monitor and encrypt/transmit to HAP Clients with minimal memory usage (global-scope)
|
||||
HapOut hapOut; // Specialized output stream that can both print to serial monitor and encrypt/transmit to HAP Clients with minimal memory usage (global-scoped variable)
|
||||
HAPClient **hap; // HAP Client structure containing HTTP client connections, parsing routines, and state variables (global-scoped variable)
|
||||
Span homeSpan; // HAP Attributes database and all related control functions for this Accessory (global-scoped variable)
|
||||
HapCharacteristics hapChars; // Instantiation of all HAP Characteristics (used to create SpanCharacteristics)
|
||||
HapCharacteristics hapChars; // Instantiation of all HAP Characteristics used to create SpanCharacteristics (global-scoped variable)
|
||||
|
||||
///////////////////////////////
|
||||
// Span //
|
||||
///////////////////////////////
|
||||
|
||||
Span::Span(){
|
||||
|
||||
nvs_flash_init(); // initialize non-volatile-storage partition in flash
|
||||
|
||||
nvs_open("CHAR",NVS_READWRITE,&charNVS); // open Characteristic data namespace in NVS
|
||||
nvs_open("WIFI",NVS_READWRITE,&wifiNVS); // open WIFI data namespace in NVS
|
||||
nvs_open("OTA",NVS_READWRITE,&otaNVS); // open OTA data namespace in NVS
|
||||
|
||||
nvs_open("SRP",NVS_READWRITE,&srpNVS); // open SRP data namespace in NVS
|
||||
nvs_open("HAP",NVS_READWRITE,&HAPClient::hapNVS); // open HAP data namespace in NVS
|
||||
|
||||
nvs_get_u8(wifiNVS,"REBOOTS",&rebootCount);
|
||||
rebootCount++;
|
||||
nvs_set_u8(wifiNVS,"REBOOTS",rebootCount);
|
||||
nvs_commit(wifiNVS);
|
||||
|
||||
}
|
||||
|
||||
///////////////////////////////
|
||||
|
||||
void Span::begin(Category catID, const char *displayName, const char *hostNameBase, const char *modelName){
|
||||
|
||||
loopTaskHandle=xTaskGetCurrentTaskHandle(); // a roundabout way of getting the current task handle
|
||||
|
|
@ -78,16 +98,6 @@ void Span::begin(Category catID, const char *displayName, const char *hostNameBa
|
|||
|
||||
hapServer=new WiFiServer(tcpPortNum);
|
||||
|
||||
nvs_flash_init(); // initialize non-volatile-storage partition in flash
|
||||
nvs_open("CHAR",NVS_READWRITE,&charNVS); // open Characteristic data namespace in NVS
|
||||
nvs_open("WIFI",NVS_READWRITE,&wifiNVS); // open WIFI data namespace in NVS
|
||||
nvs_open("OTA",NVS_READWRITE,&otaNVS); // open OTA data namespace in NVS
|
||||
|
||||
nvs_get_u8(wifiNVS,"REBOOTS",&rebootCount);
|
||||
rebootCount++;
|
||||
nvs_set_u8(wifiNVS,"REBOOTS",rebootCount);
|
||||
nvs_commit(wifiNVS);
|
||||
|
||||
size_t len;
|
||||
|
||||
if(strlen(network.wifiData.ssid)){ // if setWifiCredentials was already called
|
||||
|
|
@ -677,7 +687,7 @@ void Span::processSerialCommand(const char *c){
|
|||
|
||||
case 'S': {
|
||||
|
||||
setPairingCode(c+1);
|
||||
setPairingCode(c+1,false);
|
||||
}
|
||||
break;
|
||||
|
||||
|
|
@ -736,13 +746,10 @@ void Span::processSerialCommand(const char *c){
|
|||
nvs_set_blob(wifiNVS,"WIFIDATA",&network.wifiData,sizeof(network.wifiData)); // update data
|
||||
nvs_commit(wifiNVS); // commit to NVS
|
||||
LOG0("\n*** Credentials saved!\n");
|
||||
if(strlen(network.setupCode)){
|
||||
char s[10];
|
||||
sprintf(s,"S%s",network.setupCode);
|
||||
processSerialCommand(s);
|
||||
} else {
|
||||
if(strlen(network.setupCode))
|
||||
setPairingCode(network.setupCode,false);
|
||||
else
|
||||
LOG0("*** Setup Code Unchanged\n");
|
||||
}
|
||||
|
||||
LOG0("\n*** Restarting...\n\n");
|
||||
STATUS_UPDATE(start(LED_ALERT),HS_AP_TERMINATED)
|
||||
|
|
@ -1204,33 +1211,42 @@ const char* Span::statusString(HS_STATUS s){
|
|||
|
||||
///////////////////////////////
|
||||
|
||||
Span& Span::setPairingCode(const char *s){
|
||||
Span& Span::setPairingCode(const char *s, boolean progCall){
|
||||
|
||||
char setupCode[10];
|
||||
|
||||
sscanf(s," %9[0-9]",setupCode);
|
||||
|
||||
if(strlen(setupCode)!=8){
|
||||
LOG0("\n*** Invalid request to change Setup Code. Code must be exactly 8 digits.\n\n");
|
||||
LOG0("\n*** Invalid request to change Setup Code to '%s'. Code must be exactly 8 digits.\n\n",s);
|
||||
if(progCall){
|
||||
LOG0("=== PROGRAM HALTED ===");
|
||||
while(1);
|
||||
}
|
||||
return(*this);
|
||||
}
|
||||
|
||||
if(!network.allowedCode(setupCode)){
|
||||
LOG0("\n*** Invalid request to change Setup Code. Code too simple.\n\n");
|
||||
LOG0("\n*** Invalid request to change Setup Code to '%s'. Code too simple.\n\n",s);
|
||||
if(progCall){
|
||||
LOG0("=== PROGRAM HALTED ===");
|
||||
while(1);
|
||||
}
|
||||
return(*this);
|
||||
}
|
||||
|
||||
TempBuffer<Verification> verifyData; // temporary storage for verification data
|
||||
SRP6A *srp=new SRP6A; // create temporary instance of SRP
|
||||
|
||||
LOG0("\nGenerating SRP verification data for new Setup Code: %.3s-%.2s-%.3s ... ",setupCode,setupCode+3,setupCode+5);
|
||||
if(!progCall)
|
||||
LOG0("\nGenerating new SRP verification data for Setup Code: %.3s-%.2s-%.3s ... ",setupCode,setupCode+3,setupCode+5);
|
||||
|
||||
srp->createVerifyCode(setupCode,verifyData); // create random salt and compute verification code from specified Setup Code
|
||||
nvs_set_blob(HAPClient::srpNVS,"VERIFYDATA",verifyData,verifyData.len()); // update data
|
||||
nvs_commit(HAPClient::srpNVS); // commit to NVS
|
||||
srp->createVerifyCode(setupCode,verifyData); // create random salt and compute verification code from specified Setup Code
|
||||
nvs_set_blob(srpNVS,"VERIFYDATA",verifyData,verifyData.len()); // update data
|
||||
nvs_commit(srpNVS); // commit to NVS
|
||||
|
||||
LOG0("New Code Saved!\n");
|
||||
LOG0("Setup Payload for Optional QR Code: %s\n\n",qrCode.get(atoi(setupCode),qrID,atoi(category)));
|
||||
if(!progCall)
|
||||
LOG0("New Code Saved!\nSetup Payload for Optional QR Code: %s\n\n",qrCode.get(atoi(setupCode),qrID,atoi(category)));
|
||||
|
||||
delete srp;
|
||||
return(*this);
|
||||
|
|
|
|||
|
|
@ -215,9 +215,6 @@ class Span{
|
|||
boolean isBridge=true; // flag indicating whether device is configured as a bridge (i.e. first Accessory contains nothing but AccessoryInformation and HAPProtocolInformation)
|
||||
HapQR qrCode; // optional QR Code to use for pairing
|
||||
const char *sketchVersion="n/a"; // version of the sketch
|
||||
nvs_handle charNVS; // handle for non-volatile-storage of Characteristics data
|
||||
nvs_handle wifiNVS=0; // handle for non-volatile-storage of WiFi data
|
||||
nvs_handle otaNVS; // handle for non-volatile storage of OTA data
|
||||
char pairingCodeCommand[12]=""; // user-specified Pairing Code - only needed if Pairing Setup Code is specified in sketch using setPairingCode()
|
||||
String lastClientIP="0.0.0.0"; // IP address of last client accessing device through encrypted channel
|
||||
boolean newCode; // flag indicating new application code has been loaded (based on keeping track of app SHA256)
|
||||
|
|
@ -225,6 +222,11 @@ class Span{
|
|||
uint8_t rebootCount=0; // counts number of times device was rebooted (used in optional Reboot callback)
|
||||
uint32_t rebootCallbackTime; // length of time to wait (in milliseconds) before calling optional Reboot callback
|
||||
|
||||
nvs_handle charNVS; // handle for non-volatile-storage of Characteristics data
|
||||
nvs_handle wifiNVS=0; // handle for non-volatile-storage of WiFi data
|
||||
nvs_handle otaNVS; // handle for non-volatile storage of OTA data
|
||||
nvs_handle srpNVS; // handle for non-volatile storage of SRP data
|
||||
|
||||
int connected=0; // WiFi connection status (increments upon each connect and disconnect)
|
||||
unsigned long waitTime=60000; // time to wait (in milliseconds) between WiFi connection attempts
|
||||
unsigned long alarmConnect=0; // time after which WiFi connection attempt should be tried again
|
||||
|
|
@ -291,6 +293,8 @@ class Span{
|
|||
|
||||
public:
|
||||
|
||||
Span(); // constructor
|
||||
|
||||
void begin(Category catID=DEFAULT_CATEGORY,
|
||||
const char *displayName=DEFAULT_DISPLAY_NAME,
|
||||
const char *hostNameBase=DEFAULT_HOST_NAME,
|
||||
|
|
@ -342,7 +346,7 @@ class Span{
|
|||
Span& setWifiCredentials(const char *ssid, const char *pwd); // sets WiFi Credentials
|
||||
Span& setStatusCallback(void (*f)(HS_STATUS status)){statusCallback=f;return(*this);} // sets an optional user-defined function to call when HomeSpan status changes
|
||||
const char* statusString(HS_STATUS s); // returns char string for HomeSpan status change messages
|
||||
Span& setPairingCode(const char *s); // sets the Pairing Code - use is NOT recommended. Use 'S' from CLI instead
|
||||
Span& setPairingCode(const char *s, boolean progCall=true); // sets the Pairing Code - use is NOT recommended. Use 'S' from CLI instead
|
||||
void deleteStoredValues(){processSerialCommand("V");} // deletes stored Characteristic values from NVS
|
||||
|
||||
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
|
||||
|
|
|
|||
|
|
@ -27,7 +27,7 @@
|
|||
|
||||
#include "HomeSpan.h"
|
||||
|
||||
#define MAX_LIGHTS 2
|
||||
#define MAX_LIGHTS 1
|
||||
|
||||
void setup() {
|
||||
|
||||
|
|
@ -35,6 +35,7 @@ void setup() {
|
|||
|
||||
homeSpan.setLogLevel(2);
|
||||
homeSpan.enableWebLog(50,"pool.ntp.org","UTC",NULL);
|
||||
homeSpan.setPairingCode("12345670");
|
||||
// homeSpan.enableWebLog(50,"pool.ntp.org","UTC","myStatus");
|
||||
// homeSpan.enableWebLog(50,NULL,NULL,NULL);
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue