Skip to content

Instantly share code, notes, and snippets.

@dtatulea
Created March 14, 2016 16:12
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save dtatulea/0ae543e3a993996b634f to your computer and use it in GitHub Desktop.
Save dtatulea/0ae543e3a993996b634f to your computer and use it in GitHub Desktop.
auto bearer activation scratch
diff --git a/drivers/ubloxmodem/gprs-context.c b/drivers/ubloxmodem/gprs-context.c
index dd9dba8..a5b3024 100644
--- a/drivers/ubloxmodem/gprs-context.c
+++ b/drivers/ubloxmodem/gprs-context.c
@@ -35,6 +35,7 @@
#include <ofono/log.h>
#include <ofono/modem.h>
#include <ofono/gprs-context.h>
+#include <ofono/gprs.h>
#include "gatchat.h"
#include "gatresult.h"
@@ -477,6 +478,13 @@ static void ublox_gprs_activate_primary(struct ofono_gprs_context *gc,
gcd->cb_data = data;
gcd->auth_method = ctx->auth_method;
+
+ if (ofono_gprs_context_get_type(gc) == OFONO_GPRS_CONTEXT_TYPE_IMS) {
+ DBG("here here");
+ ublox_post_activation(gc);
+ return;
+ }
+
memcpy(gcd->apn, ctx->apn, sizeof(ctx->apn));
if (strlen(ctx->username) && strlen(ctx->password)) {
@@ -526,7 +534,10 @@ static void cgev_notify(GAtResult *result, gpointer user_data)
struct gprs_context_data *gcd = ofono_gprs_context_get_data(gc);
GAtResultIter iter;
const char *event;
- gint cid;
+ unsigned int cid = 0;
+ char tmp[16] = {0};
+
+ DBG("");
g_at_result_iter_init(&iter, result);
@@ -536,16 +547,17 @@ static void cgev_notify(GAtResult *result, gpointer user_data)
if (!g_at_result_iter_next_unquoted_string(&iter, &event))
return;
- if (g_str_has_prefix(event, "NW DEACT") == FALSE)
- return;
+ if (g_str_has_prefix(event, "ME PDN ACT")) {
+ sscanf(event, "%s %s %s %u", tmp, tmp, tmp, &cid);
- if (!g_at_result_iter_skip_next(&iter))
- return;
+ DBG("cid %d activated", cid);
+ ofono_gprs_context_notify(gc, cid);
- if (!g_at_result_iter_next_number(&iter, &cid))
return;
-
- DBG("cid %d", cid);
+ } else if (g_str_has_prefix(event, "NW DEACT")) {
+ sscanf(event, "%s %s %s %u", tmp, tmp, tmp, &cid);
+ DBG("cid %d deactivated", cid);
+ }
if ((unsigned int) cid != gcd->active_context)
return;
diff --git a/include/gprs-context.h b/include/gprs-context.h
index 0090cc4..a739db3 100644
--- a/include/gprs-context.h
+++ b/include/gprs-context.h
@@ -97,6 +97,8 @@ void ofono_gprs_context_remove(struct ofono_gprs_context *gc);
void ofono_gprs_context_set_data(struct ofono_gprs_context *gc, void *data);
void *ofono_gprs_context_get_data(struct ofono_gprs_context *gc);
+void ofono_gprs_context_notify(struct ofono_gprs_context *gc, unsigned int cid);
+
struct ofono_modem *ofono_gprs_context_get_modem(struct ofono_gprs_context *gc);
void ofono_gprs_context_set_type(struct ofono_gprs_context *gc,
diff --git a/src/gprs.c b/src/gprs.c
index d9c0fe5..cef8611 100644
--- a/src/gprs.c
+++ b/src/gprs.c
@@ -283,12 +283,22 @@ static unsigned int gprs_cid_alloc(struct ofono_gprs *gprs)
return idmap_alloc(gprs->cid_map);
}
+static void gprs_cid_take(struct ofono_gprs *gprs, unsigned int id)
+{
+ idmap_take(gprs->cid_map, id);
+}
+
static void gprs_cid_release(struct ofono_gprs *gprs, unsigned int id)
{
idmap_put(gprs->cid_map, id);
}
-static gboolean assign_context(struct pri_context *ctx)
+static gboolean gprs_cid_taken(struct ofono_gprs *gprs, unsigned int id)
+{
+ return idmap_find(gprs->cid_map, id) != 0;
+}
+
+static gboolean assign_context(struct pri_context *ctx, int use_cid)
{
struct idmap *cidmap = ctx->gprs->cid_map;
GSList *l;
@@ -296,7 +306,12 @@ static gboolean assign_context(struct pri_context *ctx)
if (cidmap == NULL)
return FALSE;
- ctx->context.cid = gprs_cid_alloc(ctx->gprs);
+ if (use_cid > 0) {
+ gprs_cid_take(ctx->gprs, use_cid);
+ ctx->context.cid = use_cid;
+ } else
+ ctx->context.cid = gprs_cid_alloc(ctx->gprs);
+
if (ctx->context.cid == 0)
return FALSE;
@@ -1245,7 +1260,7 @@ static DBusMessage *pri_set_property(DBusConnection *conn,
if (ctx->gprs->flags & GPRS_FLAG_ATTACHING)
return __ofono_error_attach_in_progress(msg);
- if (value && assign_context(ctx) == FALSE)
+ if (value && assign_context(ctx, 0) == FALSE)
return __ofono_error_not_implemented(msg);
gc = ctx->context_driver;
@@ -1872,6 +1887,50 @@ static struct pri_context *add_context(struct ofono_gprs *gprs,
return context;
}
+void ofono_gprs_context_notify(struct ofono_gprs_context *gc, unsigned int cid)
+{
+ struct ofono_gprs *gprs = gc->gprs;
+ struct pri_context *ctx;
+ const char *path;
+ DBusMessage *signal;
+
+ if (gprs_cid_taken(gprs, cid))
+ return;
+
+ DBG("");
+
+ // TODO:
+ ctx = add_context(gprs, "auto", OFONO_GPRS_CONTEXT_TYPE_IMS);
+ if (ctx == NULL) {
+ ofono_error("Can't create auto context.");
+ return;
+ }
+
+ if (assign_context(ctx, cid) == FALSE) {
+ ofono_warn("Can't assign context to driver.");
+ release_context(ctx);
+ return;
+ }
+
+ path = __ofono_atom_get_path(gprs->atom);
+ signal = dbus_message_new_signal(path,
+ OFONO_CONNECTION_CONTEXT_INTERFACE,
+ "PropertyChanged");
+ if (signal == NULL)
+ // TODO
+ return;
+
+
+ ctx->pending = dbus_message_ref(signal);
+
+ gc = ctx->context_driver;
+ gc->type = OFONO_GPRS_CONTEXT_TYPE_IMS;
+ gc->driver->activate_primary(gc, &ctx->context,
+ pri_activate_callback, ctx);
+
+}
+
+
static void send_context_added_signal(struct ofono_gprs *gprs,
struct pri_context *context,
DBusConnection *conn)
diff --git a/src/idmap.c b/src/idmap.c
index c097eb4..3b72830 100644
--- a/src/idmap.c
+++ b/src/idmap.c
@@ -166,6 +166,19 @@ void idmap_take(struct idmap *idmap, unsigned int id)
idmap->bits[offset] |= 1UL << (bit % BITS_PER_LONG);
}
+int idmap_find(struct idmap *idmap, unsigned int id)
+{
+ unsigned int bit = id - idmap->min;
+ unsigned int offset;
+
+ if (bit >= idmap->size)
+ return 0;
+
+ offset = bit / BITS_PER_LONG;
+ return (idmap->bits[offset] & (1UL << (bit % BITS_PER_LONG))) != 0;
+
+}
+
/*
* Allocate the next bit skipping the ids up to and including last. If there
* is no free ids until the max id is encountered, the counter is wrapped back
diff --git a/src/idmap.h b/src/idmap.h
index ebda177..97a6f04 100644
--- a/src/idmap.h
+++ b/src/idmap.h
@@ -25,6 +25,7 @@ struct idmap *idmap_new(unsigned int size);
void idmap_free(struct idmap *idmap);
void idmap_put(struct idmap *idmap, unsigned int id);
void idmap_take(struct idmap *idmap, unsigned int id);
+int idmap_find(struct idmap *idmap, unsigned int id);
unsigned int idmap_alloc(struct idmap *idmap);
unsigned int idmap_alloc_next(struct idmap *idmap, unsigned int last);
struct idmap *idmap_new_from_range(unsigned int min, unsigned int max);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment