[svn-commits] mnicholson: branch mnicholson/chan-mobile-refactor r801 - /team/mnicholson/ch...

SVN commits to the Digium repositories svn-commits at lists.digium.com
Fri Mar 13 11:07:52 CDT 2009


Author: mnicholson
Date: Fri Mar 13 11:07:49 2009
New Revision: 801

URL: http://svn.digium.com/svn-view/asterisk-addons?view=rev&rev=801
Log:
Added more hfp helper functions and started using them.

Modified:
    team/mnicholson/chan-mobile-refactor/channels/chan_mobile.c

Modified: team/mnicholson/chan-mobile-refactor/channels/chan_mobile.c
URL: http://svn.digium.com/svn-view/asterisk-addons/team/mnicholson/chan-mobile-refactor/channels/chan_mobile.c?view=diff&rev=801&r1=800&r2=801
==============================================================================
--- team/mnicholson/chan-mobile-refactor/channels/chan_mobile.c (original)
+++ team/mnicholson/chan-mobile-refactor/channels/chan_mobile.c Fri Mar 13 11:07:49 2009
@@ -352,6 +352,8 @@
 static int hfp_wait(struct hfp_pvt *pvt);
 static int hfp_parse_ciev(struct hfp_pvt *pvt, char *buf, int *value);
 static char *hfp_parse_clip(struct hfp_pvt *pvt, char *buf);
+static int hfp_parse_cmti(struct hfp_pvt *pvt, char *buf);
+static int hfp_parse_cmgr(struct hfp_pvt *pvt, char *buf, char **from_number, char **text);
 
 static int hfp_brsf2int(struct hfp_hf *hf);
 static struct hfp_ag *hfp_int2brsf(int brsf, struct hfp_ag *ag);
@@ -368,7 +370,12 @@
 static int hfp_send_dtmf(struct hfp_pvt *pvt, char digit);
 static int hfp_send_cmgf(struct hfp_pvt *pvt, int mode);
 static int hfp_send_cnmi(struct hfp_pvt *pvt);
+static int hfp_send_cmgr(struct hfp_pvt *pvt, int index);
+static int hfp_send_cmgs(struct hfp_pvt *pvt, const char *number);
+static int hfp_send_sms_text(struct hfp_pvt *pvt, const char *message);
 static int hfp_send_chup(struct hfp_pvt *pvt);
+static int hfp_send_atd(struct hfp_pvt *pvt, const char *number);
+static int hfp_send_ata(struct hfp_pvt *pvt);
 
 static int hfp_read_brsf(struct hfp_pvt *pvt);
 static int hfp_read_cind(struct hfp_pvt *pvt);
@@ -398,6 +405,8 @@
 	AT_CIND,
 	AT_CIEV,
 	AT_CLIP,
+	AT_CMTI,
+	AT_CMGR,
 	AT_CKPD,
 	AT_VGM,
 	AT_VGS,
@@ -897,7 +906,7 @@
 
 	pvt = ast->tech_pvt;
 
-	rfcomm_write(pvt->rfcomm_socket, "ATA\r");
+	hfp_send_ata(pvt->hfp);
 
 	ast_setstate(ast, AST_STATE_UP);
 
