tests: improve NetworkManager stub service for Wi-Fi scanning
Now that nmcli initiates a scan before displaying Wi-Fi networks, the stub service must properly support that as well. For the moment, the stub service chooses "now" as LastScan timestamp. This causes nmcli not to trigger a new scan, because nmcli gives unstable output if multiple nmcli processes in parallel race to trigger a Wi-Fi scan. That should be fixed.
This commit is contained in:
@@ -2772,6 +2772,17 @@ wifi_list_aps (NMDeviceWifi *wifi,
|
||||
|
||||
needs_rescan = rescan_cutoff < 0 || (rescan_cutoff > 0 && nm_device_wifi_get_last_scan (wifi) < rescan_cutoff);
|
||||
|
||||
/* FIXME: nmcli should either
|
||||
* - don't request any new scan for any device and print the full AP list right
|
||||
* away.
|
||||
* - or, when requesting a scan on one or more devices, don't print the result
|
||||
* before all requests complete.
|
||||
*
|
||||
* Otherwise:
|
||||
* - the printed output is not self consistent. E.g. it will print the result
|
||||
* on one device at a certain time, while printing the result for another
|
||||
* device at a later point in time.
|
||||
* - the order in which we print the AP list per-device, is unstable. */
|
||||
if (needs_rescan) {
|
||||
data = g_slice_new0 (WifiListData);
|
||||
data->nmc = nmc;
|
||||
|
@@ -49,6 +49,11 @@ class Util:
|
||||
|
||||
PY3 = (sys.version_info[0] == 3)
|
||||
|
||||
@staticmethod
|
||||
def g_source_remove(source_id):
|
||||
if source_id is not None:
|
||||
GLib.source_remove(source_id)
|
||||
|
||||
@staticmethod
|
||||
def addr_family_check(family, allow_af_unspec = False):
|
||||
if family == socket.AF_INET:
|
||||
@@ -840,6 +845,7 @@ PRP_WIFI_AP_HW_ADDRESS = "HwAddress"
|
||||
PRP_WIFI_AP_MODE = "Mode"
|
||||
PRP_WIFI_AP_MAX_BITRATE = "MaxBitrate"
|
||||
PRP_WIFI_AP_STRENGTH = "Strength"
|
||||
PRP_WIFI_AP_LAST_SEEN = "LastSeen"
|
||||
|
||||
class WifiAp(ExportedObj):
|
||||
|
||||
@@ -875,6 +881,7 @@ class WifiAp(ExportedObj):
|
||||
PRP_WIFI_AP_MODE: dbus.UInt32(getattr(NM,'80211Mode').INFRA),
|
||||
PRP_WIFI_AP_MAX_BITRATE: dbus.UInt32(54000),
|
||||
PRP_WIFI_AP_STRENGTH: dbus.Byte(strength),
|
||||
PRP_WIFI_AP_LAST_SEEN: dbus.Int32(NM.utils_get_timestamp_msec() / 1000),
|
||||
}
|
||||
|
||||
self.dbus_interface_add(IFACE_WIFI_AP, props, WifiAp.PropertiesChanged)
|
||||
@@ -902,6 +909,18 @@ class WifiDevice(Device):
|
||||
mac = Util.random_mac(self.ident)
|
||||
|
||||
self.aps = []
|
||||
self.scan_cb_id = None
|
||||
|
||||
# Note: we would like to simulate how nmcli calls RequestScan() and we could
|
||||
# do so by using an older timestamp. However, that makes the client tests
|
||||
# racy, because if a bunch of nmcli instances run in parallel against this
|
||||
# service, earlier instances will issue a RequestScan(), while later instances
|
||||
# won't do that (because the LastScan timestamp is already updated). That means,
|
||||
# the later instances will print the scan result immediately, and in another sort
|
||||
# order. That should be fixed, by nmcli not starting to print anything, before
|
||||
# all RequestScan() requests complete, and thus, always print a consistent list
|
||||
# of results.
|
||||
ts = NM.utils_get_timestamp_msec()
|
||||
|
||||
props = {
|
||||
PRP_WIFI_HW_ADDRESS: mac,
|
||||
@@ -911,7 +930,7 @@ class WifiDevice(Device):
|
||||
PRP_WIFI_WIRELESS_CAPABILITIES: dbus.UInt32(0xFF),
|
||||
PRP_WIFI_ACCESS_POINTS: ExportedObj.to_path_array(self.aps),
|
||||
PRP_WIFI_ACTIVE_ACCESS_POINT: ExportedObj.to_path(None),
|
||||
PRP_WIFI_LAST_SCAN: NM.utils_get_timestamp_msec(),
|
||||
PRP_WIFI_LAST_SCAN: dbus.Int64(ts),
|
||||
}
|
||||
|
||||
self.dbus_interface_add(IFACE_WIFI, props, WifiDevice.PropertiesChanged)
|
||||
@@ -928,6 +947,15 @@ class WifiDevice(Device):
|
||||
|
||||
@dbus.service.method(dbus_interface=IFACE_WIFI, in_signature='a{sv}', out_signature='')
|
||||
def RequestScan(self, props):
|
||||
self.scan_cb_id = Util.g_source_remove(self.scan_cb_id)
|
||||
def cb():
|
||||
ts = NM.utils_get_timestamp_msec()
|
||||
for ap in self.aps:
|
||||
ap._dbus_property_set(IFACE_WIFI_AP, PRP_WIFI_AP_LAST_SEEN, dbus.Int32(ts / 1000))
|
||||
self._dbus_property_set(IFACE_WIFI, PRP_WIFI_LAST_SCAN, dbus.Int64(ts))
|
||||
self.scan_cb_id = None
|
||||
return False
|
||||
self.scan_cb_id = GLib.idle_add(cb)
|
||||
pass
|
||||
|
||||
@dbus.service.signal(IFACE_WIFI, signature='o')
|
||||
@@ -947,6 +975,10 @@ class WifiDevice(Device):
|
||||
self.AccessPointRemoved(ExportedObj.to_path(ap))
|
||||
ap.unexport()
|
||||
|
||||
def stop(self):
|
||||
self.scan_cb_id = Util.g_source_remove(self.scan_cb_id)
|
||||
super(WifiDevice, self).stop()
|
||||
|
||||
@dbus.service.signal(IFACE_WIFI, signature='o')
|
||||
def AccessPointRemoved(self, ap_path):
|
||||
pass
|
||||
@@ -1138,11 +1170,7 @@ class ActiveConnection(ExportedObj):
|
||||
self.StateChanged(state, dbus.UInt32(reason))
|
||||
|
||||
def activation_cancel(self):
|
||||
if self._activation_id is None:
|
||||
return False
|
||||
GLib.source_remove(self._activation_id)
|
||||
self._activation_id = None
|
||||
return True
|
||||
self._activation_id = Util.g_source_remove(self._activation_id)
|
||||
|
||||
def _activation_step2(self):
|
||||
assert self._activation_id is not None
|
||||
|
Reference in New Issue
Block a user