iface-modem-simple: wait for packet service 'attach' state in ConnectionStep
This commit is contained in:
committed by
Aleksander Morgado
parent
d008e437c3
commit
213cd81b3a
@@ -119,6 +119,7 @@ enum {
|
||||
PROP_MODEM_3GPP_5GS_NETWORK_SUPPORTED,
|
||||
PROP_MODEM_3GPP_IGNORED_FACILITY_LOCKS,
|
||||
PROP_MODEM_3GPP_INITIAL_EPS_BEARER,
|
||||
PROP_MODEM_3GPP_PACKET_SERVICE_STATE,
|
||||
PROP_MODEM_CDMA_CDMA1X_REGISTRATION_STATE,
|
||||
PROP_MODEM_CDMA_EVDO_REGISTRATION_STATE,
|
||||
PROP_MODEM_CDMA_CDMA1X_NETWORK_SUPPORTED,
|
||||
@@ -207,6 +208,7 @@ struct _MMBroadbandModemPrivate {
|
||||
GPtrArray *modem_3gpp_registration_regex;
|
||||
MMModem3gppFacility modem_3gpp_ignored_facility_locks;
|
||||
MMBaseBearer *modem_3gpp_initial_eps_bearer;
|
||||
MMModem3gppPacketServiceState modem_3gpp_packet_service_state;
|
||||
|
||||
/*<--- Modem 3GPP Profile Manager interface --->*/
|
||||
/* Properties */
|
||||
@@ -13079,6 +13081,9 @@ set_property (GObject *object,
|
||||
g_clear_object (&self->priv->modem_3gpp_initial_eps_bearer);
|
||||
self->priv->modem_3gpp_initial_eps_bearer = g_value_dup_object (value);
|
||||
break;
|
||||
case PROP_MODEM_3GPP_PACKET_SERVICE_STATE:
|
||||
self->priv->modem_3gpp_packet_service_state = g_value_get_enum (value);
|
||||
break;
|
||||
case PROP_MODEM_CDMA_CDMA1X_REGISTRATION_STATE:
|
||||
self->priv->modem_cdma_cdma1x_registration_state = g_value_get_enum (value);
|
||||
break;
|
||||
@@ -13229,6 +13234,9 @@ get_property (GObject *object,
|
||||
case PROP_MODEM_3GPP_INITIAL_EPS_BEARER:
|
||||
g_value_set_object (value, self->priv->modem_3gpp_initial_eps_bearer);
|
||||
break;
|
||||
case PROP_MODEM_3GPP_PACKET_SERVICE_STATE:
|
||||
g_value_set_enum (value, self->priv->modem_3gpp_packet_service_state);
|
||||
break;
|
||||
case PROP_MODEM_CDMA_CDMA1X_REGISTRATION_STATE:
|
||||
g_value_set_enum (value, self->priv->modem_cdma_cdma1x_registration_state);
|
||||
break;
|
||||
@@ -13308,6 +13316,7 @@ mm_broadband_modem_init (MMBroadbandModem *self)
|
||||
self->priv->modem_3gpp_eps_network_supported = FALSE;
|
||||
self->priv->modem_3gpp_5gs_network_supported = FALSE;
|
||||
self->priv->modem_3gpp_ignored_facility_locks = MM_MODEM_3GPP_FACILITY_NONE;
|
||||
self->priv->modem_3gpp_packet_service_state = MM_MODEM_3GPP_PACKET_SERVICE_STATE_UNKNOWN;
|
||||
self->priv->modem_cdma_cdma1x_registration_state = MM_MODEM_CDMA_REGISTRATION_STATE_UNKNOWN;
|
||||
self->priv->modem_cdma_evdo_registration_state = MM_MODEM_CDMA_REGISTRATION_STATE_UNKNOWN;
|
||||
self->priv->modem_cdma_cdma1x_network_supported = TRUE;
|
||||
@@ -13866,6 +13875,10 @@ mm_broadband_modem_class_init (MMBroadbandModemClass *klass)
|
||||
PROP_MODEM_3GPP_INITIAL_EPS_BEARER,
|
||||
MM_IFACE_MODEM_3GPP_INITIAL_EPS_BEARER);
|
||||
|
||||
g_object_class_override_property (object_class,
|
||||
PROP_MODEM_3GPP_PACKET_SERVICE_STATE,
|
||||
MM_IFACE_MODEM_3GPP_PACKET_SERVICE_STATE);
|
||||
|
||||
g_object_class_override_property (object_class,
|
||||
PROP_MODEM_CDMA_CDMA1X_REGISTRATION_STATE,
|
||||
MM_IFACE_MODEM_CDMA_CDMA1X_REGISTRATION_STATE);
|
||||
|
||||
@@ -11,6 +11,7 @@
|
||||
* GNU General Public License for more details:
|
||||
*
|
||||
* Copyright (C) 2011 - 2012 Google, Inc.
|
||||
* Copyright (c) 2022 Qualcomm Innovation Center, Inc.
|
||||
*/
|
||||
|
||||
#include <stdlib.h>
|
||||
@@ -105,6 +106,139 @@ get_private (MMIfaceModem3gpp *self)
|
||||
return priv;
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
/* Helper method to wait for a final packet service state */
|
||||
|
||||
typedef struct {
|
||||
MMModem3gppPacketServiceState final_state;
|
||||
gulong packet_service_state_changed_id;
|
||||
guint packet_service_state_changed_wait_id;
|
||||
} WaitForPacketServiceStateContext;
|
||||
|
||||
MMModem3gppPacketServiceState
|
||||
mm_iface_modem_3gpp_wait_for_packet_service_state_finish (MMIfaceModem3gpp *self,
|
||||
GAsyncResult *res,
|
||||
GError **error)
|
||||
{
|
||||
GError *inner_error = NULL;
|
||||
gssize value;
|
||||
|
||||
value = g_task_propagate_int (G_TASK (res), &inner_error);
|
||||
if (inner_error) {
|
||||
g_propagate_error (error, inner_error);
|
||||
return MM_MODEM_3GPP_PACKET_SERVICE_STATE_UNKNOWN;
|
||||
}
|
||||
return (MMModem3gppPacketServiceState)value;
|
||||
}
|
||||
|
||||
static void
|
||||
wait_for_packet_service_state_context_complete (GTask *task,
|
||||
MMModem3gppPacketServiceState state,
|
||||
GError *error)
|
||||
{
|
||||
MMIfaceModem3gpp *self;
|
||||
WaitForPacketServiceStateContext *ctx;
|
||||
|
||||
self = g_task_get_source_object (task);
|
||||
ctx = g_task_get_task_data (task);
|
||||
|
||||
if (ctx->packet_service_state_changed_id) {
|
||||
if (g_signal_handler_is_connected (self, ctx->packet_service_state_changed_id))
|
||||
g_signal_handler_disconnect (self, ctx->packet_service_state_changed_id);
|
||||
ctx->packet_service_state_changed_id = 0;
|
||||
}
|
||||
|
||||
if (ctx->packet_service_state_changed_wait_id) {
|
||||
g_source_remove (ctx->packet_service_state_changed_wait_id);
|
||||
ctx->packet_service_state_changed_wait_id = 0;
|
||||
}
|
||||
|
||||
if (error)
|
||||
g_task_return_error (task, error);
|
||||
else
|
||||
g_task_return_int (task, state);
|
||||
|
||||
g_object_unref (task);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
packet_service_state_changed_wait_expired (GTask *task)
|
||||
{
|
||||
GError *error;
|
||||
|
||||
error = g_error_new (MM_CORE_ERROR,
|
||||
MM_CORE_ERROR_RETRY,
|
||||
"Too much time waiting to get to a final packet service state");
|
||||
wait_for_packet_service_state_context_complete (task, MM_MODEM_3GPP_PACKET_SERVICE_STATE_UNKNOWN, error);
|
||||
return G_SOURCE_REMOVE;
|
||||
}
|
||||
|
||||
static void
|
||||
packet_service_state_changed (MMIfaceModem3gpp *self,
|
||||
GParamSpec *spec,
|
||||
GTask *task)
|
||||
{
|
||||
WaitForPacketServiceStateContext *ctx;
|
||||
MMModem3gppPacketServiceState state = MM_MODEM_3GPP_PACKET_SERVICE_STATE_UNKNOWN;
|
||||
|
||||
g_object_get (self,
|
||||
MM_IFACE_MODEM_3GPP_PACKET_SERVICE_STATE, &state,
|
||||
NULL);
|
||||
|
||||
ctx = g_task_get_task_data (task);
|
||||
|
||||
/* If we want a specific final state and this is not the one we were
|
||||
* looking for, then skip */
|
||||
if ((ctx->final_state != MM_MODEM_3GPP_PACKET_SERVICE_STATE_UNKNOWN) &&
|
||||
(state != MM_MODEM_3GPP_PACKET_SERVICE_STATE_UNKNOWN) &&
|
||||
(state != ctx->final_state))
|
||||
return;
|
||||
|
||||
/* Done! */
|
||||
wait_for_packet_service_state_context_complete (task, state, NULL);
|
||||
}
|
||||
|
||||
void
|
||||
mm_iface_modem_3gpp_wait_for_packet_service_state (MMIfaceModem3gpp *self,
|
||||
MMModem3gppPacketServiceState final_state,
|
||||
GAsyncReadyCallback callback,
|
||||
gpointer user_data)
|
||||
{
|
||||
MMModem3gppPacketServiceState state = MM_MODEM_3GPP_PACKET_SERVICE_STATE_UNKNOWN;
|
||||
WaitForPacketServiceStateContext *ctx;
|
||||
GTask *task;
|
||||
|
||||
task = g_task_new (self, NULL, callback, user_data);
|
||||
|
||||
g_object_get (self,
|
||||
MM_IFACE_MODEM_3GPP_PACKET_SERVICE_STATE, &state,
|
||||
NULL);
|
||||
|
||||
/* Is this the state we actually wanted? */
|
||||
if (final_state == MM_MODEM_3GPP_PACKET_SERVICE_STATE_UNKNOWN ||
|
||||
(state != MM_MODEM_3GPP_PACKET_SERVICE_STATE_UNKNOWN && state == final_state)) {
|
||||
g_task_return_int (task, state);
|
||||
g_object_unref (task);
|
||||
return;
|
||||
}
|
||||
|
||||
/* Otherwise, we'll need to wait for the exact one we want */
|
||||
ctx = g_new0 (WaitForPacketServiceStateContext, 1);
|
||||
ctx->final_state = final_state;
|
||||
|
||||
g_task_set_task_data (task, ctx, g_free);
|
||||
|
||||
/* Want to get notified when packet service state changes */
|
||||
ctx->packet_service_state_changed_id = g_signal_connect (self,
|
||||
"notify::" MM_IFACE_MODEM_3GPP_PACKET_SERVICE_STATE,
|
||||
G_CALLBACK (packet_service_state_changed),
|
||||
task);
|
||||
/* But we don't want to wait forever */
|
||||
ctx->packet_service_state_changed_wait_id = g_timeout_add_seconds (10,
|
||||
(GSourceFunc)packet_service_state_changed_wait_expired,
|
||||
task);
|
||||
}
|
||||
|
||||
/*****************************************************************************/
|
||||
|
||||
void
|
||||
@@ -3338,6 +3472,11 @@ mm_iface_modem_3gpp_initialize (MMIfaceModem3gpp *self,
|
||||
skeleton, "registration-state",
|
||||
G_BINDING_DEFAULT | G_BINDING_SYNC_CREATE);
|
||||
|
||||
/* Bind our packet service state property */
|
||||
g_object_bind_property (self, MM_IFACE_MODEM_3GPP_PACKET_SERVICE_STATE,
|
||||
skeleton, "packet-service-state",
|
||||
G_BINDING_DEFAULT | G_BINDING_SYNC_CREATE);
|
||||
|
||||
g_object_set (self,
|
||||
MM_IFACE_MODEM_3GPP_DBUS_SKELETON, skeleton,
|
||||
NULL);
|
||||
@@ -3441,6 +3580,15 @@ iface_modem_3gpp_init (gpointer g_iface)
|
||||
MM_TYPE_BASE_BEARER,
|
||||
G_PARAM_READWRITE));
|
||||
|
||||
g_object_interface_install_property
|
||||
(g_iface,
|
||||
g_param_spec_enum (MM_IFACE_MODEM_3GPP_PACKET_SERVICE_STATE,
|
||||
"PacketServiceState",
|
||||
"Packet service state of the modem",
|
||||
MM_TYPE_MODEM_3GPP_PACKET_SERVICE_STATE,
|
||||
MM_MODEM_3GPP_PACKET_SERVICE_STATE_UNKNOWN,
|
||||
G_PARAM_READWRITE));
|
||||
|
||||
initialized = TRUE;
|
||||
}
|
||||
|
||||
|
||||
@@ -11,6 +11,7 @@
|
||||
* GNU General Public License for more details:
|
||||
*
|
||||
* Copyright (C) 2011-2012 Google, Inc.
|
||||
* Copyright (c) 2022 Qualcomm Innovation Center, Inc.
|
||||
*/
|
||||
|
||||
#ifndef MM_IFACE_MODEM_3GPP_H
|
||||
@@ -37,6 +38,7 @@
|
||||
#define MM_IFACE_MODEM_3GPP_5GS_NETWORK_SUPPORTED "iface-modem-3gpp-5gs-network-supported"
|
||||
#define MM_IFACE_MODEM_3GPP_IGNORED_FACILITY_LOCKS "iface-modem-3gpp-ignored-facility-locks"
|
||||
#define MM_IFACE_MODEM_3GPP_INITIAL_EPS_BEARER "iface-modem-3gpp-initial-eps-bearer"
|
||||
#define MM_IFACE_MODEM_3GPP_PACKET_SERVICE_STATE "iface-modem-3gpp-packet-service-state"
|
||||
|
||||
#define MM_IFACE_MODEM_3GPP_ALL_ACCESS_TECHNOLOGIES_MASK \
|
||||
(MM_MODEM_ACCESS_TECHNOLOGY_GSM | \
|
||||
@@ -379,6 +381,14 @@ gboolean mm_iface_modem_3gpp_reregister_in_network_finish (MMIfaceModem3gpp
|
||||
GAsyncResult *res,
|
||||
GError **error);
|
||||
|
||||
void mm_iface_modem_3gpp_wait_for_packet_service_state (MMIfaceModem3gpp *self,
|
||||
MMModem3gppPacketServiceState final_state,
|
||||
GAsyncReadyCallback callback,
|
||||
gpointer user_data);
|
||||
MMModem3gppPacketServiceState mm_iface_modem_3gpp_wait_for_packet_service_state_finish (MMIfaceModem3gpp *self,
|
||||
GAsyncResult *res,
|
||||
GError **error);
|
||||
|
||||
/* Bind properties for simple GetStatus() */
|
||||
void mm_iface_modem_3gpp_bind_simple_status (MMIfaceModem3gpp *self,
|
||||
MMSimpleStatus *status);
|
||||
|
||||
@@ -13,6 +13,7 @@
|
||||
* Copyright (C) 2009 Novell, Inc.
|
||||
* Copyright (C) 2009 - 2011 Red Hat, Inc.
|
||||
* Copyright (C) 2011 Google, Inc.
|
||||
* Copyright (c) 2022 Qualcomm Innovation Center, Inc.
|
||||
*/
|
||||
|
||||
#include <ModemManager.h>
|
||||
@@ -217,6 +218,7 @@ typedef enum {
|
||||
CONNECTION_STEP_WAIT_FOR_ENABLED,
|
||||
CONNECTION_STEP_WAIT_AFTER_ENABLED,
|
||||
CONNECTION_STEP_REGISTER,
|
||||
CONNECTION_STEP_PACKET_SERVICE_ATTACH,
|
||||
CONNECTION_STEP_BEARER,
|
||||
CONNECTION_STEP_CONNECT,
|
||||
CONNECTION_STEP_LAST
|
||||
@@ -314,6 +316,24 @@ create_bearer_ready (MMIfaceModem *self,
|
||||
connection_step (ctx);
|
||||
}
|
||||
|
||||
static void
|
||||
wait_for_packet_service_attach_ready (MMIfaceModem3gpp *self,
|
||||
GAsyncResult *res,
|
||||
ConnectionContext *ctx)
|
||||
{
|
||||
GError *error = NULL;
|
||||
|
||||
if (!mm_iface_modem_3gpp_wait_for_packet_service_state_finish (self, res, &error)) {
|
||||
g_dbus_method_invocation_take_error (ctx->invocation, error);
|
||||
connection_context_free (ctx);
|
||||
return;
|
||||
}
|
||||
|
||||
/* Packet service attached now! */
|
||||
ctx->step++;
|
||||
connection_step (ctx);
|
||||
}
|
||||
|
||||
static void
|
||||
register_in_3gpp_or_cdma_network_ready (MMIfaceModemSimple *self,
|
||||
GAsyncResult *res,
|
||||
@@ -601,6 +621,15 @@ connection_step (ConnectionContext *ctx)
|
||||
ctx->step++;
|
||||
/* fall through */
|
||||
|
||||
case CONNECTION_STEP_PACKET_SERVICE_ATTACH:
|
||||
mm_obj_info (ctx->self, "simple connect state (%d/%d): wait to get packet service state attached",
|
||||
ctx->step, CONNECTION_STEP_LAST);
|
||||
mm_iface_modem_3gpp_wait_for_packet_service_state (MM_IFACE_MODEM_3GPP (ctx->self),
|
||||
MM_MODEM_3GPP_PACKET_SERVICE_STATE_ATTACHED, /* attached state */
|
||||
(GAsyncReadyCallback)wait_for_packet_service_attach_ready,
|
||||
ctx);
|
||||
return;
|
||||
|
||||
case CONNECTION_STEP_BEARER: {
|
||||
g_autoptr(MMBearerProperties) bearer_properties = NULL;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user