Skip to content

Commit 8800fe5

Browse files
committed
Merge branch 'bugfix/prov_retry_failures' into 'master'
ci: Add retries for all provisioning methods, some refactors See merge request espressif/esp-idf!9343
2 parents 84833bf + 002a13a commit 8800fe5

File tree

11 files changed

+110
-112
lines changed

11 files changed

+110
-112
lines changed

examples/provisioning/legacy/ble_prov/ble_prov_test.py

Lines changed: 1 addition & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,6 @@
1717
from __future__ import print_function
1818
import re
1919
import os
20-
import time
2120

2221
import ttfw_idf
2322
import esp_prov
@@ -82,19 +81,7 @@ def test_examples_provisioning_ble(env, extra_data):
8281
if not esp_prov.apply_wifi_config(transport, security):
8382
raise RuntimeError("Failed to send apply config")
8483

85-
success = False
86-
while True:
87-
time.sleep(5)
88-
print("Wi-Fi connection state")
89-
ret = esp_prov.get_wifi_config(transport, security)
90-
if (ret == 1):
91-
continue
92-
elif (ret == 0):
93-
print("Provisioning was successful")
94-
success = True
95-
break
96-
97-
if not success:
84+
if not esp_prov.wait_wifi_connected(transport, security):
9885
raise RuntimeError("Provisioning failed")
9986

10087

examples/provisioning/legacy/ble_prov/main/app_prov.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -248,8 +248,8 @@ static void app_prov_event_handler(void* handler_arg, esp_event_base_t event_bas
248248
/* If none of the expected reasons,
249249
* retry connecting to host SSID */
250250
g_prov->wifi_state = WIFI_PROV_STA_CONNECTING;
251-
esp_wifi_connect();
252251
}
252+
esp_wifi_connect();
253253
}
254254
}
255255

examples/provisioning/legacy/console_prov/main/app_prov.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -186,8 +186,8 @@ static void app_prov_event_handler(void* handler_arg, esp_event_base_t event_bas
186186
/* If none of the expected reasons,
187187
* retry connecting to host SSID */
188188
g_prov->wifi_state = WIFI_PROV_STA_CONNECTING;
189-
esp_wifi_connect();
190189
}
190+
esp_wifi_connect();
191191
}
192192
}
193193

examples/provisioning/legacy/custom_config/main/app_prov.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -211,8 +211,8 @@ static void app_prov_event_handler(void* handler_arg, esp_event_base_t event_bas
211211
/* If none of the expected reasons,
212212
* retry connecting to host SSID */
213213
g_prov->wifi_state = WIFI_PROV_STA_CONNECTING;
214-
esp_wifi_connect();
215214
}
215+
esp_wifi_connect();
216216
}
217217
}
218218

examples/provisioning/legacy/softap_prov/main/app_prov.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -197,8 +197,8 @@ static void app_prov_event_handler(void* handler_arg, esp_event_base_t event_bas
197197
/* If none of the expected reasons,
198198
* retry connecting to host SSID */
199199
g_prov->wifi_state = WIFI_PROV_STA_CONNECTING;
200-
esp_wifi_connect();
201200
}
201+
esp_wifi_connect();
202202
}
203203
}
204204

examples/provisioning/legacy/softap_prov/softap_prov_test.py

Lines changed: 49 additions & 59 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,6 @@
1717
from __future__ import print_function
1818
import re
1919
import os
20-
import time
2120

2221
import ttfw_idf
2322
import esp_prov
@@ -52,64 +51,55 @@ def test_examples_provisioning_softap(env, extra_data):
5251
print("SoftAP SSID : " + ssid)
5352
print("SoftAP Password : " + password)
5453