@@ -1650,6 +1659,8 @@
 		return AT_CKPD;
 	} else if (!strcmp("> ", buf)) {
 		return AT_SMS_PROMPT;
+	} else if (at_match_prefix(buf, "+CMTI:")) {
+		return AT_CMTI;
 	} else if (at_match_prefix(buf, "+CIEV:")) {
 		return AT_CIEV;
 	} else if (at_match_prefix(buf, "+BRSF:")) {
@@ -1872,6 +1883,94 @@
 }
 
 /*
+ * \brief Parse a CMTI notification.
+ * \param pvt an hfp_pvt struct
+ * \param buf the buffer to parse (null terminated)
+ * @note buf will be modified when the CMTI message is parsed
+ * \return -1 on error (parse error) or the index of the new sms message
+ */
+static int hfp_parse_cmti(struct hfp_pvt *pvt, char *buf) {
+	int index;
+	char mem[8];
+
+	/* parse cmti info in the following format:
+	 * +CMTI: <mem>,<index> 
+	 */
+	if (!sscanf(buf, "+CMTI: %7s,%d", mem, &index)) {
+		ast_debug(2, "[%s] error parsing CMTI event '%s'\n", pvt->owner->id, buf);
+		return -1;
+	}
+
+	return index;
+}
+
+/*
+ * \brief Parse a CMGR message.
+ * \param pvt an hfp_pvt struct
+ * \param buf the buffer to parse (null terminated)
+ * \param from_number a pointer to a char pointer which will store the from
+ * number
+ * \param text a pointer to a char pointer which will store the message text
+ * @note buf will be modified when the CMGR message is parsed
+ * \retval -1 parse error
+ * \retval 0 success
+ */
+static int hfp_parse_cmgr(struct hfp_pvt *pvt, char *buf, char **from_number, char **text)
+{
+	int i, state;
+	size_t s;
+
+	/* parse cmgr info in the following format:
+	 * +CMGR: <msg status>,"+123456789",...\r\n
+	 * <message text>
+	 */
+	state = 0;
+	s = strlen(buf);
+	for (i = 0; i < s && s != 6; i++) {
+		switch (state) {
+		case 0: /* search for start of the number section (,) */
+			if (buf[i] == ',') {
+				state++;
+			}
+			break;
+		case 1: /* find the opening quote (") */
+			if (buf[i] == '"') {
+				state++;
+			}
+		case 2: /* mark the start of the number */
+			if (from_number) {
+				*from_number = &buf[i];
+				state++;
+			}
+			break;
+		case 3: /* search for the end of the number (") */
+			if (buf[i] == '"') {
+				buf[i] = '\0';
+				state++;
+			}
+			break;
+		case 4: /* search for the start of the message text (\n) */
+			if (buf[i] == '\n') {
+				state++;
+			}
+			break;
+		case 5: /* mark the start of the message text */
+			if (text) {
+				*text = &buf[i];
+				state++;
+			}
+			break;
+		}
+	}
+
+	if (state != 6) {
+		return -1;
+	}
+
+	return 0;
+}
+
+/*
  * \brief Convert a hfp_hf struct to a BRSF int.
  */
 static int hfp_brsf2int(struct hfp_hf *hf)
@@ -2044,12 +2143,69 @@
 }
 
 /*
+ * \brief Read an SMS message.
+ * \param pvt an hfp_pvt struct
+ * \param index the location of the requested message
+ */
+static int hfp_send_cmgr(struct hfp_pvt *pvt, int index)
+{
+	char cmd[32];
+	snprintf(cmd, sizeof(cmd), "AT+CMGR=%d\r", index);
+	return rfcomm_write(pvt->rsock, cmd);
+}
+
+/*
+ * \brief Start sending an SMS message.
+ * \param pvt an hfp_pvt struct
+ * \param number the destination of the message
+ */
+static int hfp_send_cmgs(struct hfp_pvt *pvt, const char *number)
+{
+	char cmd[64];
+	snprintf(cmd, sizeof(cmd), "AT+CMGS=\"%s\"\r", number);
+	return rfcomm_write(pvt->rsock, cmd);
+}
+
+/*
+ * \brief Send the text of an SMS message.
+ * \param pvt an hfp_pvt struct
+ * \param message the text of the message
+ */
+static int hfp_send_sms_text(struct hfp_pvt *pvt, const char *message)
+{
+	char cmd[162];
+	snprintf(cmd, sizeof(cmd), "%.160s\x1a", message);
+	return rfcomm_write(pvt->rsock, cmd);
+}
+
+/*
  * \brief Send AT+CHUP.
  * \param pvt an hfp_pvt struct
  */
 static int hfp_send_chup(struct hfp_pvt *pvt)
 {
 	return rfcomm_write(pvt->rsock, "AT+CHUP\r");
+}
+
+/*!
+ * \brief Send ATD.
+ * \param pvt an hfp_pvt struct
+ * \param number the number to send
+ */
+static int hfp_send_atd(struct hfp_pvt *pvt, const char *number)
+{
+	char cmd[64];
+	snprintf(cmd, sizeof(cmd), "ATD%s;\r", number);
+	return rfcomm_write(pvt->rsock, cmd);
+}
+
+/*!
+ * \brief Send ATA.
+ * \param pvt an hfp_pvt struct
+ */
+static int hfp_send_ata(struct hfp_pvt *pvt)
+{
+	return rfcomm_write(pvt->rsock, "ATA\r");
 }
 
 /*
@@ -2458,9 +2614,8 @@
 	char buf[256];
 	char cid_num[AST_MAX_EXTENSION], *clip;
 	int t, i, smsi;
-	char brsf, nsmode, *p, *p1;
-	char sms_src[13];
-	char sms_txt[160];
+	char brsf, nsmode;
+	char *sms_src, *sms_txt;
 	at_message_t at_msg;
 
 	brsf = nsmode = 0;
@@ -2627,19 +2782,9 @@
 				}
 				break;
 			case MBL_STATE_INSMS:
-				if (strstr(buf, "+CMGR:")) {
-					memset(sms_src, 0x00, sizeof(sms_src));
-					if ((p = strchr(buf, ','))) {
-						if (*(++p) == '"')
-							p++;
-						if ((p1 = strchr(p, ','))) {
-							if (*(--p1) == '"')
-								p1--;
-							memset(sms_src, 0x00, sizeof(sms_src));
-							strncpy(sms_src, p, p1 - p + 1);
-						}
-					}
-				} else if (strstr(buf, "OK")) {
+				if (at_msg == AT_CMGR) {
+					hfp_parse_cmgr(hfp, buf, &sms_src, &sms_txt);
+				} else if (at_msg == AT_OK) {
 					chn = mbl_new(AST_STATE_DOWN, pvt, NULL);
 					strcpy(chn->exten, "sms");
 					pbx_builtin_setvar_helper(chn, "SMSSRC", sms_src);
@@ -2647,10 +2792,7 @@
 					if (ast_pbx_start(chn))
 						ast_log(LOG_ERROR, "Unable to start pbx on incoming sms.\n");
 					pvt->state = MBL_STATE_IDLE;
-				} else {
-					ast_copy_string(sms_txt, buf, sizeof(sms_txt));
-				}
-				break;
+				}				break;
 			case MBL_STATE_OUTSMS:
 				break;
 			case MBL_STATE_OUTSMS1:
@@ -2663,15 +2805,10 @@
 			}
 			/* Unsolicited responses */
 
