---
 src/gprs.c |  106 ++++++++++++++++++++++++++++++++++++++++++++++++------------
 1 files changed, 85 insertions(+), 21 deletions(-)

diff --git a/src/gprs.c b/src/gprs.c
index 0d25506..9428003 100644
--- a/src/gprs.c
+++ b/src/gprs.c
@@ -1436,6 +1436,78 @@ void ofono_gprs_resume_notify(struct ofono_gprs *gprs)
        update_suspended_property(gprs, FALSE);
 }
 
+static void gprs_attached_update(struct ofono_gprs *gprs);
+
+static void gprs_deactivate_for_release(const struct ofono_error *error,
+                                               void *data)
+{
+       struct pri_context *ctx = data;
+       struct ofono_gprs *gprs = ctx->gprs;
+       DBusConnection *conn = ofono_dbus_get_connection();
+       dbus_bool_t value;
+
+       if (error->type != OFONO_ERROR_TYPE_NO_ERROR) {
+               DBG("Deactivating context failed with error: %s",
+                               telephony_error_to_str(error));
+
+               return;
+       }
+
+       pri_reset_context_settings(ctx);
+       release_context(ctx);
+
+       value = FALSE;
+       ofono_dbus_signal_property_changed(conn, ctx->path,
+                                       OFONO_CONNECTION_CONTEXT_INTERFACE,
+                                       "Active", DBUS_TYPE_BOOLEAN, &value);
+
+       /*
+        * If "Attached" property was about to be signalled as TRUE but there
+        * were still active contexts, try again to signal "Attached" property
+        * to registered applications after active contexts have been released.
+        */
+       gprs_attached_update(gprs);
+}
+
+static gboolean check_active_contexts(struct ofono_gprs *gprs)
+{
+       GSList *l;
+       struct pri_context *ctx;
+
+       for (l = gprs->contexts; l; l = l->next) {
+               ctx = l->data;
+
+               if (ctx->active == TRUE)
+                       return TRUE;
+       }
+
+       return FALSE;
+}
+
+static void deactivate_active_contexts(struct ofono_gprs *gprs)
+{
+       GSList *l;
+       struct pri_context *ctx;
+
+       for (l = gprs->contexts; l; l = l->next) {
+               struct ofono_gprs_context *gc;
+
+               ctx = l->data;
+
+               if (ctx->active == FALSE)
+                       continue;
+
+               /* This context is already being messed with */
+               if (ctx->pending)
+                       continue;
+
+               gc = ctx->context_driver;
+
+               gc->driver->deactivate_primary(gc, ctx->context.cid,
+                                       gprs_deactivate_for_release, ctx);
+       }
+}
+
 static void gprs_attached_update(struct ofono_gprs *gprs)
 {
        DBusConnection *conn = ofono_dbus_get_connection();
@@ -1450,30 +1522,22 @@ static void gprs_attached_update(struct ofono_gprs 
*gprs)
        if (attached == gprs->attached)
                return;
 
-       gprs->attached = attached;
-
-       if (gprs->attached == FALSE) {
-               GSList *l;
-               struct pri_context *ctx;
-
-               for (l = gprs->contexts; l; l = l->next) {
-                       ctx = l->data;
-
-                       if (ctx->active == FALSE)
-                               continue;
-
-                       pri_reset_context_settings(ctx);
-                       release_context(ctx);
-
-                       value = FALSE;
-                       ofono_dbus_signal_property_changed(conn, ctx->path,
-                                       OFONO_CONNECTION_CONTEXT_INTERFACE,
-                                       "Active", DBUS_TYPE_BOOLEAN, &value);
-               }
-
+       /*
+        * If an active context is found, a PPP session might be still active
+        * at driver level. "Attached" = TRUE property can't be signalled to
+        * the applications registered on GPRS properties.
+        * Active contexts have to be deactivated.
+        */
+       if (attached == FALSE) {
+               deactivate_active_contexts(gprs);
                gprs->bearer = -1;
+       } else if (check_active_contexts(gprs) == TRUE) {
+               deactivate_active_contexts(gprs);
+               return;
        }
 
+       gprs->attached = attached;
+
        path = __ofono_atom_get_path(gprs->atom);
        value = attached;
        ofono_dbus_signal_property_changed(conn, path,
-- 
1.7.5.4

_______________________________________________
ofono mailing list
[email protected]
http://lists.ofono.org/listinfo/ofono

Reply via email to