55-
ctrl = wifi_tools.wpa_cli(iface, reset_on_exit=True)
56-
print("Connecting to DUT SoftAP...")
57-
ip = ctrl.connect(ssid, password)
58-
got_ip = dut1.expect(re.compile(r"DHCP server assigned IP to a station, IP is: (\d+.\d+.\d+.\d+)"), timeout=45)[0]
59-
if ip != got_ip:
60-
raise RuntimeError("SoftAP connected to another host! " + ip + "!=" + got_ip)
61-
print("Connected to DUT SoftAP")
62-
63-
print("Starting Provisioning")
64-
verbose = False
65-
protover = "V0.1"
66-
secver = 1
67-
pop = "abcd1234"
68-
provmode = "softap"
69-
ap_ssid = "myssid"
70-
ap_password = "mypassword"
71-
softap_endpoint = ip.split('.')[0] + "." + ip.split('.')[1] + "." + ip.split('.')[2] + ".1:80"
72-
73-
print("Getting security")
74-
security = esp_prov.get_security(secver, pop, verbose)
75-
if security is None:
76-
raise RuntimeError("Failed to get security")
77-
78-
print("Getting transport")
79-
transport = esp_prov.get_transport(provmode, softap_endpoint)
80-
if transport is None:
81-
raise RuntimeError("Failed to get transport")
82-
83-
print("Verifying protocol version")
84-
if not esp_prov.version_match(transport, protover):
85-
raise RuntimeError("Mismatch in protocol version")
86-
87-
print("Starting Session")
88-
if not esp_prov.establish_session(transport, security):
89-
raise RuntimeError("Failed to start session")
90-
91-
print("Sending Wifi credential to DUT")
92-
if not esp_prov.send_wifi_config(transport, security, ap_ssid, ap_password):
93-
raise RuntimeError("Failed to send Wi-Fi config")
94-
95-
print("Applying config")
96-
if not esp_prov.apply_wifi_config(transport, security):
97-
raise RuntimeError("Failed to send apply config")
98-
99-
success = False
100-
while True:
101-
time.sleep(5)
102-
print("Wi-Fi connection state")
103-
ret = esp_prov.get_wifi_config(transport, security)
104-
if (ret == 1):
105-
continue
106-
elif (ret == 0):
107-
print("Provisioning was successful")
108-
success = True
109-
break
110-
111-
if not success:
112-
raise RuntimeError("Provisioning failed")
54+
try:
55+
ctrl = wifi_tools.wpa_cli(iface, reset_on_exit=True)
56+
print("Connecting to DUT SoftAP...")
57+
ip = ctrl.connect(ssid, password)
58+
got_ip = dut1.expect(re.compile(r"DHCP server assigned IP to a station, IP is: (\d+.\d+.\d+.\d+)"), timeout=60)[0]
59+
if ip != got_ip:
60+
raise RuntimeError("SoftAP connected to another host! " + ip + "!=" + got_ip)
61+
print("Connected to DUT SoftAP")
62+
63+
print("Starting Provisioning")
64+
verbose = False
65+
protover = "V0.1"
66+
secver = 1
67+
pop = "abcd1234"
68+
provmode = "softap"
69+
ap_ssid = "myssid"
70+
ap_password = "mypassword"
71+
softap_endpoint = ip.split('.')[0] + "." + ip.split('.')[1] + "." + ip.split('.')[2] + ".1:80"
72+
73+
print("Getting security")
74+
security = esp_prov.get_security(secver, pop, verbose)
75+
if security is None:
76+
raise RuntimeError("Failed to get security")
77+
78+
print("Getting transport")
79+
transport = esp_prov.get_transport(provmode, softap_endpoint)
80+
if transport is None:
81+
raise RuntimeError("Failed to get transport")
82+
83+
print("Verifying protocol version")
84+
if not esp_prov.version_match(transport, protover):
85+
raise RuntimeError("Mismatch in protocol version")
86+
87+
print("Starting Session")
88+
if not esp_prov.establish_session(transport, security):
89+
raise RuntimeError("Failed to start session")
90+
91+
print("Sending Wifi credential to DUT")
92+
if not esp_prov.send_wifi_config(transport, security, ap_ssid, ap_password):
93+
raise RuntimeError("Failed to send Wi-Fi config")
94+
95+
print("Applying config")
96+
if not esp_prov.apply_wifi_config(transport, security):
97+
raise RuntimeError("Failed to send apply config")
98+
99+
if not esp_prov.wait_wifi_connected(transport, security):
100+
raise RuntimeError("Provisioning failed")
101+
finally:
102+
ctrl.reset()
113103

