diff options
author | John Klug <john.klug@multitech.com> | 2023-01-10 16:40:41 -0600 |
---|---|---|
committer | John Klug <john.klug@multitech.com> | 2023-01-10 16:40:41 -0600 |
commit | a64a1538c6576eccfb841861cd9acf9b22c732d8 (patch) | |
tree | 00031ede7deeb96674eb000a336179f22ad32710 /src/atcmd.c | |
parent | c97e4dad4fa1720cc510d44b404a1727907c22a5 (diff) | |
parent | 78a27efb55e1c509604fe9d96f8c421d6b1bda36 (diff) | |
download | sms-utils-831174d10eba9a6a8e5973e45d9308f7040f3dc2.tar.gz sms-utils-831174d10eba9a6a8e5973e45d9308f7040f3dc2.tar.bz2 sms-utils-831174d10eba9a6a8e5973e45d9308f7040f3dc2.zip |
[GP-1842] Update the Cellular code to use SIM IMSI for Verizon detection
See merge request !14
Diffstat (limited to 'src/atcmd.c')
-rw-r--r-- | src/atcmd.c | 227 |
1 files changed, 159 insertions, 68 deletions
diff --git a/src/atcmd.c b/src/atcmd.c index b988a57..d17c03f 100644 --- a/src/atcmd.c +++ b/src/atcmd.c @@ -873,17 +873,17 @@ int atcmd_plus_cpms_read(int fd, struct data_store *read_store, char *token; int tmp; int i; - int data_stores_size; + int data_stores_size; struct data_store *store; - struct data_store *data_stores[] = {read_store, send_store, new_store}; + struct data_store *data_stores[] = {read_store, send_store, new_store}; - if (isCdmaTypeModel()) { - data_stores_size = 2; - } - else { - data_stores_size = 3; - } + if (is_telit_3gpp2_format()) { + data_stores_size = 2; + } + else { + data_stores_size = 3; + } atcmd_writeline(fd, "AT+CPMS?"); tmp = atcmd_expect_line(fd, buf, sizeof(buf), "+CPMS: "); @@ -944,7 +944,7 @@ int atcmd_plus_cpms_test(int fd, struct store_locations *read_loc, int tmp; int i, j; - struct store_locations *locations[] = {read_loc, send_loc, new_loc}; + struct store_locations *locations[] = {read_loc, send_loc, new_loc}; struct store_locations *loc; atcmd_writeline(fd, "AT+CPMS=?"); @@ -1006,14 +1006,14 @@ int atcmd_plus_cpms_write(int fd, const char *read_name, char buf[ATCMD_LINE_SIZE]; int tmp; - if (isCdmaTypeModel()) { - atcmd_writeline(fd, "AT+CPMS=\"%s\",\"%s\"", read_name, send_name); - } - else - { - atcmd_writeline(fd, "AT+CPMS=\"%s\",\"%s\",\"%s\"", - read_name, send_name, new_name); - } + if (is_telit_3gpp2_format()) { + atcmd_writeline(fd, "AT+CPMS=\"%s\",\"%s\"", read_name, send_name); + } + else + { + atcmd_writeline(fd, "AT+CPMS=\"%s\",\"%s\",\"%s\"", + read_name, send_name, new_name); + } tmp = atcmd_expect_line(fd, buf, sizeof(buf), "OK"); if (tmp <= 0) { log_debug("expected OK but it was not received"); @@ -1224,15 +1224,15 @@ int atcmd_plus_gmm_read(int fd) int tmp; atcmd_writeline(fd, "AT+GMM"); - //Swallow extra "\r\n" - tmp = atcmd_readline(fd, buf, sizeof(buf)); + //Swallow extra "\r\n" + tmp = atcmd_readline(fd, buf, sizeof(buf)); if (tmp <= 0) { log_debug("expected \\r\\n but it was not received"); return -1; } - //Read model string - tmp = atcmd_readline(fd, buf, sizeof(buf)); + //Read model string + tmp = atcmd_readline(fd, buf, sizeof(buf)); if (tmp <= 0) { log_debug("expected model but it was not received"); return -1; @@ -1300,7 +1300,7 @@ int atcmd_plus_gmi_read(int fd) return 0; } -/* ICCID needed for LNA3 to determine carrier */ +/* ICCID needed to detect Verizon on multi-carrier radios */ int atcmd_plus_iccid_read(int fd) { char buf[ATCMD_LINE_SIZE]; @@ -1313,7 +1313,7 @@ int atcmd_plus_iccid_read(int fd) if (is_telit_model()) { command = "AT#CCID"; if (strstr(Global.core.model, "FN980")) { - command = "AT+ICCID"; + command = "AT+ICCID"; } } else if (is_quectel_model()) { command = "AT+QCCID"; @@ -1323,18 +1323,18 @@ int atcmd_plus_iccid_read(int fd) } atcmd_writeline(fd, command); - //Swallow extra "\r\n" - tmp = atcmd_readline(fd, buf, sizeof(buf)); + //Swallow extra "\r\n" + tmp = atcmd_readline(fd, buf, sizeof(buf)); if (tmp <= 0) { log_debug("expected \\r\\n but it was not received"); return -1; } - //Read iccid string - tmp = atcmd_readline(fd, buf, sizeof(buf)); + //Read iccid string + tmp = atcmd_readline(fd, buf, sizeof(buf)); if (tmp <= 0) { log_debug("expected ICCID but it was not received"); - /* Currently only LNA3 models will need the ICCID */ + /* Currently only LNA3 models will need the ICCID */ return -1; } @@ -1342,12 +1342,12 @@ int atcmd_plus_iccid_read(int fd) log_debug("buf=%s for %d", buf,strlen(buf)); token = atcmd_value_tok(&save); if (!token) { - log_debug("atcmd_value_tok model"); + log_debug("atcmd_value_tok iccid"); return -1; } else { log_debug("token is %s",token); } - tmp_buf = strrchr(token,' '); + tmp_buf = strrchr(token,' '); if (tmp_buf) { token = ++tmp_buf; log_debug("Found blank, incrementing tmp"); @@ -1371,6 +1371,65 @@ int atcmd_plus_iccid_read(int fd) return 0; } +/* IMSI needed to detect Verizon when the ICCID is unrecognized */ +int atcmd_plus_imsi_read(int fd) +{ + char buf[ATCMD_LINE_SIZE]; + char *save; + char *token; + int tmp; + char *tmp_buf; + char* command = "AT+CIMI"; + + atcmd_writeline(fd, command); + //Swallow extra "\r\n" + tmp = atcmd_readline(fd, buf, sizeof(buf)); + if (tmp <= 0) { + log_debug("expected \\r\\n but it was not received"); + return -1; + } + + //Read imsi string + tmp = atcmd_readline(fd, buf, sizeof(buf)); + if (tmp <= 0) { + log_debug("expected IMSI but it was not received"); + /* Currently only LNA7/LNA7D/L4G1 models will need the IMSI */ + return -1; + } + + save = buf; + log_debug("buf=%s for %d", buf,strlen(buf)); + token = atcmd_value_tok(&save); + if (!token) { + log_debug("atcmd_value_tok imsi"); + return -1; + } else { + log_debug("token is %s",token); + } + tmp_buf = strrchr(token,' '); + if (tmp_buf) { + token = ++tmp_buf; + log_debug("Found blank, incrementing tmp"); + } else { + tmp_buf = strrchr(token,'\t'); + log_debug("Found tab, incrementing tmp"); + if(tmp_buf) + token = ++tmp_buf; + } + log_debug("token[0]=%2.2x token[1]=%2.2x",token[0],token[1]); + strncpy(Global.core.imsi, token, IMSI_LEN); + + log_debug("imsi: %s", Global.core.imsi); + + tmp = atcmd_expect_line(fd, buf, sizeof(buf), "OK"); + if (tmp <= 0) { + log_debug("expected OK but it was not received"); + return -1; + } + + return 0; +} + int atcmd_init(int fd, int read_timeout) { int tmp; @@ -1421,19 +1480,25 @@ static int sms_atcmd_init(int fd) tmp = atcmd_plus_gmm_read(fd); if (tmp < 0) { - log_error("failed to read radio model"); + log_error("failed to read radio model"); return -1; } tmp = atcmd_plus_gmi_read(fd); if (tmp < 0) { - log_error("failed to read radio manufacturer"); + log_error("failed to read radio manufacturer"); + return -1; + } + + tmp = atcmd_plus_iccid_read(fd); + if (tmp < 0) { + log_error("failed to read SIM ICCID"); return -1; } - tmp = atcmd_plus_iccid_read(fd); + tmp = atcmd_plus_imsi_read(fd); if (tmp < 0) { - log_error("failed to read SIM ICCID"); + log_error("failed to read SIM IMSI"); return -1; } @@ -1446,22 +1511,22 @@ static int sms_atcmd_init(int fd) memset(&send_store, 0, sizeof(send_store)); memset(&new_store, 0, sizeof(new_store)); - if (!strcmp(Global.core.model, "CE910-DUAL") || !strcmp(Global.core.model, "DE910-DUAL")) { - log_info("Changing message storage locations to ME for CE/DE910-DUAL"); - free(Global.core.msg_store_read); - free(Global.core.msg_store_send); - free(Global.core.pb_store); - Global.core.msg_store_read = strdup("ME"); - Global.core.msg_store_send = strdup("ME"); - Global.core.pb_store = strdup("ME"); - } + if (!strcmp(Global.core.model, "CE910-DUAL") || !strcmp(Global.core.model, "DE910-DUAL")) { + log_info("Changing message storage locations to ME for CE/DE910-DUAL"); + free(Global.core.msg_store_read); + free(Global.core.msg_store_send); + free(Global.core.pb_store); + Global.core.msg_store_read = strdup("ME"); + Global.core.msg_store_send = strdup("ME"); + Global.core.pb_store = strdup("ME"); + } atcmd_plus_cpms_test(fd, &read_store.choices, &send_store.choices, &new_store.choices); atcmd_plus_cpms_read(fd, &read_store.selected, &send_store.selected, &new_store.selected, Global.core.model); if (Global.core.msg_store_read && Global.core.msg_store_send && - Global.core.msg_store_new) { + Global.core.msg_store_new) { if (!msg_store_choice(&read_store, Global.core.msg_store_read)) { log_error("message storage location %s is not a choice", @@ -1474,8 +1539,8 @@ static int sms_atcmd_init(int fd) return -1; } - //Doesn't apply to CDMA type radios - if (!isCdmaTypeModel() && !msg_store_choice(&new_store, Global.core.msg_store_new)) { + //Doesn't apply to CDMA type radios + if (!is_telit_3gpp2_format() && !msg_store_choice(&new_store, Global.core.msg_store_new)) { log_error("message storage location %s is not a choice", Global.core.msg_store_new); return -1; @@ -1543,45 +1608,71 @@ int sms_device_open(void) return fd; } -int is_vzw_lte(void) +/* Detect Telit LTE radios that use the 3GPP2 SMS format for Verizon */ +int is_telit_lte_vzw_3gpp2_format(void) { - if (!strcmp(Global.core.model, "LE910-NA1")) { - log_debug("Found LE910-NA1"); - /* Verizon Wireless SIM */ - if (strncmp(Global.core.iccid,"891480",6) == 0) { - log_debug("Found VZW SIM"); - return 1; - } - } - - return (!strncmp(Global.core.model, "LE910-SVG", MODEL_LEN) || - !strncmp(Global.core.model, "LE910-SV1", MODEL_LEN)); + if (!strcmp(Global.core.model, "LE910-NA1")) { + log_debug("Found LE910-NA1"); + /* Verizon Wireless SIM */ + if (strncmp(Global.core.iccid,"891480",6) == 0) { + log_debug("Found VZW SIM"); + return 1; + } + } + + return (!strncmp(Global.core.model, "LE910-SVG", MODEL_LEN) || + !strncmp(Global.core.model, "LE910-SV1", MODEL_LEN)); } -/* Detect LNA7/L4G1 radio with Verizon SIM */ -int is_quectel_dual_sms_format(void) +/* Detect LNA7/LNA7D/L4G1 radios with Verizon SIM that support both 3GPP and 3GPP2 */ +int is_quectel_dual_format(void) { if (!strncmp(Global.core.model, "EG95", MODEL_LEN) || !strncmp(Global.core.model, "EG25", MODEL_LEN)) { log_debug("Found Quectel radio with dual SMS format support"); - /* Verizon Wireless SIM */ + + /* Verizon Wireless SIM ICCID */ if (strncmp(Global.core.iccid,"891480",6) == 0) { - log_debug("Found VZW SIM"); + log_debug("Found VZW SIM by ICCID"); return 1; } + + /* Extract PLMN ID - the first 5 or 6 digits of IMSI. + Assume 6 digits for Verizon. + NOTE: Other carriers may use shorter codes */ + char plmn_id_str[PLMN_ID_SIZE_VZW] = {0}; + strncpy(plmn_id_str, Global.core.imsi, PLMN_ID_LEN_VZW); + + /* Parse as integer for easier comparison */ + int plmn_id_num = atoi(plmn_id_str); + + /* Verizon Wireless SIM MCC/MNC */ + switch (plmn_id_num) { + case 310590: + case 310890: + case 311270: + case 311480: + case 312770: + log_debug("Found VZW SIM by IMSI"); + return 1; + default: + /* ignore, not Verizon */ + break; + }; } return 0; } -int isCdmaTypeModel() +/* Detect Telit LTE and CDMA radios that use the 3GPP2 SMS format for Verizon */ +int is_telit_3gpp2_format() { - /* Test for possible dual firmware model */ - if (is_vzw_lte()) - return 1; + /* Test for possible dual firmware model */ + if (is_telit_lte_vzw_3gpp2_format()) + return 1; - return (!strncmp(Global.core.model, "DE910-DUAL", MODEL_LEN) || - !strncmp(Global.core.model, "CE910-DUAL", MODEL_LEN)); + return (!strncmp(Global.core.model, "DE910-DUAL", MODEL_LEN) || + !strncmp(Global.core.model, "CE910-DUAL", MODEL_LEN)); } int is_telit_model() |