no more lock!

pull/36063/head
Shane Smiskol 3 days ago
parent 0c6974db12
commit 8c1abd96a2
  1. 25
      system/ui/lib/wifi_manager.py
  2. 13
      system/ui/widgets/network.py

@ -136,10 +136,9 @@ class WifiManager:
self._callback_queue: list[Callable] = [] self._callback_queue: list[Callable] = []
# Callbacks # Callbacks
# TODO: implement a callback queue to avoid blocking UI thread
self._need_auth: Callable[[str], None] | None = None self._need_auth: Callable[[str], None] | None = None
self._activated: Callable[[], None] | None = None self._activated: Callable[[], None] | None = None
self._forgotten: Callable[[str], None] | None = None self._forgotten: Callable[[], None] | None = None
self._networks_updated: Callable[[list[Network]], None] | None = None self._networks_updated: Callable[[list[Network]], None] | None = None
self._disconnected: Callable[[], None] | None = None self._disconnected: Callable[[], None] | None = None
@ -155,7 +154,7 @@ class WifiManager:
def set_callbacks(self, need_auth: Callable[[str], None], def set_callbacks(self, need_auth: Callable[[str], None],
activated: Callable[[], None] | None, activated: Callable[[], None] | None,
forgotten: Callable[[str], None], forgotten: Callable[[], None],
networks_updated: Callable[[list[Network]], None], networks_updated: Callable[[list[Network]], None],
disconnected: Callable[[], None]): disconnected: Callable[[], None]):
self._need_auth = need_auth self._need_auth = need_auth
@ -164,11 +163,14 @@ class WifiManager:
self._networks_updated = networks_updated self._networks_updated = networks_updated
self._disconnected = disconnected self._disconnected = disconnected
def _enqueue_callback(self, cb: Callable, *args):
self._callback_queue.append(lambda: cb(*args))
def process_callbacks(self): def process_callbacks(self):
for cb in self._callback_queue: # Call from UI thread to run any pending callbacks
print('calling wifi cb', cb.__name__) to_run, self._callback_queue = self._callback_queue, []
for cb in to_run:
cb() cb()
self._callback_queue.clear()
def set_active(self, active: bool): def set_active(self, active: bool):
self._active = active self._active = active
@ -213,19 +215,20 @@ class WifiManager:
print('hi') print('hi')
if self._need_auth is not None: if self._need_auth is not None:
print('wifi need auth', self._connecting_to_ssid) print('wifi need auth', self._connecting_to_ssid)
self._callback_queue.append(lambda ssid=self._connecting_to_ssid: self._need_auth(ssid)) # self._callback_queue.append(lambda cb=self._need_auth, ssid=self._connecting_to_ssid: cb(ssid))
self._enqueue_callback(self._need_auth, self._connecting_to_ssid)
self._connecting_to_ssid = "" self._connecting_to_ssid = ""
elif new_state == NMDeviceState.ACTIVATED: elif new_state == NMDeviceState.ACTIVATED:
if self._activated is not None: if self._activated is not None:
self._update_networks() self._update_networks()
self._callback_queue.append(self._activated) self._enqueue_callback(self._activated)
self._connecting_to_ssid = "" self._connecting_to_ssid = ""
elif new_state == NMDeviceState.DISCONNECTED and change_reason != NM_DEVICE_STATE_REASON_NEW_ACTIVATION: elif new_state == NMDeviceState.DISCONNECTED and change_reason != NM_DEVICE_STATE_REASON_NEW_ACTIVATION:
self._connecting_to_ssid = "" self._connecting_to_ssid = ""
if self._disconnected is not None: if self._disconnected is not None:
self._callback_queue.append(self._disconnected) self._enqueue_callback(self._disconnected)
def _network_scanner(self): def _network_scanner(self):
self._wait_for_wifi_device() self._wait_for_wifi_device()
@ -333,7 +336,7 @@ class WifiManager:
if self._forgotten is not None: if self._forgotten is not None:
self._update_networks() self._update_networks()
self._callback_queue.append(lambda: self._forgotten(ssid)) self._enqueue_callback(self._forgotten)
if block: if block:
worker() worker()
@ -409,7 +412,7 @@ class WifiManager:
self._networks = networks self._networks = networks
if self._networks_updated is not None: if self._networks_updated is not None:
self._callback_queue.append(lambda: self._networks_updated(self._networks)) self._enqueue_callback(self._networks_updated, self._networks)
def __del__(self): def __del__(self):
self.stop() self.stop()

