dundee: add timeout to close stalled ppp handshake
authorGustavo Padovan <gustavo.padovan@collabora.co.uk>
Tue, 14 Aug 2012 07:14:31 +0000 (04:14 -0300)
committerDaniel Wagner <daniel.wagner@bmw-carit.de>
Fri, 17 Aug 2012 12:59:50 +0000 (14:59 +0200)
If something goes wrong the PPP handshake can stall, then we just add a
timer to return an error after a certain timeout (15 seconds).

dundee/dbus.c
dundee/device.c
dundee/dundee.h

index c245eab..90bd76b 100644 (file)
@@ -43,3 +43,9 @@ DBusMessage *__dundee_error_failed(DBusMessage *msg)
                                        ".Failed",
                                        "Operation failed");
 }
+
+DBusMessage *__dundee_error_timed_out(DBusMessage *msg)
+{
+       return g_dbus_create_error(msg, DUNDEE_ERROR_INTERFACE ".Timedout",
+                       "Operation failure due to timeout");
+}
index 709919a..e921a2a 100644 (file)
@@ -35,6 +35,8 @@
 
 #include "dundee.h"
 
+#define PPP_TIMEOUT 15
+
 static int next_device_id = 0;
 static GHashTable *device_hash;
 
@@ -59,6 +61,7 @@ struct dundee_device {
        struct ipv4_settings settings;
 
        DBusMessage *pending;
+       guint connect_timeout;
        void *data;
 };
 
@@ -221,6 +224,11 @@ static void ppp_connect(const char *iface, const char *local, const char *peer,
        DBG("Primary DNS Server: %s\n", dns1);
        DBG("Secondary DNS Server: %s\n", dns2);
 
+       if (device->connect_timeout > 0) {
+               g_source_remove(device->connect_timeout);
+               device->connect_timeout = 0;
+       }
+
        g_free(device->settings.interface);
        device->settings.interface = g_strdup(iface);
        if (device->settings.interface == NULL)
@@ -287,6 +295,23 @@ out:
        device->pending = NULL;
 }
 
+static gboolean ppp_connect_timeout(gpointer user_data)
+{
+       struct dundee_device *device = user_data;
+
+       if (device->pending != NULL) {
+               __ofono_dbus_pending_reply(&device->pending,
+                               __dundee_error_timed_out(device->pending));
+               device->pending = NULL;
+       }
+
+       device->driver->disconnect(device, disconnect_callback, device);
+
+       device->connect_timeout = 0;
+
+       return FALSE;
+}
+
 static void ppp_disconnect(GAtPPPDisconnectReason reason, gpointer user_data)
 {
        DBusConnection *conn = ofono_dbus_get_connection();
@@ -344,6 +369,9 @@ static void dial_cb(gboolean ok, GAtResult *result, gpointer user_data)
        }
        g_at_ppp_set_debug(device->ppp, debug, "PPP");
 
+       device->connect_timeout = g_timeout_add_seconds(PPP_TIMEOUT,
+                                               ppp_connect_timeout, device);
+
        /* set connect and disconnect callbacks */
        g_at_ppp_set_connect_function(device->ppp, ppp_connect, device);
        g_at_ppp_set_disconnect_function(device->ppp, ppp_disconnect, device);
index 8866007..db932b6 100644 (file)
@@ -94,6 +94,7 @@ void __ofono_dbus_pending_reply(DBusMessage **msg, DBusMessage *reply);
 
 DBusMessage *__dundee_error_invalid_args(DBusMessage *msg);
 DBusMessage *__dundee_error_failed(DBusMessage *msg);
+DBusMessage *__dundee_error_timed_out(DBusMessage *msg);
 
 
 int __dundee_manager_init(void);