[PATCH 1/2] bearer-qmi: detect early disconnections when getting current settings

Aleksander Morgado aleksander at aleksander.es
Tue Sep 5 20:26:12 UTC 2017


A failure when getting current settings isn't a hard error, unless the
error is "OutOfCall", as that is telling us that the modem is
disconnected, e.g.:

    Aug 30 22:48:35 ModemManager[574]: <info>  Simple connect started...
    Aug 30 22:48:35 ModemManager[574]: <info>  Simple connect state (4/8): Wait to get fully enabled
    Aug 30 22:48:35 ModemManager[574]: <info>  Simple connect state (5/8): Register
    Aug 30 22:48:35 ModemManager[574]: <info>  Simple connect state (6/8): Bearer
    Aug 30 22:48:35 ModemManager[574]: <info>  Simple connect state (7/8): Connect
    Aug 30 22:48:35 ModemManager[574]: <info>  Modem /org/freedesktop/ModemManager1/Modem/0: state changed (registered -> connecting)
    Aug 30 22:48:35 ModemManager[574]: <info>  error: couldn't get current settings: QMI protocol error (15): 'OutOfCall'
    Aug 30 22:48:35 ModemManager[574]: <info>  Modem /org/freedesktop/ModemManager1/Modem/0: state changed (connecting -> connected)
    Aug 30 22:48:35 ModemManager[574]: <info>  Simple connect state (8/8): All done

In the previous sequence, we report the modem is connected while it
really isn't.
---
 src/mm-bearer-qmi.c | 26 ++++++++++++++++++++------
 1 file changed, 20 insertions(+), 6 deletions(-)

diff --git a/src/mm-bearer-qmi.c b/src/mm-bearer-qmi.c
index c687db60..90857a4a 100644
--- a/src/mm-bearer-qmi.c
+++ b/src/mm-bearer-qmi.c
@@ -671,12 +671,26 @@ get_current_settings_ready (QmiClientWds *client,
     g_assert (ctx->running_ipv4 || ctx->running_ipv6);
 
     output = qmi_client_wds_get_current_settings_finish (client, res, &error);
-    if (!output ||
-        !qmi_message_wds_get_current_settings_output_get_result (output, &error)) {
-        /* Never treat this as a hard connection error; not all devices support
-         * "WDS Get Current Settings" */
-        mm_info ("error: couldn't get current settings: %s", error->message);
-        g_error_free (error);
+    if (!output || !qmi_message_wds_get_current_settings_output_get_result (output, &error)) {
+        /* Only treat this as a hard connection error if OutOfCall is reported.
+         * Not all devices support "WDS Get Current Settings", but if they do
+         * and report OutOfCall, it means connection has really failed */
+        if (g_error_matches (error, QMI_PROTOCOL_ERROR, QMI_PROTOCOL_ERROR_OUT_OF_CALL)) {
+            /* Cleanup packet data handle and store error */
+            if (ctx->running_ipv4) {
+                ctx->packet_data_handle_ipv4 = 0;
+                g_clear_error (&ctx->error_ipv4);
+                ctx->error_ipv4 = error;
+            } else if (ctx->running_ipv6) {
+                ctx->packet_data_handle_ipv6 = 0;
+                g_clear_error (&ctx->error_ipv6);
+                ctx->error_ipv6 = error;
+            } else
+                g_assert_not_reached ();
+        } else {
+            mm_info ("error: couldn't get current settings: %s", error->message);
+            g_error_free (error);
+        }
     } else {
         QmiWdsIpFamily ip_family = QMI_WDS_IP_FAMILY_UNSPECIFIED;
         guint32 mtu = 0;
-- 
2.13.1



More information about the ModemManager-devel mailing list