aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--plugins/huawei/mm-broadband-modem-huawei.c262
1 files changed, 151 insertions, 111 deletions
diff --git a/plugins/huawei/mm-broadband-modem-huawei.c b/plugins/huawei/mm-broadband-modem-huawei.c
index de89e5ad..eff183a0 100644
--- a/plugins/huawei/mm-broadband-modem-huawei.c
+++ b/plugins/huawei/mm-broadband-modem-huawei.c
@@ -1278,156 +1278,196 @@ load_current_modes (MMIfaceModem *_self,
/* Set current modes (Modem interface) */
static gboolean
-allowed_mode_to_prefmode (MMModemMode allowed, guint *huawei_mode, GError **error)
-{
- char *allowed_str;
-
- *huawei_mode = 0;
- if (allowed == MM_MODEM_MODE_ANY)
- *huawei_mode = 8;
- else if (allowed == (MM_MODEM_MODE_2G | MM_MODEM_MODE_3G))
- *huawei_mode = 8;
- else if (allowed == MM_MODEM_MODE_2G)
- *huawei_mode = 2;
- else if (allowed == MM_MODEM_MODE_3G)
- *huawei_mode = 4;
- else {
- /* Not supported */
- allowed_str = mm_modem_mode_build_string_from_mask (allowed);
- g_set_error (error,
- MM_CORE_ERROR,
- MM_CORE_ERROR_FAILED,
- "Requested mode (allowed: '%s') not supported by the modem.",
- allowed_str);
- g_free (allowed_str);
- }
- return *huawei_mode ? TRUE : FALSE;
+set_current_modes_finish (MMIfaceModem *self,
+ GAsyncResult *res,
+ GError **error)
+{
+ return !g_simple_async_result_propagate_error (G_SIMPLE_ASYNC_RESULT (res), error);
+}
+
+static void
+set_current_modes_ready (MMBroadbandModemHuawei *self,
+ GAsyncResult *res,
+ GSimpleAsyncResult *simple)
+{
+ GError *error = NULL;
+
+ mm_base_modem_at_command_finish (MM_BASE_MODEM (self), res, &error);
+ if (error)
+ /* Let the error be critical. */
+ 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
-allowed_mode_to_huawei (MMModemMode allowed,
- MMModemMode preferred,
- guint *huawei_mode,
- guint *huawei_acquisition_order,
- GError **error)
-{
- gchar *allowed_str;
- gchar *preferred_str;
-
- if (allowed == MM_MODEM_MODE_ANY) {
- *huawei_mode = 2;
- *huawei_acquisition_order = 0;
- return TRUE;
- }
+prefmode_set_current_modes (MMBroadbandModemHuawei *self,
+ MMModemMode allowed,
+ MMModemMode preferred,
+ GSimpleAsyncResult *simple,
+ GError **error)
+{
+ guint i;
+ MMHuaweiPrefmodeCombination *found = NULL;
+ gchar *command;
- if (allowed == MM_MODEM_MODE_2G) {
- *huawei_mode = 13;
- *huawei_acquisition_order = 1;
- return TRUE;
- }
+ for (i = 0; i < self->priv->prefmode_supported_modes->len; i++) {
+ MMHuaweiPrefmodeCombination *single;
- if (allowed == MM_MODEM_MODE_3G) {
- *huawei_mode = 14;
- *huawei_acquisition_order = 2;
- return TRUE;
+ single = &g_array_index (self->priv->prefmode_supported_modes,
+ MMHuaweiPrefmodeCombination,
+ i);
+ if (single->allowed == allowed && single->preferred == preferred) {
+ found = single;
+ break;
+ }
}
- if (allowed == (MM_MODEM_MODE_2G | MM_MODEM_MODE_3G)) {
- *huawei_mode = 2;
- if (preferred == MM_MODEM_MODE_2G)
- *huawei_acquisition_order = 1;
- else if (preferred == MM_MODEM_MODE_3G)
- *huawei_acquisition_order = 2;
- else
- *huawei_acquisition_order = 0;
- return TRUE;
+ if (!found) {
+ g_set_error (error,
+ MM_CORE_ERROR,
+ MM_CORE_ERROR_NOT_FOUND,
+ "Requested mode ^PREFMODE combination not found");
+ return FALSE;
}
- /* Not supported */
- allowed_str = mm_modem_mode_build_string_from_mask (allowed);
- preferred_str = mm_modem_mode_build_string_from_mask (preferred);
- g_set_error (error,
- MM_CORE_ERROR,
- MM_CORE_ERROR_FAILED,
- "Requested mode (allowed: '%s', preferred: '%s') not "
- "supported by the modem.",
- allowed_str,
- preferred_str);
- g_free (allowed_str);
- g_free (preferred_str);
- return FALSE;
+ command = g_strdup_printf ("^PREFMODE=%u", found->prefmode);
+ mm_base_modem_at_command (
+ MM_BASE_MODEM (self),
+ command,
+ 3,
+ FALSE,
+ (GAsyncReadyCallback)set_current_modes_ready,
+ simple);
+ g_free (command);
+ return TRUE;
}
static gboolean
-set_current_modes_finish (MMIfaceModem *self,
- GAsyncResult *res,
+syscfg_set_current_modes (MMBroadbandModemHuawei *self,
+ MMModemMode allowed,
+ MMModemMode preferred,
+ GSimpleAsyncResult *simple,
GError **error)
{
- return !g_simple_async_result_propagate_error (G_SIMPLE_ASYNC_RESULT (res), error);
+ guint i;
+ MMHuaweiSyscfgCombination *found = NULL;
+ gchar *command;
+
+ for (i = 0; i < self->priv->syscfg_supported_modes->len; i++) {
+ MMHuaweiSyscfgCombination *single;
+
+ single = &g_array_index (self->priv->syscfg_supported_modes,
+ MMHuaweiSyscfgCombination,
+ i);
+ if (single->allowed == allowed && single->preferred == preferred) {
+ found = single;
+ break;
+ }
+ }
+
+ if (!found) {
+ g_set_error (error,
+ MM_CORE_ERROR,
+ MM_CORE_ERROR_NOT_FOUND,
+ "Requested mode ^SYSCFG combination not found");
+ return FALSE;
+ }
+
+ command = g_strdup_printf ("^SYSCFG=%u,%u,40000000,2,4",
+ found->mode,
+ found->acqorder);
+ mm_base_modem_at_command (
+ MM_BASE_MODEM (self),
+ command,
+ 3,
+ FALSE,
+ (GAsyncReadyCallback)set_current_modes_ready,
+ simple);
+ g_free (command);
+ return TRUE;
}
-static void
-allowed_mode_update_ready (MMBroadbandModemHuawei *self,
- GAsyncResult *res,
- GSimpleAsyncResult *operation_result)
+static gboolean
+syscfgex_set_current_modes (MMBroadbandModemHuawei *self,
+ MMModemMode allowed,
+ MMModemMode preferred,
+ GSimpleAsyncResult *simple,
+ GError **error)
{
- GError *error = NULL;
+ guint i;
+ MMHuaweiSyscfgexCombination *found = NULL;
+ gchar *command;
- mm_base_modem_at_command_finish (MM_BASE_MODEM (self), res, &error);
- if (error)
- /* Let the error be critical. */
- g_simple_async_result_take_error (operation_result, error);
- else
- g_simple_async_result_set_op_res_gboolean (operation_result, TRUE);
- g_simple_async_result_complete (operation_result);
- g_object_unref (operation_result);
+ for (i = 0; i < self->priv->syscfgex_supported_modes->len; i++) {
+ MMHuaweiSyscfgexCombination *single;
+
+ single = &g_array_index (self->priv->syscfgex_supported_modes,
+ MMHuaweiSyscfgexCombination,
+ i);
+ if (single->allowed == allowed && single->preferred == preferred) {
+ found = single;
+ break;
+ }
+ }
+
+ if (!found) {
+ g_set_error (error,
+ MM_CORE_ERROR,
+ MM_CORE_ERROR_NOT_FOUND,
+ "Requested mode ^SYSCFGEX combination not found");
+ return FALSE;
+ }
+
+ command = g_strdup_printf ("^SYSCFGEX=\"%s\",3fffffff,2,4,7fffffffffffffff,,",
+ found->mode_str);
+ mm_base_modem_at_command (
+ MM_BASE_MODEM (self),
+ command,
+ 3,
+ FALSE,
+ (GAsyncReadyCallback)set_current_modes_ready,
+ simple);
+ g_free (command);
+ return TRUE;
}
static void
-set_current_modes (MMIfaceModem *self,
+set_current_modes (MMIfaceModem *_self,
MMModemMode allowed,
MMModemMode preferred,
GAsyncReadyCallback callback,
gpointer user_data)
{
+ MMBroadbandModemHuawei *self = MM_BROADBAND_MODEM_HUAWEI (_self);
GSimpleAsyncResult *result;
- gchar *command = NULL;
- guint mode = 0;
- guint acquisition_order;
GError *error = NULL;
+ mm_dbg ("setting current modes (huawei)...");
+
result = g_simple_async_result_new (G_OBJECT (self),
callback,
user_data,
set_current_modes);
- if (mm_iface_modem_is_cdma_only (self)) {
- if (allowed_mode_to_prefmode (allowed, &mode, &error))
- command = g_strdup_printf ("^PREFMODE=%d", mode);
- } else {
- if (allowed_mode_to_huawei (allowed,
- preferred,
- &mode,
- &acquisition_order,
- &error))
- command = g_strdup_printf ("AT^SYSCFG=%d,%d,40000000,2,4", mode, acquisition_order);
- }
+ if (self->priv->syscfgex_support == FEATURE_SUPPORTED)
+ syscfgex_set_current_modes (self, allowed, preferred, result, &error);
+ else if (self->priv->syscfg_support == FEATURE_SUPPORTED)
+ syscfg_set_current_modes (self, allowed, preferred, result, &error);
+ else if (self->priv->prefmode_support == FEATURE_SUPPORTED)
+ prefmode_set_current_modes (self, allowed, preferred, result, &error);
+ else
+ error = g_error_new (MM_CORE_ERROR,
+ MM_CORE_ERROR_FAILED,
+ "Setting current modes is not supported");
- if (command) {
- mm_base_modem_at_command (
- MM_BASE_MODEM (self),
- command,
- 3,
- FALSE,
- (GAsyncReadyCallback)allowed_mode_update_ready,
- result);
- } else {
- g_assert (error);
+ if (error) {
g_simple_async_result_take_error (result, error);
g_simple_async_result_complete_in_idle (result);
g_object_unref (result);
}
- g_free (command);
}
/*****************************************************************************/