- 			if (strstr(buf, "+CMTI:")) {	/* SMS Incoming... */
-				if ((p = strchr(buf, ','))) {
-					p++;
-					smsi = atoi(p);
-					if (smsi > 0) {
-						snprintf(buf, sizeof(buf), "AT+CMGR=%d\r", smsi);
-						rfcomm_write(pvt->rfcomm_socket, buf);
-						pvt->state = MBL_STATE_INSMS;
-					}
+ 			if (at_msg == AT_CMTI) {	/* SMS Incoming... */
+				if ((smsi = hfp_parse_cmti(hfp, buf)) > 0) {
+					hfp_send_cmgr(hfp, smsi);
+					pvt->state = MBL_STATE_INSMS;
 				}
 			}
 
@@ -2687,8 +2824,7 @@
 				ast_verb(3, "Bluetooth Device %s initialised and ready.\n", pvt->id);
 				pvt->state = MBL_STATE_IDLE;
 			} else if (pvt->state == MBL_STATE_DIAL) {
-				snprintf(buf, sizeof(buf), "ATD%s;\r", pvt->dial_number);
-				if (rfcomm_write(pvt->rfcomm_socket, buf)) {
+				if (hfp_send_atd(hfp, pvt->dial_number)) {
 					ast_log(LOG_ERROR, "Dial failed on %s state %d\n", pvt->owner->name, pvt->state);
 					ast_queue_control(pvt->owner, AST_CONTROL_CONGESTION);
 					pvt->state = MBL_STATE_IDLE;
@@ -2713,13 +2849,11 @@
 				} else
 					pvt->state = MBL_STATE_IDLE;
 			} else if (pvt->state == MBL_STATE_OUTSMS) {
-				snprintf(buf, sizeof(buf), "AT+CMGS=\"%s\"\r", pvt->dial_number);
-				rfcomm_write(pvt->rfcomm_socket, buf);
+				hfp_send_cmgs(hfp, pvt->dial_number);
 				pvt->state = MBL_STATE_OUTSMS1;
 			} else if (pvt->state == MBL_STATE_OUTSMS1) {
 				if (!strcmp(buf, "> ")) {
-					snprintf(buf, sizeof(buf), "%s%c", pvt->sms_txt, 0x1a);
-					rfcomm_write(pvt->rfcomm_socket, buf);
+					hfp_send_sms_text(hfp, pvt->sms_txt);
 					pvt->state = MBL_STATE_OUTSMS2;
 				} else {
 					ast_log(LOG_ERROR, "Failed to send SMS to %s on device %s\n", pvt->dial_number, pvt->id);




More information about the svn-commits mailing list