From 39a3487877e489c2aa26310bd93f76f2786f9d25 Mon Sep 17 00:00:00 2001 From: Marcel Holtmann Date: Thu, 26 Nov 2009 09:20:48 +0100 Subject: [PATCH] Add checks for invalid supplicant state transitions --- plugins/supplicant.c | 38 +++++++++++++++++++++++++++++++++++--- 1 file changed, 35 insertions(+), 3 deletions(-) diff --git a/plugins/supplicant.c b/plugins/supplicant.c index cbefeaa..554548a 100644 --- a/plugins/supplicant.c +++ b/plugins/supplicant.c @@ -1570,7 +1570,7 @@ static void state_change(struct supplicant_task *task, DBusMessage *msg) const char *newstate, *oldstate; unsigned char bssid[ETH_ALEN]; unsigned int bssid_len; - enum supplicant_state state; + enum supplicant_state state, prevstate; dbus_error_init(&error); @@ -1587,7 +1587,8 @@ static void state_change(struct supplicant_task *task, DBusMessage *msg) DBG("state %s ==> %s", oldstate, newstate); - connman_info("%s %s", task->ifname, newstate); + connman_info("%s %s%s", task->ifname, newstate, + task->scanning == TRUE ? " (scanning)" : ""); state = string2state(newstate); if (state == WPA_INVALID) @@ -1598,6 +1599,7 @@ static void state_change(struct supplicant_task *task, DBusMessage *msg) task->scanning = FALSE; } + prevstate = task->state; task->state = state; if (task->network == NULL) @@ -1605,6 +1607,14 @@ static void state_change(struct supplicant_task *task, DBusMessage *msg) switch (task->state) { case WPA_COMPLETED: + switch (prevstate) { + case WPA_ASSOCIATED: + case WPA_GROUP_HANDSHAKE: + break; + default: + goto badstate; + } + /* reset scan trigger and schedule background scan */ connman_device_schedule_scan(task->device); @@ -1636,10 +1646,26 @@ static void state_change(struct supplicant_task *task, DBusMessage *msg) break; case WPA_ASSOCIATING: - connman_network_set_associating(task->network, TRUE); + switch (prevstate) { + case WPA_COMPLETED: + break; + case WPA_SCANNING: + connman_network_set_associating(task->network, TRUE); + break; + default: + goto badstate; + } break; case WPA_INACTIVE: + switch (prevstate) { + case WPA_SCANNING: + case WPA_DISCONNECTED: + break; + default: + goto badstate; + } + connman_network_set_connected(task->network, FALSE); if (task->disconnecting == TRUE) { @@ -1659,6 +1685,12 @@ static void state_change(struct supplicant_task *task, DBusMessage *msg) connman_network_set_associating(task->network, FALSE); break; } + + return; + +badstate: + connman_error("%s invalid state change %s -> %s", task->ifname, + oldstate, newstate); } static DBusHandlerResult supplicant_filter(DBusConnection *conn, -- 2.7.4