> > I’m trying to use ModemManager 1.8.2 with a Verizon LTE Cat-M1 modem.
Aleksander wrote this for my team for this very case. I've re-based it to 1.8.2 so it should go on clean. We should work on the new API at some point... I really think the patch here is great to be honest. Again we are using it not just for Vzw but also in Asia where a few carrier's require PDP #1. >From da8bc6feb036cfdcd5db8280f00565c82685d794 Mon Sep 17 00:00:00 2001 From: Aleksander Morgado <aleksan...@aleksander.es> Date: Fri, 12 May 2017 18:24:13 +0200 Subject: [PATCH 1/1] allow specifying the PDP CID to use Some operators, most notably Verizon, require connection to be performed through a specific PDP context. This API update allows the user to specify the PDP cid via a new 'pdp-cid' parameter given in either the Simple.Connect() or the Modem.CreateBearer() methods. Signed-off-by: mstanger <matthew_stan...@trimble.com> --- cli/mmcli-bearer.c | 9 ++++ docs/reference/libmm-glib/libmm-glib-sections.txt | 4 ++ .../org.freedesktop.ModemManager1.Modem.xml | 2 + libmm-glib/mm-bearer-properties.c | 59 +++++++++++++++++++++- libmm-glib/mm-bearer-properties.h | 3 ++ libmm-glib/mm-simple-connect-properties.c | 34 +++++++++++++ libmm-glib/mm-simple-connect-properties.h | 3 ++ src/mm-broadband-bearer.c | 41 ++++++++++----- src/mm-iface-modem-simple.c | 13 +++-- 9 files changed, 150 insertions(+), 18 deletions(-) diff --git a/cli/mmcli-bearer.c b/cli/mmcli-bearer.c index cd9ecca..daa8614 100644 --- a/cli/mmcli-bearer.c +++ b/cli/mmcli-bearer.c @@ -163,11 +163,18 @@ print_bearer_info (MMBearer *bearer) if (properties) { gchar *ip_family_str; + gchar *pdp_cid_str = NULL; + guint pdp_cid; ip_family_str = (mm_bearer_ip_family_build_string_from_mask ( mm_bearer_properties_get_ip_type (properties))); + + if ((pdp_cid = mm_bearer_properties_get_pdp_cid (properties)) != 0) + pdp_cid_str = g_strdup_printf ("%u", pdp_cid); + g_print (" -------------------------\n" " Properties | apn: '%s'\n" + " | PDP CID: '%s'\n" " | roaming: '%s'\n" " | IP type: '%s'\n" " | user: '%s'\n" @@ -175,6 +182,7 @@ print_bearer_info (MMBearer *bearer) " | number: '%s'\n" " | Rm protocol: '%s'\n", VALIDATE_NONE (mm_bearer_properties_get_apn (properties)), + VALIDATE_NONE (pdp_cid_str), mm_bearer_properties_get_allow_roaming (properties) ? "allowed" : "forbidden", VALIDATE_UNKNOWN (ip_family_str), VALIDATE_NONE (mm_bearer_properties_get_user (properties)), @@ -183,6 +191,7 @@ print_bearer_info (MMBearer *bearer) VALIDATE_UNKNOWN (mm_modem_cdma_rm_protocol_get_string ( mm_bearer_properties_get_rm_protocol (properties)))); g_free (ip_family_str); + g_free (pdp_cid_str); } /* IPv4 */ diff --git a/docs/reference/libmm-glib/libmm-glib-sections.txt b/docs/reference/libmm-glib/libmm-glib-sections.txt index 46f2d92..077e7ee 100644 --- a/docs/reference/libmm-glib/libmm-glib-sections.txt +++ b/docs/reference/libmm-glib/libmm-glib-sections.txt @@ -779,6 +779,8 @@ mm_simple_connect_properties_get_operator_id mm_simple_connect_properties_set_operator_id mm_simple_connect_properties_get_apn mm_simple_connect_properties_set_apn +mm_simple_connect_properties_get_pdp_cid +mm_simple_connect_properties_set_pdp_cid mm_simple_connect_properties_get_allowed_auth mm_simple_connect_properties_set_allowed_auth mm_simple_connect_properties_get_user @@ -1064,6 +1066,8 @@ mm_bearer_properties_new <SUBSECTION GettersSetters> mm_bearer_properties_get_apn mm_bearer_properties_set_apn +mm_bearer_properties_get_pdp_cid +mm_bearer_properties_set_pdp_cid mm_bearer_properties_get_allowed_auth mm_bearer_properties_set_allowed_auth mm_bearer_properties_get_user diff --git a/introspection/org.freedesktop.ModemManager1.Modem.xml b/introspection/org.freedesktop.ModemManager1.Modem.xml index a5a236c..23c14ed 100644 --- a/introspection/org.freedesktop.ModemManager1.Modem.xml +++ b/introspection/org.freedesktop.ModemManager1.Modem.xml @@ -61,6 +61,8 @@ <variablelist> <varlistentry><term><literal>"apn"</literal></term> <listitem><para>Access Point Name, given as a string value (signature <literal>"s"</literal>). Required in 3GPP.</para></listitem></varlistentry> + <varlistentry><term><literal>"pdp-cid"</literal></term> + <listitem><para>PDP context identifier, given as an unsigned 32-bit integer value (signature <literal>"u"</literal>). Optional in 3GPP.</para></listitem></varlistentry> <varlistentry><term><literal>"ip-type"</literal></term> <listitem><para>Addressing type, given as a <link linkend="MMBearerIpFamily">MMBearerIpFamily</link> value (signature <literal>"u"</literal>). Optional in 3GPP and CDMA.</para></listitem></varlistentry> <varlistentry><term><literal>"allowed-auth"</literal></term> diff --git a/libmm-glib/mm-bearer-properties.c b/libmm-glib/mm-bearer-properties.c index c87068f..8e54f10 100644 --- a/libmm-glib/mm-bearer-properties.c +++ b/libmm-glib/mm-bearer-properties.c @@ -34,6 +34,7 @@ G_DEFINE_TYPE (MMBearerProperties, mm_bearer_properties, G_TYPE_OBJECT); #define PROPERTY_APN "apn" +#define PROPERTY_PDP_CID "pdp-cid" #define PROPERTY_ALLOWED_AUTH "allowed-auth" #define PROPERTY_USER "user" #define PROPERTY_PASSWORD "password" @@ -45,6 +46,8 @@ G_DEFINE_TYPE (MMBearerProperties, mm_bearer_properties, G_TYPE_OBJECT); struct _MMBearerPropertiesPrivate { /* APN */ gchar *apn; + /* PDP CID */ + guint pdp_cid; /* IP type */ MMBearerIpFamily ip_type; /* Allowed auth */ @@ -100,6 +103,40 @@ mm_bearer_properties_get_apn (MMBearerProperties *self) /*****************************************************************************/ /** + * mm_bearer_properties_set_pdp_cid: + * @self: a #MMBearerProperties. + * @pdp_cid: PDP context ID. + * + * Sets the PDP context ID to use in the connection attempt. + */ +void +mm_bearer_properties_set_pdp_cid (MMBearerProperties *self, + guint pdp_cid) +{ + g_return_if_fail (MM_IS_BEARER_PROPERTIES (self)); + + self->priv->pdp_cid = pdp_cid; +} + +/** + * mm_bearer_properties_get_pdp_cid: + * @self: a #MMBearerProperties. + * + * Gets the PDP context ID to use in the connection attempt. + * + * Returns: the context number, or 0 if not set. + */ +guint +mm_bearer_properties_get_pdp_cid (MMBearerProperties *self) +{ + g_return_val_if_fail (MM_IS_BEARER_PROPERTIES (self), 0); + + return self->priv->pdp_cid; +} + +/*****************************************************************************/ + +/** * mm_bearer_properties_set_allowed_auth: * @self: a #MMBearerProperties. * @allowed_auth: a bitmask of #MMBearerAllowedAuth values. %MM_BEARER_ALLOWED_AUTH_UNKNOWN may be given to request the modem-default method. @@ -361,6 +398,12 @@ mm_bearer_properties_get_dictionary (MMBearerProperties *self) PROPERTY_APN, g_variant_new_string (self->priv->apn)); + if (self->priv->pdp_cid) + g_variant_builder_add (&builder, + "{sv}", + PROPERTY_PDP_CID, + g_variant_new_uint32 (self->priv->pdp_cid)); + if (self->priv->allowed_auth != MM_BEARER_ALLOWED_AUTH_UNKNOWN) g_variant_builder_add (&builder, "{sv}", @@ -428,7 +471,16 @@ mm_bearer_properties_consume_string (MMBearerProperties *self, if (g_str_equal (key, PROPERTY_APN)) mm_bearer_properties_set_apn (self, value); - else if (g_str_equal (key, PROPERTY_ALLOWED_AUTH)) { + else if (g_str_equal (key, PROPERTY_PDP_CID)) { + guint aux; + + if (!mm_get_uint_from_str (value, &aux)) { + g_set_error (error, MM_CORE_ERROR, MM_CORE_ERROR_FAILED, + "Invalid PDP CID given: %s", value); + return FALSE; + } + mm_bearer_properties_set_pdp_cid (self, aux); + }else if (g_str_equal (key, PROPERTY_ALLOWED_AUTH)) { GError *inner_error = NULL; MMBearerAllowedAuth allowed_auth; @@ -548,6 +600,10 @@ mm_bearer_properties_consume_variant (MMBearerProperties *properties, mm_bearer_properties_set_apn ( properties, g_variant_get_string (value, NULL)); + else if (g_str_equal (key, PROPERTY_PDP_CID)) + mm_bearer_properties_set_pdp_cid ( + properties, + g_variant_get_uint32 (value)); else if (g_str_equal (key, PROPERTY_ALLOWED_AUTH)) mm_bearer_properties_set_allowed_auth ( properties, @@ -664,6 +720,7 @@ mm_bearer_properties_cmp (MMBearerProperties *a, MMBearerProperties *b) { return ((!g_strcmp0 (a->priv->apn, b->priv->apn)) && + (a->priv->pdp_cid == b->priv->pdp_cid) && (a->priv->ip_type == b->priv->ip_type) && (!g_strcmp0 (a->priv->number, b->priv->number)) && (a->priv->allowed_auth == b->priv->allowed_auth) && diff --git a/libmm-glib/mm-bearer-properties.h b/libmm-glib/mm-bearer-properties.h index 361c867..6fc1347 100644 --- a/libmm-glib/mm-bearer-properties.h +++ b/libmm-glib/mm-bearer-properties.h @@ -59,6 +59,8 @@ MMBearerProperties *mm_bearer_properties_new (void); void mm_bearer_properties_set_apn (MMBearerProperties *self, const gchar *apn); +void mm_bearer_properties_set_pdp_cid (MMBearerProperties *self, + guint pdp_cid); void mm_bearer_properties_set_allowed_auth (MMBearerProperties *self, MMBearerAllowedAuth allowed_auth); void mm_bearer_properties_set_user (MMBearerProperties *self, @@ -75,6 +77,7 @@ void mm_bearer_properties_set_rm_protocol (MMBearerProperties *self, MMModemCdmaRmProtocol protocol); const gchar *mm_bearer_properties_get_apn (MMBearerProperties *self); +guint mm_bearer_properties_get_pdp_cid (MMBearerProperties *self); MMBearerAllowedAuth mm_bearer_properties_get_allowed_auth (MMBearerProperties *self); const gchar *mm_bearer_properties_get_user (MMBearerProperties *self); const gchar *mm_bearer_properties_get_password (MMBearerProperties *self); diff --git a/libmm-glib/mm-simple-connect-properties.c b/libmm-glib/mm-simple-connect-properties.c index 200b7c3..c696f50 100644 --- a/libmm-glib/mm-simple-connect-properties.c +++ b/libmm-glib/mm-simple-connect-properties.c @@ -153,6 +153,40 @@ mm_simple_connect_properties_get_apn (MMSimpleConnectProperties *self) /*****************************************************************************/ /** + * mm_simple_connect_properties_set_pdp_cid: + * @self: a #MMSimpleConnectProperties. + * @pdp_cid: PDP context ID. + * + * Sets the PDP context ID to use in the connection attempt. + */ +void +mm_simple_connect_properties_set_pdp_cid (MMSimpleConnectProperties *self, + guint pdp_cid) +{ + g_return_if_fail (MM_IS_SIMPLE_CONNECT_PROPERTIES (self)); + + mm_bearer_properties_set_pdp_cid (self->priv->bearer_properties, pdp_cid); +} + +/** + * mm_simple_connect_properties_get_pdp_cid: + * @self: a #MMSimpleConnectProperties. + * + * Gets the PDP context ID to use in the connection attempt. + * + * Returns: the context number, or 0 if not set. + */ +guint +mm_simple_connect_properties_get_pdp_cid (MMSimpleConnectProperties *self) +{ + g_return_val_if_fail (MM_IS_SIMPLE_CONNECT_PROPERTIES (self), 0); + + return mm_bearer_properties_get_pdp_cid (self->priv->bearer_properties); +} + +/*****************************************************************************/ + +/** * mm_simple_connect_properties_set_allowed_auth: * @self: a #MMSimpleConnectProperties. * @allowed_auth: a bitmask of #MMBearerAllowedAuth values. %MM_BEARER_ALLOWED_AUTH_UNKNOWN may be given to request the modem-default method. diff --git a/libmm-glib/mm-simple-connect-properties.h b/libmm-glib/mm-simple-connect-properties.h index 3167db0..5378c5e 100644 --- a/libmm-glib/mm-simple-connect-properties.h +++ b/libmm-glib/mm-simple-connect-properties.h @@ -65,6 +65,8 @@ void mm_simple_connect_properties_set_operator_id (MMSimpleConnectProperties * const gchar *operator_id); void mm_simple_connect_properties_set_apn (MMSimpleConnectProperties *self, const gchar *apn); +void mm_simple_connect_properties_set_pdp_cid (MMSimpleConnectProperties *self, + guint pdp_cid); void mm_simple_connect_properties_set_allowed_auth (MMSimpleConnectProperties *self, MMBearerAllowedAuth allowed_auth); void mm_simple_connect_properties_set_user (MMSimpleConnectProperties *self, @@ -81,6 +83,7 @@ void mm_simple_connect_properties_set_number (MMSimpleConnectProperties * const gchar *mm_simple_connect_properties_get_pin (MMSimpleConnectProperties *self); const gchar *mm_simple_connect_properties_get_operator_id (MMSimpleConnectProperties *self); const gchar *mm_simple_connect_properties_get_apn (MMSimpleConnectProperties *self); +guint mm_simple_connect_properties_get_pdp_cid (MMSimpleConnectProperties *self); MMBearerAllowedAuth mm_simple_connect_properties_get_allowed_auth (MMSimpleConnectProperties *self); const gchar *mm_simple_connect_properties_get_user (MMSimpleConnectProperties *self); const gchar *mm_simple_connect_properties_get_password (MMSimpleConnectProperties *self); diff --git a/src/mm-broadband-bearer.c b/src/mm-broadband-bearer.c index ac70173..de4fa72 100644 --- a/src/mm-broadband-bearer.c +++ b/src/mm-broadband-bearer.c @@ -732,25 +732,17 @@ initialize_pdp_context_ready (MMBaseModem *modem, } static void -find_cid_ready (MMBaseModem *modem, - GAsyncResult *res, - GTask *task) +initialize_pdp_context (GTask *task) { gchar *apn; gchar *command; - GError *error = NULL; const gchar *pdp_type; CidSelection3gppContext *ctx; ctx = (CidSelection3gppContext *) g_task_get_task_data (task); - mm_base_modem_at_sequence_full_finish (modem, res, NULL, &error); - if (error) { - mm_warn ("Couldn't find best CID to use: '%s'", error->message); - g_task_return_error (task, error); - g_object_unref (task); - return; - } + /* If no error reported, we must have a valid CID to be used */ + g_assert (ctx->cid != 0); /* Validate requested PDP type */ pdp_type = mm_3gpp_get_pdp_type_from_ip_family (ctx->ip_family); @@ -766,9 +758,6 @@ find_cid_ready (MMBaseModem *modem, return; } - /* If no error reported, we must have a valid CID to be used */ - g_assert (ctx->cid != 0); - /* If there's already a PDP context defined, just use it */ if (ctx->use_existing_cid) { g_task_return_int (task, (gssize) ctx->cid); @@ -792,6 +781,24 @@ find_cid_ready (MMBaseModem *modem, g_free (command); } +static void +find_cid_ready (MMBaseModem *modem, + GAsyncResult *res, + GTask *task) +{ + GError *error = NULL; + + mm_base_modem_at_sequence_full_finish (modem, res, NULL, &error); + if (error) { + mm_warn ("Couldn't find best CID to use: '%s'", error->message); + g_task_return_error (task, error); + g_object_unref (task); + return; + } + + initialize_pdp_context (task); +} + static gboolean parse_cid_range (MMBaseModem *modem, CidSelection3gppContext *ctx, @@ -998,6 +1005,12 @@ cid_selection_3gpp (MMBroadbandBearer *self, task = g_task_new (self, cancellable, callback, user_data); g_task_set_task_data (task, ctx, (GDestroyNotify) cid_selection_3gpp_context_free); + if ((ctx->cid = mm_bearer_properties_get_pdp_cid (mm_base_bearer_peek_config (MM_BASE_BEARER (ctx->self)))) != 0) { + mm_dbg ("Explicit CID requested by the user: %u", ctx->cid); + initialize_pdp_context (task); + return; + } + mm_dbg ("Looking for best CID..."); mm_base_modem_at_sequence_full (ctx->modem, ctx->primary, diff --git a/src/mm-iface-modem-simple.c b/src/mm-iface-modem-simple.c index a16adb1..59d980e 100644 --- a/src/mm-iface-modem-simple.c +++ b/src/mm-iface-modem-simple.c @@ -651,9 +651,10 @@ connect_auth_ready (MMBaseModem *self, /* Log about all the parameters being used for the simple connect */ { - MMBearerAllowedAuth allowed_auth; - gchar *str; - MMBearerIpFamily ip_family; + MMBearerAllowedAuth allowed_auth; + gchar *str; + MMBearerIpFamily ip_family; + guint aux_uint; #define VALIDATE_UNSPECIFIED(str) (str ? str : "unspecified") @@ -665,6 +666,12 @@ connect_auth_ready (MMBaseModem *self, mm_dbg (" APN: %s", VALIDATE_UNSPECIFIED (mm_simple_connect_properties_get_apn (ctx->properties))); + aux_uint = mm_simple_connect_properties_get_pdp_cid (ctx->properties); + if (aux_uint) + mm_dbg (" PDP CID: %u", aux_uint); + else + mm_dbg (" PDP CID: unspecified"); + ip_family = mm_simple_connect_properties_get_ip_type (ctx->properties); if (ip_family != MM_BEARER_IP_FAMILY_NONE) { str = mm_bearer_ip_family_build_string_from_mask (ip_family); -- 1.9.1 On Fri, Mar 8, 2019 at 11:40 AM Aleksander Morgado <aleksan...@aleksander.es> wrote: > > I’m trying to use ModemManager 1.8.2 with a Verizon LTE Cat-M1 modem. > Verizon requires using PDP context #3 for the internet connection. I read > the thread from 2017 ( > https://lists.freedesktop.org/archives/modemmanager-devel/2017-May/004663.html) > in which a patch was proposed to handle this case in ModemManager, but saw > that the thread ended with a plan to develop a new API for managing > profiles instead of that patch. > > > > > > > > But I haven’t been able to find this new API, and it doesn’t look like > the original patch was applied either. Is this profile management API > available in 1.8.2, or in a newer version? How do I force ModemManager to > use PDP context #3 for the internet connection? > > > > Right now, you could manually create the PDP context with the settings > you want, and MM should re-use the already created context if the > settings requested match the existing ones. > > We should work on the new API at some point... > > -- > Aleksander > https://aleksander.es > _______________________________________________ > ModemManager-devel mailing list > ModemManager-devel@lists.freedesktop.org > https://lists.freedesktop.org/mailman/listinfo/modemmanager-devel
_______________________________________________ ModemManager-devel mailing list ModemManager-devel@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/modemmanager-devel