diff options
Diffstat (limited to 'plugins')
-rw-r--r-- | plugins/iridium/mm-broadband-modem-iridium.c | 81 | ||||
-rw-r--r-- | plugins/mbm/mm-broadband-modem-mbm.c | 96 | ||||
-rw-r--r-- | plugins/nokia/mm-broadband-modem-nokia.c | 110 | ||||
-rw-r--r-- | plugins/novatel/mm-broadband-modem-novatel-lte.c | 108 |
4 files changed, 174 insertions, 221 deletions
diff --git a/plugins/iridium/mm-broadband-modem-iridium.c b/plugins/iridium/mm-broadband-modem-iridium.c index fe88bc08..197a1f73 100644 --- a/plugins/iridium/mm-broadband-modem-iridium.c +++ b/plugins/iridium/mm-broadband-modem-iridium.c @@ -46,14 +46,6 @@ G_DEFINE_TYPE_EXTENDED (MMBroadbandModemIridium, mm_broadband_modem_iridium, MM_ /*****************************************************************************/ /* Initializing the modem (Modem interface) */ -static gboolean -modem_init_finish (MMIfaceModem *self, - GAsyncResult *res, - GError **error) -{ - return !g_simple_async_result_propagate_error (G_SIMPLE_ASYNC_RESULT (res), error); -} - static const MMBaseModemAtCommand modem_init_sequence[] = { /* Init command */ { "E0 V1", 3, FALSE, NULL }, @@ -61,58 +53,12 @@ static const MMBaseModemAtCommand modem_init_sequence[] = { { NULL } }; -static void -init_sequence_ready (MMBroadbandModem *self, - GAsyncResult *res, - GSimpleAsyncResult *simple) -{ - GError *error = NULL; - - mm_base_modem_at_sequence_finish (MM_BASE_MODEM (self), res, NULL, &error); - if (error) - g_simple_async_result_take_error (simple, error); - else - g_simple_async_result_set_op_res_gboolean (simple, TRUE); - g_simple_async_result_complete (simple); - g_object_unref (simple); -} - static gboolean -after_atz_sleep_cb (GSimpleAsyncResult *simple) -{ - MMBaseModem *self; - - self = MM_BASE_MODEM (g_async_result_get_source_object (G_ASYNC_RESULT (simple))); - /* Now, run the remaining sequence */ - mm_base_modem_at_sequence (self, - modem_init_sequence, - NULL, /* response_processor_context */ - NULL, /* response_processor_context_free */ - (GAsyncReadyCallback)init_sequence_ready, - simple); - g_object_unref (self); - return FALSE; -} - -static void -atz_ready (MMBroadbandModem *self, - GAsyncResult *res, - GSimpleAsyncResult *simple) +modem_init_finish (MMIfaceModem *self, + GAsyncResult *res, + GError **error) { - GError *error = NULL; - - mm_base_modem_at_command_finish (MM_BASE_MODEM (self), res, &error); - if (error) { - g_simple_async_result_take_error (simple, error); - g_simple_async_result_complete (simple); - g_object_unref (simple); - return; - } - - /* Once ATZ reply is received, we need to wait a bit before going on, - * otherwise, the next commands given will receive garbage as reply - * (500ms should be enough) */ - g_timeout_add (500, (GSourceFunc)after_atz_sleep_cb, simple); + return !!mm_base_modem_at_sequence_finish (MM_BASE_MODEM (self), res, NULL, error); } static void @@ -120,19 +66,12 @@ modem_init (MMIfaceModem *self, GAsyncReadyCallback callback, gpointer user_data) { - GSimpleAsyncResult *result; - - result = g_simple_async_result_new (G_OBJECT (self), - callback, - user_data, - modem_init); - /* First, send ATZ alone */ - mm_base_modem_at_command (MM_BASE_MODEM (self), - "Z", - 3, - TRUE, - (GAsyncReadyCallback)atz_ready, - result); + mm_base_modem_at_sequence (MM_BASE_MODEM (self), + modem_init_sequence, + NULL, /* response_processor_context */ + NULL, /* response_processor_context_free */ + callback, + user_data); } /*****************************************************************************/ diff --git a/plugins/mbm/mm-broadband-modem-mbm.c b/plugins/mbm/mm-broadband-modem-mbm.c index a5738761..39648cf6 100644 --- a/plugins/mbm/mm-broadband-modem-mbm.c +++ b/plugins/mbm/mm-broadband-modem-mbm.c @@ -307,63 +307,93 @@ set_allowed_modes (MMIfaceModem *_self, /*****************************************************************************/ /* Initializing the modem (Modem interface) */ +static gboolean +modem_init_finish (MMIfaceModem *self, + GAsyncResult *res, + GError **error) +{ + /* Ignore errors */ + mm_base_modem_at_command_full_finish (MM_BASE_MODEM (self), res, NULL); + return TRUE; +} + +static void +modem_init (MMIfaceModem *self, + GAsyncReadyCallback callback, + gpointer user_data) +{ + mm_base_modem_at_command_full (MM_BASE_MODEM (self), + mm_base_modem_peek_port_primary (MM_BASE_MODEM (self)), + "E0 V1 X4 &C1 +CMEE=1", + 3, + FALSE, + FALSE, + NULL, /* cancellable */ + callback, + user_data); +} + +/*****************************************************************************/ +/* Initializing the modem (during first enabling) */ + typedef struct { GSimpleAsyncResult *result; MMBroadbandModemMbm *self; -} ModemInitContext; +} EnablingModemInitContext; static void -modem_init_context_complete_and_free (ModemInitContext *ctx) +enabling_modem_init_context_complete_and_free (EnablingModemInitContext *ctx) { g_simple_async_result_complete (ctx->result); g_object_unref (ctx->result); g_object_unref (ctx->self); - g_slice_free (ModemInitContext, ctx); + g_slice_free (EnablingModemInitContext, ctx); } static gboolean -modem_init_finish (MMIfaceModem *self, - GAsyncResult *res, - GError **error) +enabling_modem_init_finish (MMBroadbandModem *self, + GAsyncResult *res, + GError **error) { - /* Ignore errors */ - mm_base_modem_at_sequence_finish (MM_BASE_MODEM (self), res, NULL, NULL); - return TRUE; + return !g_simple_async_result_propagate_error (G_SIMPLE_ASYNC_RESULT (res), error); } static void -init_sequence_ready (MMBaseModem *self, - GAsyncResult *res, - ModemInitContext *ctx) +enabling_init_sequence_ready (MMBaseModem *self, + GAsyncResult *res, + EnablingModemInitContext *ctx) { - mm_base_modem_at_sequence_finish (self, res, NULL, NULL); + /* Ignore errors */ + mm_base_modem_at_sequence_full_finish (self, res, NULL, NULL); g_simple_async_result_set_op_res_gboolean (ctx->result, TRUE); - modem_init_context_complete_and_free (ctx); + enabling_modem_init_context_complete_and_free (ctx); } -static const MMBaseModemAtCommand modem_init_sequence[] = { +static const MMBaseModemAtCommand enabling_modem_init_sequence[] = { /* Init command */ - { "&F E0 V1 X4 &C1 +CMEE=1", 3, FALSE, NULL }, + { "&F", 3, FALSE, NULL }, /* Ensure disconnected */ { "*ENAP=0", 3, FALSE, NULL }, { NULL } }; static void -run_init_sequence (ModemInitContext *ctx) +run_enabling_init_sequence (EnablingModemInitContext *ctx) { - mm_base_modem_at_sequence (MM_BASE_MODEM (ctx->self), - modem_init_sequence, - NULL, /* response_processor_context */ - NULL, /* response_processor_context_free */ - (GAsyncReadyCallback)init_sequence_ready, - ctx); + mm_base_modem_at_sequence_full (MM_BASE_MODEM (ctx->self), + mm_base_modem_peek_port_primary (MM_BASE_MODEM (ctx->self)), + enabling_modem_init_sequence, + NULL, /* response_processor_context */ + NULL, /* response_processor_context_free */ + NULL, /* cancellable */ + (GAsyncReadyCallback)enabling_init_sequence_ready, + ctx); } static void emrdy_ready (MMBaseModem *self, GAsyncResult *res, - ModemInitContext *ctx) + EnablingModemInitContext *ctx) { GError *error = NULL; @@ -386,26 +416,26 @@ emrdy_ready (MMBaseModem *self, g_error_free (error); } - run_init_sequence (ctx); + run_enabling_init_sequence (ctx); } static void -modem_init (MMIfaceModem *self, - GAsyncReadyCallback callback, - gpointer user_data) +enabling_modem_init (MMBroadbandModem *self, + GAsyncReadyCallback callback, + gpointer user_data) { - ModemInitContext *ctx; + EnablingModemInitContext *ctx; - ctx = g_slice_new0 (ModemInitContext); + ctx = g_slice_new0 (EnablingModemInitContext); ctx->result = g_simple_async_result_new (G_OBJECT (self), callback, user_data, - modem_init); + enabling_modem_init); ctx->self = g_object_ref (self); /* Modem is ready?, no need to check EMRDY */ if (ctx->self->priv->have_emrdy) { - run_init_sequence (ctx); + run_enabling_init_sequence (ctx); return; } @@ -1143,4 +1173,6 @@ mm_broadband_modem_mbm_class_init (MMBroadbandModemMbmClass *klass) object_class->finalize = finalize; broadband_modem_class->setup_ports = setup_ports; + broadband_modem_class->enabling_modem_init = enabling_modem_init; + broadband_modem_class->enabling_modem_init_finish = enabling_modem_init_finish; } diff --git a/plugins/nokia/mm-broadband-modem-nokia.c b/plugins/nokia/mm-broadband-modem-nokia.c index b70049ff..c169e1b4 100644 --- a/plugins/nokia/mm-broadband-modem-nokia.c +++ b/plugins/nokia/mm-broadband-modem-nokia.c @@ -114,18 +114,10 @@ modem_init_finish (MMIfaceModem *self, } static const MMBaseModemAtCommand modem_init_sequence[] = { - /* Send the init command twice; some devices (Nokia N900) appear to take a - * few commands before responding correctly. Instead of penalizing them for - * being stupid the first time by failing to enable the device, just - * try again. - * - * TODO: only send init command 2nd time if 1st time failed? - * - * Also, when initializing a Nokia phone, first enable the echo, + /* Also, when initializing a Nokia phone, first enable the echo, * and then disable it, so that we get it properly disabled. */ - { "Z E1 E0 V1", 3, FALSE, NULL }, - { "Z E1 E0 V1", 3, FALSE, mm_base_modem_response_processor_no_result_continue }, + { "E1 E0 V1", 3, FALSE, NULL }, /* Setup errors */ { "+CMEE=1", 3, FALSE, NULL }, @@ -150,6 +142,100 @@ modem_init (MMIfaceModem *self, } /*****************************************************************************/ +/* Initializing the modem (during first enabling) */ + +typedef struct { + GSimpleAsyncResult *result; + MMBroadbandModemNokia *self; + guint retries; +} EnablingModemInitContext; + +static void +enabling_modem_init_context_complete_and_free (EnablingModemInitContext *ctx) +{ + g_simple_async_result_complete (ctx->result); + g_object_unref (ctx->result); + g_object_unref (ctx->self); + g_slice_free (EnablingModemInitContext, ctx); +} + +static gboolean +enabling_modem_init_finish (MMBroadbandModem *self, + GAsyncResult *res, + GError **error) + +{ + return !g_simple_async_result_propagate_error (G_SIMPLE_ASYNC_RESULT (res), error); +} + +static void retry_atz (EnablingModemInitContext *ctx); + +static void +atz_ready (MMBaseModem *self, + GAsyncResult *res, + EnablingModemInitContext *ctx) +{ + GError *error = NULL; + + /* One retry less */ + ctx->retries--; + + if (!mm_base_modem_at_command_full_finish (self, res, &error)) { + /* Consumed all retries... */ + if (ctx->retries == 0) { + g_simple_async_result_take_error (ctx->result, error); + enabling_modem_init_context_complete_and_free (ctx); + return; + } + + /* Retry... */ + g_error_free (error); + retry_atz (ctx); + return; + } + + /* Good! */ + g_simple_async_result_set_op_res_gboolean (ctx->result, TRUE); + enabling_modem_init_context_complete_and_free (ctx); +} + +static void +retry_atz (EnablingModemInitContext *ctx) +{ + mm_base_modem_at_command_full (MM_BASE_MODEM (ctx->self), + mm_base_modem_peek_port_primary (MM_BASE_MODEM (ctx->self)), + "Z", + 6, + FALSE, + FALSE, + NULL, /* cancellable */ + (GAsyncReadyCallback)atz_ready, + ctx); +} + +static void +enabling_modem_init (MMBroadbandModem *self, + GAsyncReadyCallback callback, + gpointer user_data) +{ + EnablingModemInitContext *ctx; + + ctx = g_slice_new0 (EnablingModemInitContext); + ctx->result = g_simple_async_result_new (G_OBJECT (self), + callback, + user_data, + enabling_modem_init); + ctx->self = g_object_ref (self); + + /* Send the init command twice; some devices (Nokia N900) appear to take a + * few commands before responding correctly. Instead of penalizing them for + * being stupid the first time by failing to enable the device, just + * try again. */ + ctx->retries = 2; + retry_atz (ctx); +} + +/*****************************************************************************/ MMBroadbandModemNokia * mm_broadband_modem_nokia_new (const gchar *device, @@ -214,4 +300,8 @@ iface_modem_init (MMIfaceModem *iface) static void mm_broadband_modem_nokia_class_init (MMBroadbandModemNokiaClass *klass) { + MMBroadbandModemClass *broadband_modem_class = MM_BROADBAND_MODEM_CLASS (klass); + + broadband_modem_class->enabling_modem_init = enabling_modem_init; + broadband_modem_class->enabling_modem_init_finish = enabling_modem_init_finish; } diff --git a/plugins/novatel/mm-broadband-modem-novatel-lte.c b/plugins/novatel/mm-broadband-modem-novatel-lte.c index 9a21c4b2..0db16863 100644 --- a/plugins/novatel/mm-broadband-modem-novatel-lte.c +++ b/plugins/novatel/mm-broadband-modem-novatel-lte.c @@ -43,112 +43,6 @@ G_DEFINE_TYPE_EXTENDED (MMBroadbandModemNovatelLte, mm_broadband_modem_novatel_l G_IMPLEMENT_INTERFACE (MM_TYPE_IFACE_MODEM_3GPP, iface_modem_3gpp_init)); /*****************************************************************************/ -/* Initializing the modem (Modem interface) */ - -static gboolean -modem_init_finish (MMIfaceModem *self, - GAsyncResult *res, - GError **error) -{ - return !g_simple_async_result_propagate_error (G_SIMPLE_ASYNC_RESULT (res), error); -} - -static void -modem_init_sequence_ready (MMBaseModem *self, - GAsyncResult *res, - GSimpleAsyncResult *simple) -{ - GError *error = NULL; - - mm_base_modem_at_sequence_full_finish (MM_BASE_MODEM (self), res, NULL, &error); - if (error) - g_simple_async_result_take_error (simple, error); - else { - MMAtSerialPort *secondary; - - /* Disable echo in secondary port as well, if any */ - secondary = mm_base_modem_peek_port_secondary (MM_BASE_MODEM (self)); - if (secondary) - /* No need to wait for the reply */ - mm_base_modem_at_command_full (MM_BASE_MODEM (self), - secondary, - "E0", - 3, - FALSE, - FALSE, /* raw */ - NULL, /* cancellable */ - NULL, - NULL); - - g_simple_async_result_set_op_res_gboolean (simple, TRUE); - } - - g_simple_async_result_complete (simple); - g_object_unref (simple); -} - -static const MMBaseModemAtCommand modem_init_sequence[] = { - /* Init command. ITU rec v.250 (6.1.1) says: - * The DTE should not include additional commands on the same command line - * after the Z command because such commands may be ignored. - * So run ATZ alone. - */ - { "Z", 6, FALSE, mm_base_modem_response_processor_no_result_continue }, - - /* Ensure echo is off after the init command */ - { "E0 V1", 3, FALSE, NULL }, - - /* Some phones (like Blackberries) don't support +CMEE=1, so make it - * optional. It completely violates 3GPP TS 27.007 (9.1) but what can we do... - */ - { "+CMEE=1", 3, FALSE, NULL }, - - /* Additional OPTIONAL initialization */ - { "X4 &C1", 3, FALSE, NULL }, - - { NULL } -}; - -static void -modem_init (MMIfaceModem *self, - GAsyncReadyCallback callback, - gpointer user_data) -{ - MMAtSerialPort *primary; - GSimpleAsyncResult *result; - guint init_sequence_index; - - result = g_simple_async_result_new (G_OBJECT (self), - callback, - user_data, - modem_init); - - primary = mm_base_modem_peek_port_primary (MM_BASE_MODEM (self)); - if (!primary) { - g_simple_async_result_set_error ( - result, - MM_CORE_ERROR, - MM_CORE_ERROR_FAILED, - "Need primary AT port to run modem init sequence"); - g_simple_async_result_complete_in_idle (result); - g_object_unref (result); - return; - } - - /* Skip ATZ if the device was hotplugged. */ - init_sequence_index = mm_base_modem_get_hotplugged (MM_BASE_MODEM (self)) ? 1 : 0; - - mm_base_modem_at_sequence_full (MM_BASE_MODEM (self), - primary, - &modem_init_sequence[init_sequence_index], - NULL, /* response_processor_context */ - NULL, /* response_processor_context_free */ - NULL, /* cancellable */ - (GAsyncReadyCallback)modem_init_sequence_ready, - result); -} - -/*****************************************************************************/ /* Modem power down (Modem interface) */ static gboolean @@ -767,8 +661,6 @@ mm_broadband_modem_novatel_lte_init (MMBroadbandModemNovatelLte *self) static void iface_modem_init (MMIfaceModem *iface) { - iface->modem_init = modem_init; - iface->modem_init_finish = modem_init_finish; iface->modem_power_down = modem_power_down; iface->modem_power_down_finish = modem_power_down_finish; iface->create_bearer = modem_create_bearer; |