diff options
author | Nathan Williams <njw@chromium.org> | 2011-11-03 16:13:07 -0400 |
---|---|---|
committer | Dan Williams <dcbw@redhat.com> | 2011-11-03 16:54:08 -0500 |
commit | a027d27da8bb723b344fc2805ae9f3e2489dac00 (patch) | |
tree | 16651e9f4e3060b20c962040ab365c6179229d27 /src | |
parent | 87ec5e09a537f3ede83238a35ccd37ccc38eff8e (diff) |
gsm: finish all disable commands before returning
Rearrange the primary and secondary-port disable operations so that
there's a linear chain of callbacks rather than a second dangling
callback chain for the secondary port; it's possible for the primary
port operations to complete, and for the callback to finish and start
tearing down the entire device, before the secondary port commands
run.
Change-Id: Ia95a7eae574737cdec38b14d39786127be1b3184
Diffstat (limited to 'src')
-rw-r--r-- | src/mm-generic-gsm.c | 40 |
1 files changed, 25 insertions, 15 deletions
diff --git a/src/mm-generic-gsm.c b/src/mm-generic-gsm.c index f7584ad6..436c07c0 100644 --- a/src/mm-generic-gsm.c +++ b/src/mm-generic-gsm.c @@ -2027,12 +2027,29 @@ disable_flash_done (MMSerialPort *port, } static void +mark_disabled (gpointer user_data) +{ + MMCallbackInfo *info = user_data; + MMGenericGsmPrivate *priv = MM_GENERIC_GSM_GET_PRIVATE (info->modem); + + mm_modem_set_state (MM_MODEM (info->modem), + MM_MODEM_STATE_DISABLING, + MM_MODEM_STATE_REASON_NONE); + + if (mm_port_get_connected (MM_PORT (priv->primary))) + mm_serial_port_flash (MM_SERIAL_PORT (priv->primary), 1000, TRUE, disable_flash_done, info); + else + disable_flash_done (MM_SERIAL_PORT (priv->primary), NULL, info); +} + +static void secondary_unsolicited_done (MMAtSerialPort *port, GString *response, GError *error, gpointer user_data) { mm_serial_port_close_force (MM_SERIAL_PORT (port)); + mark_disabled (user_data); } static void @@ -2072,13 +2089,6 @@ disable (MMModem *modem, update_lac_ci (self, 0, 0, 1); _internal_update_access_technology (self, MM_MODEM_GSM_ACCESS_TECH_UNKNOWN); - /* Clean up the secondary port if it's open */ - if (priv->secondary && mm_serial_port_is_open (MM_SERIAL_PORT (priv->secondary))) { - mm_at_serial_port_queue_command (priv->secondary, "+CREG=0", 3, NULL, NULL); - mm_at_serial_port_queue_command (priv->secondary, "+CGREG=0", 3, NULL, NULL); - mm_at_serial_port_queue_command (priv->secondary, "+CMER=0", 3, secondary_unsolicited_done, NULL); - } - info = mm_callback_info_new (modem, callback, user_data); /* Cache the previous state so we can reset it if the operation fails */ @@ -2088,14 +2098,14 @@ disable (MMModem *modem, GUINT_TO_POINTER (state), NULL); - mm_modem_set_state (MM_MODEM (info->modem), - MM_MODEM_STATE_DISABLING, - MM_MODEM_STATE_REASON_NONE); - - if (mm_port_get_connected (MM_PORT (priv->primary))) - mm_serial_port_flash (MM_SERIAL_PORT (priv->primary), 1000, TRUE, disable_flash_done, info); - else - disable_flash_done (MM_SERIAL_PORT (priv->primary), NULL, info); + /* Clean up the secondary port if it's open */ + if (priv->secondary && mm_serial_port_is_open (MM_SERIAL_PORT (priv->secondary))) { + mm_dbg("Shutting down secondary port"); + mm_at_serial_port_queue_command (priv->secondary, "+CREG=0", 3, NULL, NULL); + mm_at_serial_port_queue_command (priv->secondary, "+CGREG=0", 3, NULL, NULL); + mm_at_serial_port_queue_command (priv->secondary, "+CMER=0", 3, secondary_unsolicited_done, info); + } else + mark_disabled (info); } static void |