114104

115105
if __name__ == '__main__':

examples/provisioning/wifi_prov_mgr/wifi_prov_mgr_test.py

Lines changed: 1 addition & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,6 @@
1717
from __future__ import print_function
1818
import re
1919
import os
20-
import time
2120

2221
import ttfw_idf
2322
import esp_prov
@@ -90,24 +89,7 @@ def test_examples_wifi_prov_mgr(env, extra_data):
9089
if not esp_prov.apply_wifi_config(transport, security):
9190
raise RuntimeError("Failed to send apply config")
9291

93-
success = False
94-
retry = 0
95-
while True:
96-
time.sleep(5)
97-
print("Wi-Fi connection state")
98-
ret = esp_prov.get_wifi_config(transport, security)
99-
if (ret == 1):
100-
continue
101-
elif (ret == 0):
102-
print("Provisioning was successful")
103-
success = True
104-
elif (ret == 3 and retry < 3):
105-
retry = retry + 1
106-
print("Connection failed.. retry again...: ", ret)
107-
continue
108-
break
109-
110-
if not success:
92+
if not esp_prov.wait_wifi_connected(transport, security):
11193
raise RuntimeError("Provisioning failed")
11294

11395
# Check if BTDM memory is released after provisioning finishes

tools/ci/python_packages/wifi_tools.py

Lines changed: 20 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -51,16 +51,26 @@ def __init__(self, iface, reset_on_exit=False):
5151
iface_path = service.GetInterface(self.iface_name)
5252
self.iface_obj = bus.get_object("fi.w1.wpa_supplicant1", iface_path)
5353
self.iface_ifc = dbus.Interface(self.iface_obj, "fi.w1.wpa_supplicant1.Interface")
54+
self.iface_props = dbus.Interface(self.iface_obj, 'org.freedesktop.DBus.Properties')
5455
if self.iface_ifc is None:
5556
raise RuntimeError('supplicant : Failed to fetch interface')
5657

57-
self.old_network = self.iface_obj.Get("fi.w1.wpa_supplicant1.Interface", "CurrentNetwork",
58-
dbus_interface='org.freedesktop.DBus.Properties')
58+
self.old_network = self._get_iface_property("CurrentNetwork")
59+
print("Old network is %s" % self.old_network)
60+
5961
if self.old_network == '/':
6062
self.old_network = None
6163
else:
6264
self.connected = True
6365

66+
def _get_iface_property(self, name):
67+
""" Read the property with 'name' from the wi-fi interface object
68+
69+
Note: The result is a dbus wrapped type, so should usually convert it to the corresponding native
70+
Python type
71+
"""
72+
return self.iface_props.Get("fi.w1.wpa_supplicant1.Interface", name)
73+
6474
def connect(self, ssid, password):
6575
if self.connected is True:
6676
self.iface_ifc.Disconnect()
@@ -69,14 +79,22 @@ def connect(self, ssid, password):
6979
if self.new_network is not None:
7080
self.iface_ifc.RemoveNetwork(self.new_network)
7181

82+
print("Pre-connect state is %s, IP is %s" % (self._get_iface_property("State"), get_wiface_IPv4(self.iface_name)))
83+
7284
self.new_network = self.iface_ifc.AddNetwork({"ssid": ssid, "psk": password})
7385
self.iface_ifc.SelectNetwork(self.new_network)
7486
time.sleep(10)
7587

7688
ip = None
7789
retry = 10
7890
while retry > 0:
91+
time.sleep(5)
92+
state = str(self._get_iface_property("State"))
93+
print("wpa iface state %s (scanning %s)" % (state, bool(self._get_iface_property("Scanning"))))
94+
if state in ["disconnected", "inactive"]:
95+
self.iface_ifc.Reconnect()
7996
ip = get_wiface_IPv4(self.iface_name)
97+
print("wpa iface %s IP %s" % (self.iface_name, ip))
8098
if ip is not None:
8199
self.connected = True
82100
return ip

