diff options
author | Aleksander Morgado <aleksander@lanedo.com> | 2013-11-03 19:16:20 +0100 |
---|---|---|
committer | Aleksander Morgado <aleksander@lanedo.com> | 2013-11-10 20:31:32 +0100 |
commit | e0f497a8e7a24e681e819785259c4d24eb69045a (patch) | |
tree | 76394870880b4cb6c6f0afddac1e0862ad0edc8c | |
parent | e30b3920d6309c7f265bacfa6c1e0915d1f13281 (diff) | |
download | ModemManager-e0f497a8e7a24e681e819785259c4d24eb69045a.tar.gz |
huawei: new ^PREFMODE=? test parser
-rw-r--r-- | plugins/huawei/mm-modem-helpers-huawei.c | 119 | ||||
-rw-r--r-- | plugins/huawei/mm-modem-helpers-huawei.h | 12 | ||||
-rw-r--r-- | plugins/huawei/tests/test-modem-helpers-huawei.c | 125 |
3 files changed, 256 insertions, 0 deletions
diff --git a/plugins/huawei/mm-modem-helpers-huawei.c b/plugins/huawei/mm-modem-helpers-huawei.c index 00a36a4d9..7e1e71804 100644 --- a/plugins/huawei/mm-modem-helpers-huawei.c +++ b/plugins/huawei/mm-modem-helpers-huawei.c @@ -20,6 +20,8 @@ #define _LIBMM_INSIDE_MM #include <libmm-glib.h> +#include "mm-log.h" +#include "mm-modem-helpers.h" #include "mm-modem-helpers-huawei.h" /*****************************************************************************/ @@ -244,3 +246,120 @@ mm_huawei_parse_sysinfoex_response (const char *reply, g_regex_unref (r); return matched; } + +/*****************************************************************************/ +/* ^PREFMODE test parser + * + * AT^PREFMODE=? + * ^PREFMODE:(2,4,8) + */ + +static gboolean +mode_from_prefmode (guint huawei_mode, + MMModemMode *modem_mode, + GError **error) +{ + g_assert (modem_mode != NULL); + + *modem_mode = MM_MODEM_MODE_NONE; + switch (huawei_mode) { + case 2: + *modem_mode = MM_MODEM_MODE_2G; + break; + case 4: + *modem_mode = MM_MODEM_MODE_3G; + break; + case 8: + *modem_mode = (MM_MODEM_MODE_2G | MM_MODEM_MODE_3G); + break; + default: + g_set_error (error, + MM_CORE_ERROR, + MM_CORE_ERROR_FAILED, + "No translation from huawei prefmode '%u' to mode", + huawei_mode); + } + + return *modem_mode != MM_MODEM_MODE_NONE ? TRUE : FALSE; +} + +GArray * +mm_huawei_parse_prefmode_test (const gchar *response, + GError **error) +{ + gchar **split; + guint i; + MMModemMode all = MM_MODEM_MODE_NONE; + GArray *out; + + response = mm_strip_tag (response, "^PREFMODE:"); + split = g_strsplit_set (response, "(,)\r\n", -1); + if (!split) { + g_set_error (error, + MM_CORE_ERROR, + MM_CORE_ERROR_FAILED, + "Unexpected ^PREFMODE format output"); + return NULL; + } + + out = g_array_sized_new (FALSE, + FALSE, + sizeof (MMHuaweiPrefmodeCombination), + 3); + for (i = 0; split[i]; i++) { + guint val; + MMModemMode preferred = MM_MODEM_MODE_NONE; + GError *inner_error = NULL; + MMHuaweiPrefmodeCombination combination; + + if (split[i][0] == '\0') + continue; + + if (!mm_get_uint_from_str (split[i], &val)) { + mm_dbg ("Error parsing ^PREFMODE value: %s", split[i]); + continue; + } + + if (!mode_from_prefmode (val, &preferred, &inner_error)) { + mm_dbg ("Unhandled ^PREFMODE: %s", inner_error->message); + g_error_free (inner_error); + continue; + } + + combination.prefmode = val; + combination.allowed = MM_MODEM_MODE_NONE; /* reset it later */ + combination.preferred = preferred; + + all |= preferred; + + g_array_append_val (out, combination); + } + g_strfreev (split); + + /* No value */ + if (out->len == 0) { + g_array_unref (out); + return NULL; + } + + /* Single value listed; PREFERRED=NONE... */ + if (out->len == 1) { + MMHuaweiPrefmodeCombination *combination; + + combination = &g_array_index (out, MMHuaweiPrefmodeCombination, 0); + combination->allowed = all; + combination->preferred = MM_MODEM_MODE_NONE; + } else { + /* Multiple values, reset ALLOWED */ + for (i = 0; i < out->len; i++) { + MMHuaweiPrefmodeCombination *combination; + + combination = &g_array_index (out, MMHuaweiPrefmodeCombination, i); + combination->allowed = all; + if (combination->preferred == all) + combination->preferred = MM_MODEM_MODE_NONE; + } + } + + return out; +} diff --git a/plugins/huawei/mm-modem-helpers-huawei.h b/plugins/huawei/mm-modem-helpers-huawei.h index f0f1356be..00191b2d6 100644 --- a/plugins/huawei/mm-modem-helpers-huawei.h +++ b/plugins/huawei/mm-modem-helpers-huawei.h @@ -51,4 +51,16 @@ gboolean mm_huawei_parse_sysinfoex_response (const char *reply, guint *out_sys_submode, GError **error); +/*****************************************************************************/ +/* ^PREFMODE test parser */ + +typedef struct { + guint prefmode; + MMModemMode allowed; + MMModemMode preferred; +} MMHuaweiPrefmodeCombination; + +GArray *mm_huawei_parse_prefmode_test (const gchar *response, + GError **error); + #endif /* MM_MODEM_HELPERS_HUAWEI_H */ diff --git a/plugins/huawei/tests/test-modem-helpers-huawei.c b/plugins/huawei/tests/test-modem-helpers-huawei.c index e5bb9e72b..c7b8b7780 100644 --- a/plugins/huawei/tests/test-modem-helpers-huawei.c +++ b/plugins/huawei/tests/test-modem-helpers-huawei.c @@ -22,6 +22,7 @@ #include <libmm-glib.h> #include "mm-log.h" +#include "mm-modem-helpers.h" #include "mm-modem-helpers-huawei.h" /*****************************************************************************/ @@ -250,6 +251,129 @@ test_sysinfoex (void) } /*****************************************************************************/ +/* Test ^PREFMODE=? responses */ + +#define MAX_PREFMODE_COMBINATIONS 3 + +typedef struct { + const gchar *str; + MMHuaweiPrefmodeCombination expected_modes[MAX_PREFMODE_COMBINATIONS]; +} PrefmodeTest; + +static const PrefmodeTest prefmode_tests[] = { + { + "^PREFMODE:(2,4,8)\r\n", + { + { + .prefmode = 8, + .allowed = (MM_MODEM_MODE_3G | MM_MODEM_MODE_2G), + .preferred = MM_MODEM_MODE_NONE + }, + { + .prefmode = 4, + .allowed = (MM_MODEM_MODE_3G | MM_MODEM_MODE_2G), + .preferred = MM_MODEM_MODE_3G + }, + { + .prefmode = 2, + .allowed = (MM_MODEM_MODE_3G | MM_MODEM_MODE_2G), + .preferred = MM_MODEM_MODE_2G + } + } + }, + { + "^PREFMODE:(2,4)\r\n", + { + { + .prefmode = 4, + .allowed = (MM_MODEM_MODE_3G | MM_MODEM_MODE_2G), + .preferred = MM_MODEM_MODE_3G + }, + { + .prefmode = 2, + .allowed = (MM_MODEM_MODE_3G | MM_MODEM_MODE_2G), + .preferred = MM_MODEM_MODE_2G + }, + { 0, 0, 0} + } + }, + { + "^PREFMODE:(2)\r\n", + { + { + .prefmode = 2, + .allowed = MM_MODEM_MODE_2G, + .preferred = MM_MODEM_MODE_NONE + }, + { 0, 0, 0} + } + }, +}; + +static void +test_prefmode (void) +{ + guint i; + + for (i = 0; i < G_N_ELEMENTS (prefmode_tests); i++) { + GError *error = NULL; + GArray *combinations = NULL; + guint j; + guint n_expected_combinations = 0; + + for (j = 0; j < MAX_PREFMODE_COMBINATIONS; j++) { + if (prefmode_tests[i].expected_modes[j].prefmode != 0) + n_expected_combinations++; + } + + combinations = mm_huawei_parse_prefmode_test (prefmode_tests[i].str, &error); + g_assert_no_error (error); + g_assert (combinations != NULL); + g_assert_cmpuint (combinations->len, ==, n_expected_combinations); + +#if defined ENABLE_TEST_MESSAGE_TRACES + for (j = 0; j < combinations->len; j++) { + MMHuaweiPrefmodeCombination *single; + gchar *allowed_str; + gchar *preferred_str; + + single = &g_array_index (combinations, MMHuaweiPrefmodeCombination, j); + allowed_str = mm_modem_mode_build_string_from_mask (single->allowed); + preferred_str = mm_modem_mode_build_string_from_mask (single->preferred); + mm_dbg ("Test[%u], Combination[%u]: %u, \"%s\", \"%s\"", + i, + j, + single->prefmode, + allowed_str, + preferred_str); + g_free (allowed_str); + g_free (preferred_str); + } +#endif + + for (j = 0; j < combinations->len; j++) { + MMHuaweiPrefmodeCombination *single; + guint k; + gboolean found = FALSE; + + single = &g_array_index (combinations, MMHuaweiPrefmodeCombination, j); + for (k = 0; k <= n_expected_combinations; k++) { + if (single->allowed == prefmode_tests[i].expected_modes[k].allowed && + single->preferred == prefmode_tests[i].expected_modes[k].preferred && + single->prefmode == prefmode_tests[i].expected_modes[k].prefmode) { + found = TRUE; + break; + } + } + + g_assert (found == TRUE); + } + + g_array_unref (combinations); + } +} + +/*****************************************************************************/ void _mm_log (const char *loc, @@ -281,6 +405,7 @@ int main (int argc, char **argv) g_test_add_func ("/MM/huawei/ndisstatqry", test_ndisstatqry); g_test_add_func ("/MM/huawei/sysinfo", test_sysinfo); g_test_add_func ("/MM/huawei/sysinfoex", test_sysinfoex); + g_test_add_func ("/MM/huawei/prefmode", test_prefmode); return g_test_run (); } |