From: Lee, Chun-Yi <[email protected]> There have a race condition issue in connman between wifi driver object with element->driver reference. On some machine, the wifi driver object doesn't generate before we try to register a element. It causes element->driver is NULL, and will not do driver->remove when remove element.
Signed-off-by: Lee, Chun-Yi <[email protected]> --- src/connman.h | 1 + src/device.c | 2 ++ src/element.c | 43 ++++++++++++++++++++++++++----------------- 3 files changed, 29 insertions(+), 17 deletions(-) diff --git a/src/connman.h b/src/connman.h index 3a546fe..a467c64 100644 --- a/src/connman.h +++ b/src/connman.h @@ -169,6 +169,7 @@ void __connman_element_foreach(struct connman_element *element, void __connman_element_list(struct connman_element *element, enum connman_element_type type, DBusMessageIter *iter); +void __connman_element_probe_element(struct connman_element *element); struct connman_service *__connman_element_get_service(struct connman_element *element); struct connman_device *__connman_element_get_device(struct connman_element *element); diff --git a/src/device.c b/src/device.c index 373eb5f..8e9b67b 100644 --- a/src/device.c +++ b/src/device.c @@ -587,6 +587,8 @@ static void probe_driver(struct connman_element *element, gpointer user_data) element->device->driver = driver; setup_device(element->device); + + __connman_element_probe_element(element); } static void remove_device(struct connman_device *device) diff --git a/src/element.c b/src/element.c index 74383cc..41860c3 100644 --- a/src/element.c +++ b/src/element.c @@ -479,6 +479,31 @@ static gboolean probe_driver(GNode *node, gpointer data) return FALSE; } +void __connman_element_probe_element(struct connman_element *element) +{ + GSList *list; + + DBG("element %p name %s", element, element->name); + + for (list = driver_list; list; list = list->next) { + struct connman_driver *driver = list->data; + + if (match_driver(element, driver) == FALSE) + continue; + + DBG("driver %p name %s", driver, driver->name); + + if (__connman_device_has_driver(element->device) == TRUE) { + if (element->driver == NULL) + element->driver = driver; + break; + } else if (driver->probe(element) == 0) { + element->driver = driver; + break; + } + } +} + void __connman_driver_rescan(struct connman_driver *driver) { DBG("driver %p name %s", driver, driver->name); @@ -1007,23 +1032,7 @@ const void *connman_element_get_blob(struct connman_element *element, static void probe_element(struct connman_element *element) { - GSList *list; - - DBG("element %p name %s", element, element->name); - - for (list = driver_list; list; list = list->next) { - struct connman_driver *driver = list->data; - - if (match_driver(element, driver) == FALSE) - continue; - - DBG("driver %p name %s", driver, driver->name); - - if (driver->probe(element) == 0) { - element->driver = driver; - break; - } - } + __connman_element_probe_element(element); } static void register_element(gpointer data, gpointer user_data) -- 1.6.0.2 _______________________________________________ connman mailing list [email protected] http://lists.connman.net/listinfo/connman
