天天看點

GPRS子產品(MG2639)TEXT模式和PDU模式發送短消息詳解(含代碼片段)

1.使用at指令發送短消息常用Text和PDU(Protocol   Data   Unit,協定資料單元)模式。使用Text模式收發短信代碼簡單,實作起來十分容易,但最大的缺點是不能發中文短信(接收到一條短信之後使用文本模式将其讀出是完全可以的,隻是讀出的内容與使用PDU模式讀出的内容有一些差別,但正文内容是完全可以擷取到的);而PDU模式不僅支援中文短信,也能發送英文短信。PDU模式收發短信可以使用3種編碼:7-bit、8-bit和UCS2編碼。7-bit編碼用于發送普通的ASCII字元,8-bit編碼通常用于發送資料消息,UCS2編碼用于發送Unicode字元。後文将使用具體的例子結合程式中的細節來說明一下TEXT模式和PDU模式發送短信的執行個體。

假設:通過序列槽給GPRS子產品發送AT指令的函數為at_send(char *buf, int length).

2.TEXT模式發送短信

char at_cmgf[] = "at+cmgf=1\x0d";
char at_cmgs[] = "10086\x0d";
at_send(at_cmgf, sizeof(at_cmgf)-1);//set mode to TEXT mode
at_send(at_cmgs, sizeof(at_cmgs)-1);//send message length
//成功的話将會接收到">",接收到後可以輸入短信正文内容
at_send("hello, world\x1a", 12);//短信正文内容
           

如果在send短信正文内容之後沒有傳回ERROR的話那短信就發送成功了,過一會兒之後子產品會傳回“+CMGS:”開頭的一個資訊。

說明:短信正文内容之後的\x1a表示的是<ctrl/Z>的ASCII碼(如果是在序列槽調試子產品的時候,隻需要在短信内容之後按下ctrl+z鍵即可,并不需要敲回車),這個末尾是不用加\x0d的。

3.PDU模式發送短信

step1:獲得短信中心号碼&處理短信中心的号碼可以通過at指令從子產品中讀取,也可以通過在網上查詢得到,下面說一下用at指令從子產品中讀取的方法:

char at_csca[] = "at+csca?\x0d";
at_send(at_csca, sizeof(at_csca)-1);//短信中心的号碼就在傳回的内容中
           

假如擷取到的短信中心的号碼是:8613800230500計算短信中心号碼長度,如果是奇數,那麼在這個号碼的末尾加上一個f(大小寫都可以),然後在将号碼奇數位和偶數位交換。8613800230500-->8613800230500f-->683108200305f0

然後在上面處理過的短信中心前面加上91(91是國際型)得到:91683108200305f0

短信中心号碼處理的最後一步是在上面的結果前面加上短信中心的長度,長度的計算是91683108200305f0的長度除以2,這裡是16/2=8(十六進制)。

因為這個長度占兩個位元組,是以這裡自然就成了08,是以短信中心号碼處理的最後結果是0891683108200305f0。

step2:手機号碼的處理&處理

假設接收方的手機号碼為:13512121212

前面的處理類似于短信中心号碼,也是計算長度的奇偶然後判定是否要加f,最後在奇偶交換得到:3115121212f2

上面處理好的手機号碼前面加上81(表示國内的号碼)得到:813115121212f2

上一步的結果前面加上手機号碼的長度(真實長度,不包括81以及f),這裡是11位,是以為0b得到:0b813115121212f2

上一步的前面再加上00,1個位元組表示移動台向短消息服務中心送出的短消息序号從0到255一般移動子產品會自動改動是以預設為00 。

step3:編碼格式以及有效時間設定

一般使用0008a7即可,00表示是短消息傳輸層作為高層協定參考或者是遠端裝置協同工作的标示需要服務商支援但是00H是所有服務商都支援的。

08表示編碼方式為:UCS2編碼0等級,這個編碼方式可以傳輸中文。

a7表示短信的有效時間(發送短信都會到短信中心中轉,如果對方無法接收短信,比如關機,超過這個有效時間之後短信中心則會丢棄這條短信)

12小時+(VP-143)*30分鐘,這裡的VP值就是a7

step4:短消息正文

字元串轉換為Unicode代碼,例如“你好”的unicode代碼為 4F60597D,

前面加上短信内容長度:這裡為8/2=4(十六進制)得到044F60597D以上四步完成,短信内容就已經OK了,就隻剩下發送了。

step5:短信的發送

char at_cmgf[] = "at+cmgf=0\x0d";//設定為PDU模式
char at_cmgs[] = "at+cmgs=00\x0d";//短信的長度,後面會把00重新指派
char at_msg[] = "0891683108200305f011000b813115121212f20008a7044F60597D\x1a";
at_cmgs[8] = '1';
at_cmgs[9] = '8';
at_send(at_cmgf, sizeof(at_cmgf)-1);
at_send(at_cmgs, sizeof(at_cmgs)-1);//如果成功會傳回'>'
           
at_send(at_msg, sizeof(at_msg)-1);
           

發送成功的話效果與TEXT模式相同。

說明:這裡的發送長度被設定為了18(這裡是十進制),關于18的計算過程如下step2+step3+step4的長度之和除以2-->36/2=18

PDU模式的格式詳情可以參考:http://blog.csdn.net/zixu/article/details/1527208

繼續閱讀