@ -1,6 +1,5 @@
from enum import IntEnum from enum import IntEnum
from functools import partial from functools import partial
from threading import Lock
from typing import cast from typing import cast
import pyray as rl import pyray as rl
@ -50,7 +49,6 @@ class WifiManagerUI(Widget):
self._networks: list[Network] = [] self._networks: list[Network] = []
self._networks_buttons: dict[str, Button] = {} self._networks_buttons: dict[str, Button] = {}
self._forget_networks_buttons: dict[str, Button] = {} self._forget_networks_buttons: dict[str, Button] = {}
self._lock = Lock()
self._confirm_dialog = ConfirmDialog("", "Forget", "Cancel") self._confirm_dialog = ConfirmDialog("", "Forget", "Cancel")
self.wifi_manager.set_callbacks(need_auth=self._on_need_auth, self.wifi_manager.set_callbacks(need_auth=self._on_need_auth,
@ -73,7 +71,6 @@ class WifiManagerUI(Widget):
def _render(self, rect: rl.Rectangle): def _render(self, rect: rl.Rectangle):
self.wifi_manager.process_callbacks() self.wifi_manager.process_callbacks()
with self._lock:
if not self._networks: if not self._networks:
gui_label(rect, "Scanning Wi-Fi networks...", 72, alignment=rl.GuiTextAlignment.TEXT_ALIGN_CENTER) gui_label(rect, "Scanning Wi-Fi networks...", 72, alignment=rl.GuiTextAlignment.TEXT_ALIGN_CENTER)
return return
@ -213,7 +210,7 @@ class WifiManagerUI(Widget):
self.wifi_manager.forget_connection(network.ssid) self.wifi_manager.forget_connection(network.ssid)
def _on_network_updated(self, networks: list[Network]): def _on_network_updated(self, networks: list[Network]):
with self._lock: print('networks updated', [n.ssid for n in networks])
self._networks = networks self._networks = networks
for n in self._networks: for n in self._networks:
self._networks_buttons[n.ssid] = Button(n.ssid, partial(self._networks_buttons_callback, n), font_size=55, text_alignment=TextAlignment.LEFT, self._networks_buttons[n.ssid] = Button(n.ssid, partial(self._networks_buttons_callback, n), font_size=55, text_alignment=TextAlignment.LEFT,
@ -223,7 +220,6 @@ class WifiManagerUI(Widget):
def _on_need_auth(self, ssid): def _on_need_auth(self, ssid):
print('need auth for', ssid) print('need auth for', ssid)
with self._lock:
network = next((n for n in self._networks if n.ssid == ssid), None) network = next((n for n in self._networks if n.ssid == ssid), None)
if network: if network:
self.state = UIState.NEEDS_AUTH self.state = UIState.NEEDS_AUTH
@ -231,17 +227,16 @@ class WifiManagerUI(Widget):
self._password_retry = True self._password_retry = True
def _on_activated(self): def _on_activated(self):
with self._lock: print('_on_activated')
if self.state == UIState.CONNECTING: if self.state == UIState.CONNECTING:
self.state = UIState.IDLE self.state = UIState.IDLE
def _on_forgotten(self, ssid): def _on_forgotten(self):
with self._lock: print('_on_forgotten')
if self.state == UIState.FORGETTING: if self.state == UIState.FORGETTING:
self.state = UIState.IDLE self.state = UIState.IDLE
def _on_disconnected(self): def _on_disconnected(self):
with self._lock:
if self.state == UIState.CONNECTING: if self.state == UIState.CONNECTING:
self.state = UIState.IDLE self.state = UIState.IDLE

Loading…
Cancel
Save