core: fatal errors in iface initializations force the modem into a FAILED state

Modems which end up being found unusable (e.g. no SIM, fatal SIM error, no
capabilities) will be exposed in DBus, but just with the Modem interface and
in a FAILED state which allows no actions.
This commit is contained in:
Aleksander Morgado
2012-03-30 11:06:32 +02:00
parent 3b366118b6
commit 7518772d4b
7 changed files with 223 additions and 229 deletions

View File

@@ -92,6 +92,7 @@ typedef enum { /*< underscore_name=mm_modem_lock >*/
/** /**
* MMModemState: * MMModemState:
* @MM_MODEM_STATE_FAILED: The modem is unusable.
* @MM_MODEM_STATE_UNKNOWN: State unknown or not reportable. * @MM_MODEM_STATE_UNKNOWN: State unknown or not reportable.
* @MM_MODEM_STATE_INITIALIZING: The modem is currently being initialized. * @MM_MODEM_STATE_INITIALIZING: The modem is currently being initialized.
* @MM_MODEM_STATE_LOCKED: The modem needs to be unlocked. * @MM_MODEM_STATE_LOCKED: The modem needs to be unlocked.
@@ -108,6 +109,7 @@ typedef enum { /*< underscore_name=mm_modem_lock >*/
* Enumeration of possible modem states. * Enumeration of possible modem states.
*/ */
typedef enum { /*< underscore_name=mm_modem_state >*/ typedef enum { /*< underscore_name=mm_modem_state >*/
MM_MODEM_STATE_FAILED = -1,
MM_MODEM_STATE_UNKNOWN = 0, MM_MODEM_STATE_UNKNOWN = 0,
MM_MODEM_STATE_INITIALIZING = 1, MM_MODEM_STATE_INITIALIZING = 1,
MM_MODEM_STATE_LOCKED = 2, MM_MODEM_STATE_LOCKED = 2,

View File

@@ -172,8 +172,8 @@
The modem's state (see #org.freedesktop.ModemManager1.Modem:State) changed. The modem's state (see #org.freedesktop.ModemManager1.Modem:State) changed.
--> -->
<signal name="StateChanged"> <signal name="StateChanged">
<arg name="old" type="u" /> <arg name="old" type="i" />
<arg name="new" type="u" /> <arg name="new" type="i" />
<arg name="reason" type="u" /> <arg name="reason" type="u" />
</signal> </signal>
@@ -333,7 +333,7 @@
<link linkend="MM-MODEM-STATE-UNKNOWN:CAPS"><constant>MM_MODEM_STATE_UNKNOWN</constant></link> <link linkend="MM-MODEM-STATE-UNKNOWN:CAPS"><constant>MM_MODEM_STATE_UNKNOWN</constant></link>
will be reported. will be reported.
--> -->
<property name="State" type="u" access="read" /> <property name="State" type="i" access="read" />
<!-- <!--
AccessTechnologies: AccessTechnologies:

View File

@@ -565,22 +565,18 @@ initialize_ready (MMBaseModem *self,
if (!mm_base_modem_initialize_finish (self, res, &error)) { if (!mm_base_modem_initialize_finish (self, res, &error)) {
/* Wrong state is returned when modem is found locked */ /* Wrong state is returned when modem is found locked */
if (g_error_matches (error, if (g_error_matches (error, MM_CORE_ERROR, MM_CORE_ERROR_WRONG_STATE))
MM_CORE_ERROR,
MM_CORE_ERROR_WRONG_STATE)) {
mm_dbg ("Couldn't finish initialization in the current state: '%s'", mm_dbg ("Couldn't finish initialization in the current state: '%s'",
error->message); error->message);
mm_base_modem_set_valid (self, TRUE); else
} else {
mm_warn ("couldn't initialize the modem: '%s'", error->message); mm_warn ("couldn't initialize the modem: '%s'", error->message);
mm_base_modem_set_valid (self, FALSE);
}
g_error_free (error); g_error_free (error);
return; } else
}
mm_dbg ("modem properly initialized"); mm_dbg ("modem properly initialized");
/* Even with initialization errors, we do set the state to valid, so
* that the modem gets exported and the failure notified to the user.
*/
mm_base_modem_set_valid (self, TRUE); mm_base_modem_set_valid (self, TRUE);
} }

View File

@@ -6070,7 +6070,8 @@ disable (MMBaseModem *self,
/* Check state before launching modem disabling */ /* Check state before launching modem disabling */
switch (MM_BROADBAND_MODEM (self)->priv->modem_state) { switch (MM_BROADBAND_MODEM (self)->priv->modem_state) {
case MM_MODEM_STATE_UNKNOWN: case MM_MODEM_STATE_UNKNOWN:
/* We should never have a UNKNOWN->DISABLED transition requested by case MM_MODEM_STATE_FAILED:
/* We should never have a UNKNOWN|FAILED->DISABLED transition requested by
* the user. */ * the user. */
g_assert_not_reached (); g_assert_not_reached ();
break; break;
@@ -6078,7 +6079,7 @@ disable (MMBaseModem *self,
case MM_MODEM_STATE_INITIALIZING: case MM_MODEM_STATE_INITIALIZING:
case MM_MODEM_STATE_LOCKED: case MM_MODEM_STATE_LOCKED:
case MM_MODEM_STATE_DISABLED: case MM_MODEM_STATE_DISABLED:
/* Just return success, don't relaunch enabling */ /* Just return success, don't relaunch disabling */
g_simple_async_result_set_op_res_gboolean (result, TRUE); g_simple_async_result_set_op_res_gboolean (result, TRUE);
break; break;
@@ -6350,7 +6351,8 @@ enable (MMBaseModem *self,
/* Check state before launching modem enabling */ /* Check state before launching modem enabling */
switch (MM_BROADBAND_MODEM (self)->priv->modem_state) { switch (MM_BROADBAND_MODEM (self)->priv->modem_state) {
case MM_MODEM_STATE_UNKNOWN: case MM_MODEM_STATE_UNKNOWN:
/* We should never have a UNKNOWN->ENABLED transition */ case MM_MODEM_STATE_FAILED:
/* We should never have a UNKNOWN|FAILED->ENABLED transition */
g_assert_not_reached (); g_assert_not_reached ();
break; break;
@@ -6420,7 +6422,6 @@ typedef enum {
INITIALIZE_STEP_PRIMARY_OPEN, INITIALIZE_STEP_PRIMARY_OPEN,
INITIALIZE_STEP_SETUP_SIMPLE_STATUS, INITIALIZE_STEP_SETUP_SIMPLE_STATUS,
INITIALIZE_STEP_IFACE_MODEM, INITIALIZE_STEP_IFACE_MODEM,
INITIALIZE_STEP_ABORT_IF_LOCKED,
INITIALIZE_STEP_IFACE_3GPP, INITIALIZE_STEP_IFACE_3GPP,
INITIALIZE_STEP_IFACE_3GPP_USSD, INITIALIZE_STEP_IFACE_3GPP_USSD,
INITIALIZE_STEP_IFACE_CDMA, INITIALIZE_STEP_IFACE_CDMA,
@@ -6440,7 +6441,6 @@ typedef struct {
InitializeStep step; InitializeStep step;
MMAtSerialPort *port; MMAtSerialPort *port;
gboolean close_port; gboolean close_port;
gboolean abort_if_locked;
} InitializeContext; } InitializeContext;
static void initialize_step (InitializeContext *ctx); static void initialize_step (InitializeContext *ctx);
@@ -6486,6 +6486,49 @@ initialize_finish (MMBaseModem *self,
return TRUE; return TRUE;
} }
static void
iface_modem_initialize_ready (MMBroadbandModem *self,
GAsyncResult *result,
InitializeContext *ctx)
{
GError *error = NULL;
/* If the modem interface fails to get initialized, we will move the modem
* to a FAILED state. Note that in this case we still export the interface. */
if (!mm_iface_modem_initialize_finish (MM_IFACE_MODEM (self), result, &error)) {
/* Report the new FAILED state */
mm_warn ("Modem couldn't be initialized: %s", error->message);
g_error_free (error);
mm_iface_modem_update_state (MM_IFACE_MODEM (self),
MM_MODEM_STATE_FAILED,
MM_MODEM_STATE_CHANGE_REASON_UNKNOWN);
/* Just jump to the last step */
ctx->step = INITIALIZE_STEP_LAST;
initialize_step (ctx);
return;
}
/* bind simple properties */
mm_iface_modem_bind_simple_status (MM_IFACE_MODEM (self),
self->priv->modem_simple_status);
/* If we find ourselves in a LOCKED state, we shouldn't keep on
* the initialization sequence. Instead, we will re-initialize once
* we are unlocked. */
if (ctx->self->priv->modem_state == MM_MODEM_STATE_LOCKED) {
/* Jump to the Simple interface */
ctx->step = INITIALIZE_STEP_IFACE_SIMPLE;
initialize_step (ctx);
return;
}
/* Go on to next step */
ctx->step++;
initialize_step (ctx);
}
#undef INTERFACE_INIT_READY_FN #undef INTERFACE_INIT_READY_FN
#define INTERFACE_INIT_READY_FN(NAME,TYPE,FATAL_ERRORS) \ #define INTERFACE_INIT_READY_FN(NAME,TYPE,FATAL_ERRORS) \
static void \ static void \
@@ -6495,24 +6538,31 @@ initialize_finish (MMBaseModem *self,
{ \ { \
GError *error = NULL; \ GError *error = NULL; \
\ \
if (!mm_##NAME##_initialize_finish (TYPE (self), \ if (!mm_##NAME##_initialize_finish (TYPE (self), result, &error)) { \
result, \
&error)) { \
if (FATAL_ERRORS) { \ if (FATAL_ERRORS) { \
g_simple_async_result_take_error (G_SIMPLE_ASYNC_RESULT (ctx->result), error); \ mm_warn ("Couldn't initialize interface: '%s'", \
initialize_context_complete_and_free (ctx); \ error->message); \
g_error_free (error); \
\
/* Report the new FAILED state */ \
mm_iface_modem_update_state (MM_IFACE_MODEM (self), \
MM_MODEM_STATE_FAILED, \
MM_MODEM_STATE_CHANGE_REASON_UNKNOWN); \
\
/* Just jump to the last step */ \
ctx->step = INITIALIZE_STEP_LAST; \
initialize_step (ctx); \
return; \ return; \
} \ } \
\ \
mm_dbg ("Couldn't initialize interface: '%s'", \ mm_dbg ("Couldn't initialize interface: '%s'", \
error->message); \ error->message); \
/* Just shutdown the interface */ \ /* Just shutdown this interface */ \
mm_##NAME##_shutdown (TYPE (self)); \ mm_##NAME##_shutdown (TYPE (self)); \
g_error_free (error); \ g_error_free (error); \
} else { \ } else { \
/* bind simple properties */ \ /* bind simple properties */ \
mm_##NAME##_bind_simple_status (TYPE (self), \ mm_##NAME##_bind_simple_status (TYPE (self), self->priv->modem_simple_status); \
self->priv->modem_simple_status); \
} \ } \
\ \
/* Go on to next step */ \ /* Go on to next step */ \
@@ -6520,7 +6570,6 @@ initialize_finish (MMBaseModem *self,
initialize_step (ctx); \ initialize_step (ctx); \
} }
INTERFACE_INIT_READY_FN (iface_modem, MM_IFACE_MODEM, TRUE)
INTERFACE_INIT_READY_FN (iface_modem_3gpp, MM_IFACE_MODEM_3GPP, TRUE) INTERFACE_INIT_READY_FN (iface_modem_3gpp, MM_IFACE_MODEM_3GPP, TRUE)
INTERFACE_INIT_READY_FN (iface_modem_3gpp_ussd, MM_IFACE_MODEM_3GPP_USSD, FALSE) INTERFACE_INIT_READY_FN (iface_modem_3gpp_ussd, MM_IFACE_MODEM_3GPP_USSD, FALSE)
INTERFACE_INIT_READY_FN (iface_modem_cdma, MM_IFACE_MODEM_CDMA, TRUE) INTERFACE_INIT_READY_FN (iface_modem_cdma, MM_IFACE_MODEM_CDMA, TRUE)
@@ -6586,6 +6635,7 @@ initialize_step (InitializeContext *ctx)
/* Fall down to next step */ /* Fall down to next step */
ctx->step++; ctx->step++;
} }
case INITIALIZE_STEP_SETUP_SIMPLE_STATUS: case INITIALIZE_STEP_SETUP_SIMPLE_STATUS:
/* Simple status must be created before any interface initialization, /* Simple status must be created before any interface initialization,
* so that interfaces add and bind the properties they want to export. * so that interfaces add and bind the properties they want to export.
@@ -6603,20 +6653,6 @@ initialize_step (InitializeContext *ctx)
ctx); ctx);
return; return;
case INITIALIZE_STEP_ABORT_IF_LOCKED:
/* If we find ourselves in a LOCKED state, we shouldn't keep on
* the initialization sequence. Instead, we will re-initialize once
* we are unlocked. */
if (ctx->self->priv->modem_state == MM_MODEM_STATE_LOCKED) {
/* Jump to the Simple interface */
ctx->abort_if_locked = TRUE;
ctx->step = INITIALIZE_STEP_IFACE_SIMPLE;
initialize_step (ctx);
return;
}
/* Fall down to next step */
ctx->step++;
case INITIALIZE_STEP_IFACE_3GPP: case INITIALIZE_STEP_IFACE_3GPP:
if (mm_iface_modem_is_3gpp (MM_IFACE_MODEM (ctx->self))) { if (mm_iface_modem_is_3gpp (MM_IFACE_MODEM (ctx->self))) {
/* Initialize the 3GPP interface */ /* Initialize the 3GPP interface */
@@ -6691,14 +6727,36 @@ initialize_step (InitializeContext *ctx)
ctx->step++; ctx->step++;
case INITIALIZE_STEP_LAST: case INITIALIZE_STEP_LAST:
if (ctx->abort_if_locked) { if (ctx->self->priv->modem_state == MM_MODEM_STATE_FAILED) {
/* Fatal SIM failure :-( */
g_simple_async_result_set_error (ctx->result,
MM_CORE_ERROR,
MM_CORE_ERROR_WRONG_STATE,
"Modem is unusable, "
"cannot fully initialize");
/* Ensure we only leave the Modem interface around */
mm_iface_modem_3gpp_shutdown (MM_IFACE_MODEM_3GPP (ctx->self));
mm_iface_modem_3gpp_ussd_shutdown (MM_IFACE_MODEM_3GPP_USSD (ctx->self));
mm_iface_modem_cdma_shutdown (MM_IFACE_MODEM_CDMA (ctx->self));
mm_iface_modem_location_shutdown (MM_IFACE_MODEM_LOCATION (ctx->self));
mm_iface_modem_messaging_shutdown (MM_IFACE_MODEM_MESSAGING (ctx->self));
mm_iface_modem_time_shutdown (MM_IFACE_MODEM_TIME (ctx->self));
mm_iface_modem_simple_shutdown (MM_IFACE_MODEM_SIMPLE (ctx->self));
initialize_context_complete_and_free (ctx);
return;
}
if (ctx->self->priv->modem_state == MM_MODEM_STATE_LOCKED) {
/* We're locked :-/ */ /* We're locked :-/ */
g_simple_async_result_set_error (ctx->result, g_simple_async_result_set_error (ctx->result,
MM_CORE_ERROR, MM_CORE_ERROR,
MM_CORE_ERROR_WRONG_STATE, MM_CORE_ERROR_WRONG_STATE,
"Modem is currently locked, " "Modem is currently locked, "
"cannot fully initialize"); "cannot fully initialize");
} else { initialize_context_complete_and_free (ctx);
return;
}
/* All initialized without errors! /* All initialized without errors!
* Set as disabled (a.k.a. initialized) */ * Set as disabled (a.k.a. initialized) */
mm_iface_modem_update_state (MM_IFACE_MODEM (ctx->self), mm_iface_modem_update_state (MM_IFACE_MODEM (ctx->self),
@@ -6706,8 +6764,6 @@ initialize_step (InitializeContext *ctx)
MM_MODEM_STATE_CHANGE_REASON_UNKNOWN); MM_MODEM_STATE_CHANGE_REASON_UNKNOWN);
g_simple_async_result_set_op_res_gboolean (G_SIMPLE_ASYNC_RESULT (ctx->result), TRUE); g_simple_async_result_set_op_res_gboolean (G_SIMPLE_ASYNC_RESULT (ctx->result), TRUE);
}
initialize_context_complete_and_free (ctx); initialize_context_complete_and_free (ctx);
return; return;
} }
@@ -6727,6 +6783,15 @@ initialize (MMBaseModem *self,
/* Check state before launching modem initialization */ /* Check state before launching modem initialization */
switch (MM_BROADBAND_MODEM (self)->priv->modem_state) { switch (MM_BROADBAND_MODEM (self)->priv->modem_state) {
case MM_MODEM_STATE_FAILED:
/* NOTE: this will only happen if we ever support hot-plugging SIMs */
g_simple_async_result_set_error (result,
MM_CORE_ERROR,
MM_CORE_ERROR_WRONG_STATE,
"Cannot initialize modem: "
"device is unusable");
break;
case MM_MODEM_STATE_UNKNOWN: case MM_MODEM_STATE_UNKNOWN:
case MM_MODEM_STATE_LOCKED: { case MM_MODEM_STATE_LOCKED: {
InitializeContext *ctx; InitializeContext *ctx;

View File

@@ -188,8 +188,10 @@ handle_register_auth_ready (MMBaseModem *self,
NULL); NULL);
switch (modem_state) { switch (modem_state) {
case MM_MODEM_STATE_FAILED:
case MM_MODEM_STATE_UNKNOWN: case MM_MODEM_STATE_UNKNOWN:
/* We should never have a UNKNOWN->REGISTERED transition */ case MM_MODEM_STATE_LOCKED:
/* We should never have such request (interface wasn't exported yet) */
g_assert_not_reached (); g_assert_not_reached ();
break; break;
@@ -199,13 +201,6 @@ handle_register_auth_ready (MMBaseModem *self,
MM_CORE_ERROR_WRONG_STATE, MM_CORE_ERROR_WRONG_STATE,
"Cannot register modem: " "Cannot register modem: "
"device not fully initialized yet"); "device not fully initialized yet");
handle_register_context_free (ctx);
return;
case MM_MODEM_STATE_LOCKED:
/* We should never have such request in LOCKED state
* (interface wasn't exported yet) */
g_assert_not_reached ();
break; break;
case MM_MODEM_STATE_ENABLED: case MM_MODEM_STATE_ENABLED:
@@ -381,8 +376,10 @@ handle_scan_auth_ready (MMBaseModem *self,
NULL); NULL);
switch (modem_state) { switch (modem_state) {
case MM_MODEM_STATE_FAILED:
case MM_MODEM_STATE_UNKNOWN: case MM_MODEM_STATE_UNKNOWN:
/* We should never have such request in UNKNOWN state */ case MM_MODEM_STATE_LOCKED:
/* We should never have such request (interface wasn't exported yet) */
g_assert_not_reached (); g_assert_not_reached ();
break; break;
@@ -392,13 +389,6 @@ handle_scan_auth_ready (MMBaseModem *self,
MM_CORE_ERROR_WRONG_STATE, MM_CORE_ERROR_WRONG_STATE,
"Cannot scan networks: " "Cannot scan networks: "
"device not fully initialized yet"); "device not fully initialized yet");
handle_scan_context_free (ctx);
return;
case MM_MODEM_STATE_LOCKED:
/* We should never have such request in LOCKED state
* (interface wasn't exported yet) */
g_assert_not_reached ();
break; break;
case MM_MODEM_STATE_DISABLED: case MM_MODEM_STATE_DISABLED:

View File

@@ -130,8 +130,10 @@ handle_activate_auth_ready (MMBaseModem *self,
NULL); NULL);
switch (modem_state) { switch (modem_state) {
case MM_MODEM_STATE_FAILED:
case MM_MODEM_STATE_UNKNOWN: case MM_MODEM_STATE_UNKNOWN:
/* We should never have such request in UNKNOWN state */ case MM_MODEM_STATE_LOCKED:
/* We should never have such request (interface wasn't exported yet) */
g_assert_not_reached (); g_assert_not_reached ();
break; break;
@@ -144,12 +146,6 @@ handle_activate_auth_ready (MMBaseModem *self,
handle_activate_context_free (ctx); handle_activate_context_free (ctx);
return; return;
case MM_MODEM_STATE_LOCKED:
/* We should never have such request in LOCKED state
* (interface wasn't exported yet) */
g_assert_not_reached ();
break;
case MM_MODEM_STATE_ENABLED: case MM_MODEM_STATE_ENABLED:
case MM_MODEM_STATE_SEARCHING: case MM_MODEM_STATE_SEARCHING:
case MM_MODEM_STATE_REGISTERED: case MM_MODEM_STATE_REGISTERED:
@@ -280,8 +276,10 @@ handle_activate_manual_auth_ready (MMBaseModem *self,
NULL); NULL);
switch (modem_state) { switch (modem_state) {
case MM_MODEM_STATE_FAILED:
case MM_MODEM_STATE_UNKNOWN: case MM_MODEM_STATE_UNKNOWN:
/* We should never have such request in UNKNOWN state */ case MM_MODEM_STATE_LOCKED:
/* We should never have such request (interface wasn't exported yet) */
g_assert_not_reached (); g_assert_not_reached ();
break; break;
@@ -294,12 +292,6 @@ handle_activate_manual_auth_ready (MMBaseModem *self,
handle_activate_manual_context_free (ctx); handle_activate_manual_context_free (ctx);
return; return;
case MM_MODEM_STATE_LOCKED:
/* We should never have such request in LOCKED state
* (interface wasn't exported yet) */
g_assert_not_reached ();
break;
case MM_MODEM_STATE_ENABLED: case MM_MODEM_STATE_ENABLED:
case MM_MODEM_STATE_SEARCHING: case MM_MODEM_STATE_SEARCHING:
case MM_MODEM_STATE_REGISTERED: case MM_MODEM_STATE_REGISTERED:

View File

@@ -1286,31 +1286,18 @@ handle_reset_auth_ready (MMBaseModem *self,
MM_IFACE_MODEM_STATE, &modem_state, MM_IFACE_MODEM_STATE, &modem_state,
NULL); NULL);
switch (modem_state) { if (modem_state < MM_MODEM_STATE_DISABLED) {
case MM_MODEM_STATE_UNKNOWN:
case MM_MODEM_STATE_INITIALIZING:
case MM_MODEM_STATE_LOCKED:
g_dbus_method_invocation_return_error (ctx->invocation, g_dbus_method_invocation_return_error (ctx->invocation,
MM_CORE_ERROR, MM_CORE_ERROR,
MM_CORE_ERROR_WRONG_STATE, MM_CORE_ERROR_WRONG_STATE,
"Cannot reset modem: not initialized/unlocked yet"); "Cannot reset modem: not initialized/unlocked yet");
handle_reset_context_free (ctx); handle_reset_context_free (ctx);
return; return;
}
case MM_MODEM_STATE_DISABLED:
case MM_MODEM_STATE_DISABLING:
case MM_MODEM_STATE_ENABLING:
case MM_MODEM_STATE_ENABLED:
case MM_MODEM_STATE_SEARCHING:
case MM_MODEM_STATE_REGISTERED:
case MM_MODEM_STATE_DISCONNECTING:
case MM_MODEM_STATE_CONNECTING:
case MM_MODEM_STATE_CONNECTED:
MM_IFACE_MODEM_GET_INTERFACE (self)->reset (MM_IFACE_MODEM (self), MM_IFACE_MODEM_GET_INTERFACE (self)->reset (MM_IFACE_MODEM (self),
(GAsyncReadyCallback)handle_reset_ready, (GAsyncReadyCallback)handle_reset_ready,
ctx); ctx);
break;
}
} }
static gboolean static gboolean
@@ -1399,10 +1386,7 @@ handle_factory_reset_auth_ready (MMBaseModem *self,
MM_IFACE_MODEM_STATE, &modem_state, MM_IFACE_MODEM_STATE, &modem_state,
NULL); NULL);
switch (modem_state) { if (modem_state < MM_MODEM_STATE_DISABLED) {
case MM_MODEM_STATE_UNKNOWN:
case MM_MODEM_STATE_INITIALIZING:
case MM_MODEM_STATE_LOCKED:
g_dbus_method_invocation_return_error (ctx->invocation, g_dbus_method_invocation_return_error (ctx->invocation,
MM_CORE_ERROR, MM_CORE_ERROR,
MM_CORE_ERROR_WRONG_STATE, MM_CORE_ERROR_WRONG_STATE,
@@ -1410,22 +1394,12 @@ handle_factory_reset_auth_ready (MMBaseModem *self,
"not initialized/unlocked yet"); "not initialized/unlocked yet");
handle_factory_reset_context_free (ctx); handle_factory_reset_context_free (ctx);
return; return;
}
case MM_MODEM_STATE_DISABLED:
case MM_MODEM_STATE_DISABLING:
case MM_MODEM_STATE_ENABLING:
case MM_MODEM_STATE_ENABLED:
case MM_MODEM_STATE_SEARCHING:
case MM_MODEM_STATE_REGISTERED:
case MM_MODEM_STATE_DISCONNECTING:
case MM_MODEM_STATE_CONNECTING:
case MM_MODEM_STATE_CONNECTED:
MM_IFACE_MODEM_GET_INTERFACE (self)->factory_reset (MM_IFACE_MODEM (self), MM_IFACE_MODEM_GET_INTERFACE (self)->factory_reset (MM_IFACE_MODEM (self),
ctx->code, ctx->code,
(GAsyncReadyCallback)handle_factory_reset_ready, (GAsyncReadyCallback)handle_factory_reset_ready,
ctx); ctx);
break;
}
} }
static gboolean static gboolean
@@ -1649,6 +1623,7 @@ handle_set_bands_auth_ready (MMBaseModem *self,
GAsyncResult *res, GAsyncResult *res,
HandleSetBandsContext *ctx) HandleSetBandsContext *ctx)
{ {
GArray *bands_array;
MMModemState modem_state; MMModemState modem_state;
GError *error = NULL; GError *error = NULL;
@@ -1663,10 +1638,7 @@ handle_set_bands_auth_ready (MMBaseModem *self,
MM_IFACE_MODEM_STATE, &modem_state, MM_IFACE_MODEM_STATE, &modem_state,
NULL); NULL);
switch (modem_state) { if (modem_state < MM_MODEM_STATE_DISABLED) {
case MM_MODEM_STATE_UNKNOWN:
case MM_MODEM_STATE_INITIALIZING:
case MM_MODEM_STATE_LOCKED:
g_dbus_method_invocation_return_error (ctx->invocation, g_dbus_method_invocation_return_error (ctx->invocation,
MM_CORE_ERROR, MM_CORE_ERROR,
MM_CORE_ERROR_WRONG_STATE, MM_CORE_ERROR_WRONG_STATE,
@@ -1674,17 +1646,7 @@ handle_set_bands_auth_ready (MMBaseModem *self,
"not initialized/unlocked yet"); "not initialized/unlocked yet");
handle_set_bands_context_free (ctx); handle_set_bands_context_free (ctx);
return; return;
}
case MM_MODEM_STATE_DISABLED:
case MM_MODEM_STATE_DISABLING:
case MM_MODEM_STATE_ENABLING:
case MM_MODEM_STATE_ENABLED:
case MM_MODEM_STATE_SEARCHING:
case MM_MODEM_STATE_REGISTERED:
case MM_MODEM_STATE_DISCONNECTING:
case MM_MODEM_STATE_CONNECTING:
case MM_MODEM_STATE_CONNECTED: {
GArray *bands_array;
bands_array = mm_common_bands_variant_to_garray (ctx->bands); bands_array = mm_common_bands_variant_to_garray (ctx->bands);
mm_iface_modem_set_bands (MM_IFACE_MODEM (self), mm_iface_modem_set_bands (MM_IFACE_MODEM (self),
@@ -1692,9 +1654,6 @@ handle_set_bands_auth_ready (MMBaseModem *self,
(GAsyncReadyCallback)handle_set_bands_ready, (GAsyncReadyCallback)handle_set_bands_ready,
ctx); ctx);
g_array_unref (bands_array); g_array_unref (bands_array);
break;
}
}
} }
static gboolean static gboolean
@@ -1919,10 +1878,7 @@ handle_set_allowed_modes_auth_ready (MMBaseModem *self,
MM_IFACE_MODEM_STATE, &modem_state, MM_IFACE_MODEM_STATE, &modem_state,
NULL); NULL);
switch (modem_state) { if (modem_state < MM_MODEM_STATE_DISABLED) {
case MM_MODEM_STATE_UNKNOWN:
case MM_MODEM_STATE_INITIALIZING:
case MM_MODEM_STATE_LOCKED:
g_dbus_method_invocation_return_error (ctx->invocation, g_dbus_method_invocation_return_error (ctx->invocation,
MM_CORE_ERROR, MM_CORE_ERROR,
MM_CORE_ERROR_WRONG_STATE, MM_CORE_ERROR_WRONG_STATE,
@@ -1930,23 +1886,13 @@ handle_set_allowed_modes_auth_ready (MMBaseModem *self,
"not initialized/unlocked yet"); "not initialized/unlocked yet");
handle_set_allowed_modes_context_free (ctx); handle_set_allowed_modes_context_free (ctx);
return; return;
}
case MM_MODEM_STATE_DISABLED:
case MM_MODEM_STATE_DISABLING:
case MM_MODEM_STATE_ENABLING:
case MM_MODEM_STATE_ENABLED:
case MM_MODEM_STATE_SEARCHING:
case MM_MODEM_STATE_REGISTERED:
case MM_MODEM_STATE_DISCONNECTING:
case MM_MODEM_STATE_CONNECTING:
case MM_MODEM_STATE_CONNECTED:
mm_iface_modem_set_allowed_modes (MM_IFACE_MODEM (self), mm_iface_modem_set_allowed_modes (MM_IFACE_MODEM (self),
ctx->allowed, ctx->allowed,
ctx->preferred, ctx->preferred,
(GAsyncReadyCallback)handle_set_allowed_modes_ready, (GAsyncReadyCallback)handle_set_allowed_modes_ready,
ctx); ctx);
break;
}
} }
static gboolean static gboolean
@@ -2075,9 +2021,8 @@ mm_iface_modem_unlock_check_finish (MMIfaceModem *self,
GAsyncResult *res, GAsyncResult *res,
GError **error) GError **error)
{ {
if (g_simple_async_result_propagate_error (G_SIMPLE_ASYNC_RESULT (res), error)) { if (g_simple_async_result_propagate_error (G_SIMPLE_ASYNC_RESULT (res), error))
return MM_MODEM_LOCK_UNKNOWN; return MM_MODEM_LOCK_UNKNOWN;
}
return (MMModemLock) GPOINTER_TO_UINT (g_simple_async_result_get_op_res_gpointer (G_SIMPLE_ASYNC_RESULT (res))); return (MMModemLock) GPOINTER_TO_UINT (g_simple_async_result_get_op_res_gpointer (G_SIMPLE_ASYNC_RESULT (res)));
} }
@@ -2111,7 +2056,8 @@ unlock_check_ready (MMIfaceModem *self,
&error); &error);
if (error) { if (error) {
/* Treat several SIM related, serial and other core errors as critical /* Treat several SIM related, serial and other core errors as critical
* and abort the checks. */ * and abort the checks. These will end up moving the modem to a FAILED
* state. */
if (error->domain == MM_SERIAL_ERROR || if (error->domain == MM_SERIAL_ERROR ||
g_error_matches (error, g_error_matches (error,
MM_CORE_ERROR, MM_CORE_ERROR,
@@ -3014,6 +2960,7 @@ struct _InitializationContext {
GSimpleAsyncResult *result; GSimpleAsyncResult *result;
GCancellable *cancellable; GCancellable *cancellable;
MmGdbusModem *skeleton; MmGdbusModem *skeleton;
GError *fatal_error;
}; };
static InitializationContext * static InitializationContext *
@@ -3042,6 +2989,7 @@ initialization_context_new (MMIfaceModem *self,
static void static void
initialization_context_complete_and_free (InitializationContext *ctx) initialization_context_complete_and_free (InitializationContext *ctx)
{ {
g_assert (ctx->fatal_error == NULL);
g_simple_async_result_complete_in_idle (ctx->result); g_simple_async_result_complete_in_idle (ctx->result);
g_object_unref (ctx->cancellable); g_object_unref (ctx->cancellable);
g_object_unref (ctx->self); g_object_unref (ctx->self);
@@ -3116,22 +3064,23 @@ load_current_capabilities_ready (MMIfaceModem *self,
GAsyncResult *res, GAsyncResult *res,
InitializationContext *ctx) InitializationContext *ctx)
{ {
GError *error = NULL;
/* We have the property in the interface bound to the property in the /* We have the property in the interface bound to the property in the
* skeleton. */ * skeleton. */
g_object_set (self, g_object_set (self,
MM_IFACE_MODEM_CURRENT_CAPABILITIES, MM_IFACE_MODEM_CURRENT_CAPABILITIES,
MM_IFACE_MODEM_GET_INTERFACE (self)->load_current_capabilities_finish (self, res, &error), MM_IFACE_MODEM_GET_INTERFACE (self)->load_current_capabilities_finish (self,
res,
&ctx->fatal_error),
NULL); NULL);
if (ctx->fatal_error) {
if (error) { g_prefix_error (&ctx->fatal_error,
mm_warn ("couldn't load Current Capabilities: '%s'", error->message); "couldn't load Current Capabilities: ");
g_error_free (error); /* Jump to the last step */
} ctx->step = INITIALIZATION_STEP_LAST;
} else
/* Go on to next step */ /* Go on to next step */
ctx->step++; ctx->step++;
interface_initialization_step (ctx); interface_initialization_step (ctx);
} }
@@ -3222,20 +3171,17 @@ load_unlock_required_ready (MMIfaceModem *self,
GAsyncResult *res, GAsyncResult *res,
InitializationContext *ctx) InitializationContext *ctx)
{ {
GError *error = NULL;
/* NOTE: we already propagated the lock state, no need to do it again */ /* NOTE: we already propagated the lock state, no need to do it again */
mm_iface_modem_unlock_check_finish (self, res, &error); mm_iface_modem_unlock_check_finish (self, res, &ctx->fatal_error);
if (error) { if (ctx->fatal_error) {
/* FATAL */ g_prefix_error (&ctx->fatal_error,
mm_warn ("couldn't load unlock required status: '%s'", error->message); "Couldn't check unlock status: ");
g_simple_async_result_take_error (ctx->result, error); /* Jump to the last step */
initialization_context_complete_and_free (ctx); ctx->step = INITIALIZATION_STEP_LAST;
return; } else
}
/* Go on to next step */ /* Go on to next step */
ctx->step++; ctx->step++;
interface_initialization_step (ctx); interface_initialization_step (ctx);
} }
@@ -3612,9 +3558,12 @@ interface_initialization_step (InitializationContext *ctx)
} }
case INITIALIZATION_STEP_LAST: case INITIALIZATION_STEP_LAST:
/* We are done without errors! */ if (ctx->fatal_error) {
g_simple_async_result_take_error (ctx->result, ctx->fatal_error);
/* Handle method invocations */ ctx->fatal_error = NULL;
} else {
/* We are done without errors!
* Handle method invocations */
g_signal_connect (ctx->skeleton, g_signal_connect (ctx->skeleton,
"handle-create-bearer", "handle-create-bearer",
G_CALLBACK (handle_create_bearer), G_CALLBACK (handle_create_bearer),
@@ -3651,12 +3600,12 @@ interface_initialization_step (InitializationContext *ctx)
"handle-set-allowed-modes", "handle-set-allowed-modes",
G_CALLBACK (handle_set_allowed_modes), G_CALLBACK (handle_set_allowed_modes),
ctx->self); ctx->self);
g_simple_async_result_set_op_res_gboolean (ctx->result, TRUE);
}
/* Finally, export the new interface */ /* Finally, export the new interface, even if we got errors */
mm_gdbus_object_skeleton_set_modem (MM_GDBUS_OBJECT_SKELETON (ctx->self), mm_gdbus_object_skeleton_set_modem (MM_GDBUS_OBJECT_SKELETON (ctx->self),
MM_GDBUS_MODEM (ctx->skeleton)); MM_GDBUS_MODEM (ctx->skeleton));
g_simple_async_result_set_op_res_gboolean (ctx->result, TRUE);
initialization_context_complete_and_free (ctx); initialization_context_complete_and_free (ctx);
return; return;
} }