diff options
-rw-r--r-- | include/libgsmd/misc.h | 8 | ||||
-rw-r--r-- | include/libgsmd/sms.h | 2 | ||||
-rw-r--r-- | src/gsmd/usock.c | 71 | ||||
-rw-r--r-- | src/libgsmd/libgsmd_network.c | 34 | ||||
-rw-r--r-- | src/util/shell.c | 29 |
5 files changed, 93 insertions, 51 deletions
diff --git a/include/libgsmd/misc.h b/include/libgsmd/misc.h index 554d958..088f624 100644 --- a/include/libgsmd/misc.h +++ b/include/libgsmd/misc.h @@ -34,14 +34,6 @@ extern int lgsm_pin_auth(struct lgsm_handle *lh, const char *pin); /* Get Signal Strehngth (Chapter 8.5) */ extern int lgsm_signal_quality(struct lgsm_handle *h); -/* Set voice mail number */ -extern int lgsm_voicemail_set(struct lgsm_handle *lh, - struct lgsm_addr *addr); - -/* Get currently configured voice mail number */ -extern int lgsm_voicemail_get(struct lgsm_handle *lh, - struct lgsm_addr *addr); - /* Operator Selection, Network Registration */ extern int lgsm_oper_get(struct lgsm_handle *lh); extern int lgsm_opers_get(struct lgsm_handle *lh); diff --git a/include/libgsmd/sms.h b/include/libgsmd/sms.h index 9808442..4575fd9 100644 --- a/include/libgsmd/sms.h +++ b/include/libgsmd/sms.h @@ -79,6 +79,8 @@ extern int lgsm_sms_get_storage(struct lgsm_handle *lh); extern int lgsm_sms_set_storage(struct lgsm_handle *lh, enum ts0705_mem_type mem1, enum ts0705_mem_type mem2, enum ts0705_mem_type mem3); +extern int lgsm_number2addr(struct gsmd_addr *dst, const char *src, + int skipplus); /* Retrieve current default service centre address */ extern int lgsm_sms_get_smsc(struct lgsm_handle *lh); diff --git a/src/gsmd/usock.c b/src/gsmd/usock.c index 80f2e01..c7a0224 100644 --- a/src/gsmd/usock.c +++ b/src/gsmd/usock.c @@ -520,55 +520,38 @@ static int usock_rcv_modem(struct gsmd_user *gu, struct gsmd_msg_hdr *gph, static int network_vmail_cb(struct gsmd_atcmd *cmd, void *ctx, char *resp) { struct gsmd_user *gu = ctx; - struct gsmd_voicemail *vmail; - struct gsmd_ucmd *ucmd; - char *comma; - - DEBUGP("entering(cmd=%p, gu=%p)\n", cmd, gu); + struct gsmd_voicemail vmail; + struct gsm_extrsp *er; + int rc; + int ret = cmd->ret; - ucmd = ucmd_alloc(sizeof(*vmail)); - if (!ucmd) - return -ENOMEM; - - /* FIXME: pass error values back somehow */ - ucmd->hdr.version = GSMD_PROTO_VERSION; - ucmd->hdr.msg_type = GSMD_MSG_NETWORK; - ucmd->hdr.len = sizeof(*vmail); - ucmd->hdr.id = cmd->id; + DEBUGP("cmd = '%s', resp: '%s'\n", cmd->buf, resp); if (cmd->buf[7] == '=') { /* response to set command */ - ucmd->hdr.msg_subtype = GSMD_NETWORK_VMAIL_SET; - /* FIXME: */ - return 0; + rc = gsmd_ucmd_submit(gu, GSMD_MSG_NETWORK, + GSMD_NETWORK_VMAIL_SET,cmd->id, sizeof(ret), &ret); } else { /* response to get command */ - char *tok = strtok(resp, ","); - if (!tok) - goto out_free_einval; - ucmd->hdr.msg_subtype = GSMD_NETWORK_VMAIL_GET; - vmail->enable = atoi(tok); - - tok = strtok(NULL, ","); - if (!tok) - goto out_free_einval; - strncpy(vmail->addr.number, tok, GSMD_ADDR_MAXLEN); - vmail->addr.number[GSMD_ADDR_MAXLEN] = '\0'; - - tok = strtok(NULL, ","); - if (!tok) - goto out_free_einval; - vmail->addr.type = atoi(tok); + if (strncmp(resp, "+CSVM: ", 7)) + return -EINVAL; + resp += 7; + er = extrsp_parse(gsmd_tallocs, resp); + if(!er) + return -ENOMEM; + if(er->num_tokens == 3 && + er->tokens[0].type == GSMD_ECMD_RTT_NUMERIC && + er->tokens[1].type == GSMD_ECMD_RTT_STRING && + er->tokens[2].type == GSMD_ECMD_RTT_NUMERIC) { + vmail.enable = er->tokens[0].u.numeric; + strcpy(vmail.addr.number, er->tokens[1].u.string); + vmail.addr.type = er->tokens[2].u.numeric; + } + rc = gsmd_ucmd_submit(gu, GSMD_MSG_NETWORK, GSMD_NETWORK_VMAIL_GET, + cmd->id, sizeof(vmail), &vmail); + talloc_free(er); } - - usock_cmd_enqueue(ucmd, gu); - - return 0; - -out_free_einval: - gsmd_log(GSMD_ERROR, "can't understand voicemail response\n"); - talloc_free(ucmd); - return -EINVAL; + return rc; } int gsmd_ucmd_submit(struct gsmd_user *gu, u_int8_t msg_type, @@ -813,7 +796,9 @@ static int usock_rcv_network(struct gsmd_user *gu, struct gsmd_msg_hdr *gph, cmd = atcmd_fill("AT+CSVM?", 8+1, &network_vmail_cb, gu, 0, NULL); break; case GSMD_NETWORK_VMAIL_SET: - cmd = atcmd_fill("AT+CSVM=", 8+1, &network_vmail_cb, gu, 0, NULL); + cmdlen = sprintf(buffer, "AT+CSVM=1,\"%s\",%d", + vmail->addr.number, vmail->addr.type); + cmd = atcmd_fill(buffer, cmdlen + 1, &network_vmail_cb, gu, 0, NULL); break; case GSMD_NETWORK_SIGQ_GET: cmd = atcmd_fill("AT+CSQ", 6+1, &network_sigq_cb, gu, 0, NULL); diff --git a/src/libgsmd/libgsmd_network.c b/src/libgsmd/libgsmd_network.c index 333debd..5551de3 100644 --- a/src/libgsmd/libgsmd_network.c +++ b/src/libgsmd/libgsmd_network.c @@ -26,6 +26,7 @@ #include <libgsmd/libgsmd.h> #include <libgsmd/misc.h> +#include <libgsmd/sms.h> #include <gsmd/usock.h> #include <gsmd/event.h> @@ -133,3 +134,36 @@ int lgsm_get_subscriber_num(struct lgsm_handle *lh) { return lgsm_send_simple(lh, GSMD_MSG_NETWORK, GSMD_NETWORK_GET_NUMBER); } + +int lgsm_voicemail_set(struct lgsm_handle *lh, const char *number) +{ + struct gsmd_msg_hdr *gmh; + struct gsmd_voicemail *vmail; + int rc; + + gmh = lgsm_gmh_fill(GSMD_MSG_NETWORK, + GSMD_NETWORK_VMAIL_SET, sizeof(*vmail)); + if (!gmh) + return -ENOMEM; + + vmail = (struct gsmd_voicemail *) gmh->data; + vmail->enable = 1; + if (lgsm_number2addr(&vmail->addr, number, 0)){ + lgsm_gmh_free(gmh); + return -EINVAL; + } + + if (lgsm_send(lh, gmh) < gmh->len + sizeof(*gmh)) { + lgsm_gmh_free(gmh); + return -EIO; + } + + lgsm_gmh_free(gmh); + return 0; +} + +/* Get currently configured voice mail number */ +int lgsm_voicemail_get(struct lgsm_handle *lh) +{ + return lgsm_send_simple(lh, GSMD_MSG_NETWORK, GSMD_NETWORK_VMAIL_GET); +} diff --git a/src/util/shell.c b/src/util/shell.c index e621e33..a8109df 100644 --- a/src/util/shell.c +++ b/src/util/shell.c @@ -285,6 +285,9 @@ static int net_msghandler(struct lgsm_handle *lh, struct gsmd_msg_hdr *gmh) ((void *) gmh + sizeof(*gmh)); const struct gsmd_own_number *num = (struct gsmd_own_number *) ((void *) gmh + sizeof(*gmh)); + const struct gsmd_voicemail *vmail = (struct gsmd_voicemail *) + ((void *) gmh + sizeof(*gmh)); + int result = *(int *) gmh->data; static const char *oper_stat[] = { [GSMD_OPER_UNKNOWN] = "of unknown status", [GSMD_OPER_AVAILABLE] = "available", @@ -341,6 +344,18 @@ static int net_msghandler(struct lgsm_handle *lh, struct gsmd_msg_hdr *gmh) "" : " services"); pending_responses --; break; + case GSMD_NETWORK_VMAIL_SET: + if (result) + printf("Set voicemail error %i\n", result); + else + printf("Set voicemail OK \n"); + pending_responses --; + break; + case GSMD_NETWORK_VMAIL_GET: + if(vmail->addr.number) + printf ("voicemail number is %s \n",vmail->addr.number); + pending_responses --; + break; default: return -EINVAL; } @@ -481,6 +496,8 @@ static int shell_help(void) "\tsM\tSMS Set preferred storage (sM=mem1,mem2,mem3)\n" "\tsc\tSMS Show Service Centre\n" "\tsC\tSMS Set Service Centre (sC=number)\n" + "\tgvm\tGet Voicemail number\n" + "\tsvm\tSet Voicemail number(svm=number)\n" "\tim\tGet imsi\n" "\tcs\tGet Call status\n" "\tgp\tGet PIN status\n" @@ -766,6 +783,18 @@ int shell_main(struct lgsm_handle *lgsmh, int sync) } else if (!strcmp(buf, "n")) { lgsm_get_subscriber_num(lgsmh); pending_responses ++; + } else if ( !strncmp(buf, "gvm", 3)) { + printf("Get Voicemail Number\n"); + lgsm_voicemail_get(lgsmh); + pending_responses ++; + } else if ( !strncmp(buf, "svm", 3)) { + printf("Set Voicemail Number\n"); + ptr = strchr(buf, '='); + if (!ptr || strlen(ptr) < 3) + printf("No.\n"); + else + lgsm_voicemail_set(lgsmh, ptr + 1); + pending_responses ++; } else if (!strncmp(buf, "im", 2)) { printf("Get imsi\n"); lgsm_get_imsi(lgsmh); |