From 2c88c37f9972e82d9cffa3e495ef5e234e82096c Mon Sep 17 00:00:00 2001 From: Andrew Zaborowski Date: Fri, 5 Aug 2016 14:25:34 +0200 Subject: [PATCH] netdev: Cancel the CMD_CONNECT genl command on disconnect CMD_DISCONNECT fails on some occasions when CMD_CONNECT is still running. When this happens the DBus disconnect command receives an error reply but iwd's device state is left as disconnected even though there's a connection at the kernel level which times out a few seconds later. If the CMD_CONNECT is cancelled I couldn't reproduce this so far. src/network.c:network_connect() src/network.c:network_connect_psk() src/network.c:network_connect_psk() psk: 69ae3f8b2f84a438cf6a44275913182dd2714510ccb8cbdf8da9dc8b61718560 src/network.c:network_connect_psk() len: 32 src/network.c:network_connect_psk() ask_psk: false src/device.c:device_enter_state() Old State: disconnected, new state: connecting src/scan.c:scan_notify() Scan notification 33 src/device.c:device_netdev_event() Associating src/netdev.c:netdev_mlme_notify() MLME notification 60 MLME notification is missing ifindex attribute src/device.c:device_dbus_disconnect() src/device.c:device_connect_cb() 6, result: 5 src/device.c:device_enter_state() Old State: connecting, new state: disconnecting src/device.c:device_disconnect_cb() 6, success: 0 src/device.c:device_enter_state() Old State: disconnecting, new state: disconnected src/scan.c:scan_notify() Scan notification 34 src/netdev.c:netdev_mlme_notify() MLME notification 19 src/netdev.c:netdev_mlme_notify() MLME notification 60 MLME notification is missing ifindex attribute src/netdev.c:netdev_mlme_notify() MLME notification 37 src/netdev.c:netdev_authenticate_event() src/scan.c:get_scan_callback() get_scan_callback src/scan.c:get_scan_done() get_scan_done src/netdev.c:netdev_mlme_notify() MLME notification 60 MLME notification is missing ifindex attribute src/netdev.c:netdev_mlme_notify() MLME notification 19 MLME notification is missing ifindex attribute src/netdev.c:netdev_mlme_notify() MLME notification 38 src/netdev.c:netdev_associate_event() src/netdev.c:netdev_mlme_notify() MLME notification 46 src/netdev.c:netdev_connect_event() src/netdev.c:netdev_mlme_notify() MLME notification 60 MLME notification is missing ifindex attribute src/netdev.c:netdev_mlme_notify() MLME notification 20 MLME notification is missing ifindex attribute src/netdev.c:netdev_mlme_notify() MLME notification 20 src/netdev.c:netdev_mlme_notify() MLME notification 39 src/netdev.c:netdev_deauthenticate_event() --- src/netdev.c | 15 +++++++++++++-- 1 file changed, 13 insertions(+), 2 deletions(-) diff --git a/src/netdev.c b/src/netdev.c index e6a4aff6..0a9fcbec 100644 --- a/src/netdev.c +++ b/src/netdev.c @@ -67,6 +67,7 @@ struct netdev { uint32_t pairwise_new_key_cmd_id; uint32_t pairwise_set_key_cmd_id; uint32_t group_new_key_cmd_id; + uint32_t connect_cmd_id; struct l_queue *watches; uint32_t next_watch_id; @@ -296,6 +297,11 @@ static void netdev_connect_free(struct netdev *netdev) l_genl_family_cancel(nl80211, netdev->group_new_key_cmd_id); netdev->group_new_key_cmd_id = 0; } + + if (netdev->connect_cmd_id) { + l_genl_family_cancel(nl80211, netdev->connect_cmd_id); + netdev->connect_cmd_id = 0; + } } static void netdev_free(void *data) @@ -1021,6 +1027,8 @@ static void netdev_cmd_connect_cb(struct l_genl_msg *msg, void *user_data) { struct netdev *netdev = user_data; + netdev->connect_cmd_id = 0; + /* Wait for connect event */ if (l_genl_msg_get_error(msg) >= 0) { if (netdev->event_filter) @@ -1102,8 +1110,11 @@ int netdev_connect(struct netdev *netdev, struct scan_bss *bss, if (!cmd_connect) return -EINVAL; - if (!l_genl_family_send(nl80211, cmd_connect, - netdev_cmd_connect_cb, netdev, NULL)) { + netdev->connect_cmd_id = l_genl_family_send(nl80211, cmd_connect, + netdev_cmd_connect_cb, + netdev, NULL); + + if (!netdev->connect_cmd_id) { l_genl_msg_unref(cmd_connect); return -EIO; }