tools/esp_prov/esp_prov.py

Lines changed: 27 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -276,6 +276,32 @@ def get_wifi_config(tp, sec):
276276
return None
277277

278278

279+
def wait_wifi_connected(tp, sec):
280+
"""
281+
Wait for provisioning to report Wi-Fi is connected
282+
283+
Returns True if Wi-Fi connection succeeded, False if connection consistently failed
284+
"""
285+
TIME_PER_POLL = 5
286+
retry = 3
287+
288+
while True:
289+
time.sleep(TIME_PER_POLL)
290+
print("\n==== Wi-Fi connection state ====")
291+
ret = get_wifi_config(tp, sec)
292+
if ret == "connecting":
293+
continue
294+
elif ret == "connected":
295+
print("==== Provisioning was successful ====")
296+
return True
297+
elif retry > 0:
298+
retry -= 1
299+
print("Waiting to poll status again (status %s, %d tries left)..." % (ret, retry))
300+
else:
301+
print("---- Provisioning failed ----")
302+
return False
303+
304+
279305
def desc_format(*args):
280306
desc = ''
281307
for arg in args:
@@ -471,14 +497,4 @@ def desc_format(*args):
471497
exit(7)
472498
print("==== Apply config sent successfully ====")
473499

474-
while True:
475-
time.sleep(5)
476-
print("\n==== Wi-Fi connection state ====")
477-
ret = get_wifi_config(obj_transport, obj_security)
478-
if (ret == 1):
479-
continue
480-
elif (ret == 0):
481-
print("==== Provisioning was successful ====")
482-
else:
483-
print("---- Provisioning failed ----")
484-
break
500+
wait_wifi_connected(obj_transport, obj_security)

tools/esp_prov/prov/wifi_prov.py

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -45,19 +45,24 @@ def config_get_status_response(security_ctx, response_data):
4545
cmd_resp1.ParseFromString(decrypted_message)
4646
print_verbose(security_ctx, "Response type " + str(cmd_resp1.msg))
4747
print_verbose(security_ctx, "Response status " + str(cmd_resp1.resp_get_status.status))
48+
4849
if cmd_resp1.resp_get_status.sta_state == 0:
4950
print("++++ WiFi state: " + "connected ++++")
51+
return "connected"
5052
elif cmd_resp1.resp_get_status.sta_state == 1:
5153
print("++++ WiFi state: " + "connecting... ++++")
54+
return "connecting"
5255
elif cmd_resp1.resp_get_status.sta_state == 2:
5356
print("++++ WiFi state: " + "disconnected ++++")
57+
return "disconnected"
5458
elif cmd_resp1.resp_get_status.sta_state == 3:
5559
print("++++ WiFi state: " + "connection failed ++++")
5660
if cmd_resp1.resp_get_status.fail_reason == 0:
5761
print("++++ Failure reason: " + "Incorrect Password ++++")
5862
elif cmd_resp1.resp_get_status.fail_reason == 1:
5963
print("++++ Failure reason: " + "Incorrect SSID ++++")
60-
return cmd_resp1.resp_get_status.sta_state
64+
return "failed"
65+
return "unknown"
6166

6267

6368
def config_set_config_request(security_ctx, ssid, passphrase):

tools/esp_prov/transport/transport_http.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -34,9 +34,9 @@ def __init__(self, hostname, ssl_context=None):
3434
raise RuntimeError("Unable to resolve hostname :" + hostname)
3535

3636
if ssl_context is None:
37-
self.conn = HTTPConnection(hostname, timeout=30)
37+
self.conn = HTTPConnection(hostname, timeout=45)
3838
else:
39-
self.conn = HTTPSConnection(hostname, context=ssl_context, timeout=30)
39+
self.conn = HTTPSConnection(hostname, context=ssl_context, timeout=45)
4040
try:
4141
print("Connecting to " + hostname)
4242
self.conn.connect()

0 commit comments

Comments
 (0)