modemmanager-next/samsung: Fix timer race in disconnect

When disconnecting, the previous logic flow was like this:

1.  Send disconenct command to modem.
2.  Get confirmation that the command was sent; set a timeout timer.
3.  Modem sends disconnect response; stop the timeout timer,
free the context.

However, in some cases, steps 2 qnd 3 were reversed so that the
function that stops the timer is called before the timer is set.
The result is that the timeout timer is not removed, and when it
expires, it operates on a freed context, leading to a crash.

The logic has been changed to set the timer earlier:

1.  Send disconenct command to modem; set the timeout timer.
2.  Get confirmation that the command was sent; if error,
stop the timeout timer, free the context.
3.  Modem sends disconnect response; stop the timeout timer,
free the context.

BUG=chromium-os:31743
TEST=ran cellular smoke test, which crashed before, but doesn't now.

Change-Id: Iac3d769655d69ea004c727eba7a3d8be14395101
diff --git a/plugins/samsung/mm-broadband-bearer-samsung.c b/plugins/samsung/mm-broadband-bearer-samsung.c
index afac777..9b36d71 100644
--- a/plugins/samsung/mm-broadband-bearer-samsung.c
+++ b/plugins/samsung/mm-broadband-bearer-samsung.c
@@ -452,14 +452,14 @@
         g_simple_async_result_take_error (ctx->result, error);
         g_simple_async_result_complete (ctx->result);
         g_object_unref (ctx->result);
-
+        if (ctx->timeout_id) {
+            g_source_remove (ctx->timeout_id);
+            ctx->timeout_id = 0;
+        }
         ctx->self->priv->pending_disconnect = NULL;
         g_free (ctx);
         return;
     }
-
-    /* Set a 60-second disconnection-failure timeout */
-    ctx->timeout_id = g_timeout_add_seconds (60, (GSourceFunc)disconnect_3gpp_timeout, ctx);
 }
 
 static void
@@ -494,6 +494,10 @@
     g_free (command);
 
     self->priv->pending_disconnect = ctx;
+
+    /* Set a 60-second disconnection-failure timeout */
+    ctx->timeout_id = g_timeout_add_seconds (
+        60, (GSourceFunc)disconnect_3gpp_timeout, ctx);
 }
 
 static void