加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 百科 > 正文

Code Segment about PDU

发布时间:2020-12-12 23:31:40 所属栏目:百科 来源:网络整理
导读:/* * ===================================================================================== * * Filename: gmesg.c * * ===================================================================================== */ /* 头文件开始 1.编码转换需要iconv

/*

* =====================================================================================

*

* Filename: gmesg.c

*

* =====================================================================================

*/

/* 头文件开始 1.编码转换需要iconv.h 2.对消息内容特殊转换需要gmesg.h */

/*{{{*/

#include

#include

#include

#include

#include

#include

#include

#include

#include

#include "gmesg.h"

#include "gport.h"

#define SLEEP3S 0

/*}}}*/

/* 头文件结束 1.编码转换需要iconv.h 2.对消息内容特殊转换需要gmesg.h */

/*

* === FUNCTION ======================================================================

* Name: init_gprs_pdu

* Description: 从数据库中读出默认设置的pdu数据

* =====================================================================================

*/

/*{{{*/

int init_gprs_pdu ( struct gprs_pdu **gpdu,char *signal )

{

sqlite3 *db = NULL;

int rc,i;

char *dbname = "gprsPdu.db";

char *ErrMsg = NULL;

char **dbResult = NULL;

char sql_select[MSIZE] = { 0 };

int nrow,ncolumn;

if ( NULL == signal )

{

strcpy(sql_select,"select * from gprs_pdu where id=1");

}

else

{

sprintf(sql_select,"select * from gprs_pdu where status = /'%s/'",signal);

}

rc = sqlite3_open(dbname,&db);

if ( SQLITE_OK != rc )

{

fprintf(stderr,"Cannot open database :%s/n",sqlite3_errmsg(db));

sqlite3_close(db);

return -1;

}

rc = sqlite3_get_table (db,sql_select,&dbResult,&nrow,&ncolumn,&ErrMsg);

i = ncolumn + 1; /* 去掉id字段 */

(*gpdu) = (struct gprs_pdu *) malloc (sizeof(struct gprs_pdu));

memset(*gpdu,sizeof(struct gprs_pdu));

strcpy( (*gpdu)->sim_attr,dbResult[i] );

i++;

strcpy( (*gpdu)->sim_center,dbResult[i] );

i++;

strcpy( (*gpdu)->phone_attr,dbResult[i] );

i++;

strcpy( (*gpdu)->phone,dbResult[i] );

i++;

strcpy( (*gpdu)->fix,dbResult[i] );

i++;

strcpy( (*gpdu)->gb2312_msg,dbResult[i] );

i++;

sqlite3_free_table( dbResult );

sqlite3_close(db);

return 0;

}

/* ----- end of function init_gprs_pdu ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: clear_gprs_pdu

* Description: 清除结构体struct gprs_pdu

* =====================================================================================

*/

/*{{{*/

int clear_gprs_pdu ( struct gprs_pdu *gpdu )

{

free(gpdu);

return 0;

}

/* ----- end of function clear_gprs_pdu ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: code_convert

* Description: 代码转换:从一种编码转为另一种编码

* =====================================================================================

*/

/*{{{*/

int code_convert(char *from_charset,char *to_charset,char *inbuf,int inlen,char *outbuf,int outlen )

{

iconv_t cd; /* 字符集转换描述符 */

char **pin = &inbuf; /* 被转换的编码 */

char **pout = &outbuf; /* 转换后的编码 */

/* iconv_open 申请编码转换描述符,对系统有依赖,可以使用iconv --list查看 */

cd = iconv_open(to_charset,from_charset);

if ( cd == 0 )

{

return -1;

}

memset(outbuf,outlen);

/* iconv 实现编码转换 */

if ( iconv(cd,pin,&inlen,pout,&outlen) == -1 )

{

return -1;

}

/* 关闭编码转换描述符 */

iconv_close(cd);

return 0;

}

/* ----- end of function code_convert ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: u2g

* Description: UNICODE码转为GB2312码

* =====================================================================================

*/

/*{{{*/

int u2g ( char *inbuf,int outlen )

{

//return code_convert("unicode","utf-8",inbuf,inlen,outbuf,outlen);

/* 交叉编译后在,开发板中个人使用下面的,iconv_open对系统有依赖 */

return code_convert("UTF-16","GB2312",outlen);

}

/* ----- end of function u2g ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: g2u

* Description: GB2312码转为UNICODE码

* =====================================================================================

*/

/*{{{*/

int g2u ( char *inbuf,int outlen )

{

/* 交叉编译后在,开发板中个人使用下面的,iconv_open对系统有依赖 */

/* GB2312 -> UTF-16 转换之后,前端会有多余字节 */

return code_convert("GB2312","UTF-16",outlen);

/* GB2312 -> UCS2 主机正常,在开发板上使用时会段错误,断点在iconv_open处,可能缺少lib*/

//return code_convert("GB2312","UCS2",outlen);

}

/* ----- end of function g2u ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: bytes2string

* Description: 将字节流转换成字符串,为了PDU编码作准备

* =====================================================================================

*/

/*{{{*/

int bytes2string ( const unsigned char *pSrc,char *pDst,int nSrcLength )

{

const char tab[] = "0123456789ABCDEF";

int i;

for ( i=0; i

{

*pDst++ = tab[*pSrc >> 4]; /* 取出高4位 */

*pDst++ = tab[*pSrc & 0x0f]; /* 取出底4位 */

pSrc++;

}

/* 加上结束标志 */

*pDst = '/0';

/* 返回字符串长度,将一个字节分成两个字符,所以长度乘以2 */

return nSrcLength*2;

}

/* ----- end of function bytes2string ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: switch_byte1

* Description: 实现字符串中相邻的字符交换,为了PDU编码作准备,电话号码相邻数字交换。

* =====================================================================================

*/

/*{{{*/

int switch_byte1 ( char *src,int len )

{

int i;

char tch;

for ( i=0; i

{

tch = *(src + i + 1);

*(src + i + 1) = *(src + i);

*(src + i) = tch;

}

return len;

}

/* ----- end of function switch_byte1 ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: switch_byte2

* Description: 与编码有关的函数,经过iconv转换(GB2312 -> UTF-16)的编码,再经字节流转变成字符串后,字符串

* 中的十六进制字符,顺序双对换,根据系统的不同,决定该函数是否需要调用.例如:

* 在宿主机上(Unbuntu)上需要调用,目标板(s3c2410)不需要.

* =====================================================================================

*/

/*{{{*/

int switch_byte2 ( char *src,int len )

{

int i;

char tch;

for ( i=0; i

{

/* 将第1个字符与第3个字符交换 */

tch = *(src + i + 2);

*(src + i + 2) = *(src + i);

*(src + i) = tch;

/* 将第2个字符与第4个字符交换 */

tch = *(src + i + 3);

*(src + i + 3) = *(src + i + 1);

*(src + i + 1) = tch;

/* eg. "1234" ---> "3412" */

}

return len;

}

/* ----- end of function switch_byte2 ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: change_sim_attr

* Description: 更改短信息中心地址长度和号码类型

* =====================================================================================

*/

/*{{{*/

int change_sim_attr ( const char *src,char *des )

{

printf ( "/nsrc : %s/n",src );

memset(des,strlen(des));

strcpy(des,src);

return 0;

}

/* ----- end of function make_sim_attr ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: change_sim_center

* Description: 更改短信息中心服务号码 (参数改变)

* =====================================================================================

*/

/*{{{*/

int change_sim_center ( const char *src,char *des )

{

memset(des,strlen(des));

strcat(des,"86");

strcat(des,src);

if( strlen(des)%2 != 0 )

{

strcat(des,"F");

}

return 0;

}

/* ----- end of function change_sim_center ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: change_phone_attr

* Description: 更改发送到目的地址(手机)的属性

* =====================================================================================

*/

/*{{{*/

int change_phone_attr ( const char *src,src);

return 0;

}

/* ----- end of function change_phone_attr ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: change_other_phone

* Description: 更改发送到目的手机号码 (参数改变)

* =====================================================================================

*/

/*{{{*/

int change_other_phone ( const char *src,src);

if ( strlen(des)%2 != 0 )

{

strcat(des,"F");

}

return 0;

}

/* ----- end of function change_other_phone ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: change_fix

* Description: 改变固定格式,详细请参考其他(没有不变的东西)

* =====================================================================================

*/

/*{{{*/

int change_fix ( const char *src,src);

return 0;

}

/* ----- end of function change_fix ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: change_gb2312_msg

* Description: 改变要发送的实际信息内容

* =====================================================================================

*/

/*{{{*/

int change_gb2312_msg ( const char *src,src);

return 0;

}

/* ----- end of function change_gb2312_msg ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: make_mesg

* Description: 该函数是该文件的'主'函数,它调动上面的函数来实现短信消息的内容合成。

* =====================================================================================

*/

/*{{{*/

int make_mesg ( char *src,char *dest,int src_len,int des_len )

{

int rc;

char b2s[MSIZE]; /* 字节流转换字符串 */

char nhex[6]; /* 计算消息的内容长度(十六进制表示)*/

char nhex_even[4] = {'0'}; /* PDU规则,长度为奇数前加0 */

g2u(src,src_len,dest,des_len); /* 将GB2312流转换成UTF-16 */

rc = bytes2string(dest,b2s,strlen(dest));

/* 开发板中不需要switch_byte2,主机上需要. 让我伤心的地方 */

//rc = switch_byte2(b2s,rc);

/* GB2312 -> UTF-16 转换之后,再经过字节流转换成字符串,前端多了4个字符. */

sprintf(nhex,"%X",(rc-4)/2); /* (GB2312 -> UTF-16)除以2是得到的汉字字符个数,在格式化输出十六进制 */

//sprintf(nhex,rc/2); /* 使用(GB2312 -> UCS2)时 */

/* 判断长度是否是偶数 */

if ( strlen(nhex)%2 == 1 )

{

/* 奇数 前端加0 */

strcat(nhex_even,nhex);

memset(dest,MSIZE);

strcpy(dest,nhex_even);

}

else

{

memset(dest,nhex);

}

strcat(dest,b2s+4); /* (GB2312 -> UTF-16)前面的4个字节是没用的 */

//strcat(dest,b2s); /* 使用(GB2312 -> UCS2)时 */

return strlen(dest);

}

/* ----- end of function make_mesg ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: make_content

* Description: 将不同部分的内容组合成完整PDU编码内容

* =====================================================================================

*/

/*{{{*/

int make_content(struct gprs_pdu *gpdu,char *content)

{

int nsim = 0; /* SIM用户识别卡所占字节(转换为十六进制)*/

char unicode_msg[MSIZE];

/* 1. 先将消息内容进行编码转换 */

make_mesg(gpdu->gb2312_msg,unicode_msg,strlen(gpdu->gb2312_msg),MSIZE);

/* 2. 短信消息中心号码数字奇偶转换 */

switch_byte1(gpdu->sim_center,strlen(gpdu->sim_center));

/* 3. 接受方手机号码数字奇偶转换 */

switch_byte1(gpdu->phone,strlen(gpdu->phone));

/* 4. 将短消息中心地址长度(16/2)和号码类型拼接到content数组中 */

strcat(content,gpdu->sim_attr);

/* 5. 将短信息中心号码拼接到content数组中 */

strcat(content,gpdu->sim_center);

/* 6. 计算SMSC(Short Message Server Center)相关内容的长度, */

nsim = strlen(content);

/* 7. 将接收方的手机号属性拼接到content数组中 */

strcat(content,gpdu->phone_attr);

/* 8. 将接受方的手机号拼接到content数组中 */

strcat(content,gpdu->phone);

/* 9. 将手机号后面的固定格式拼接到content数组中 */

strcat(content,gpdu->fix);

/* 10.将消息的实际内容拼接到content数组中 */

strcat(content,unicode_msg);

/* 11.返回:PDU总长度减去SIM用户识别卡所占字节*/

return (strlen(content) - nsim) ;

}

/* ----- end of function make_content ----- */

/*}}}*/

/*

* === FUNCTION ======================================================================

* Name: send_msg

* Description: 功能:发送信息

* =====================================================================================

*/

/*{{{*/

void send_msg ( int fd,char *content,int len,char *dail )

{

char cmd_buff[C_SIZE];

char call_buff[C_SIZE] = "ATD"; /* 拨号功能 */

int n_rw = 0;

printf("Start:/n");

/* 第一阶段:先发送 "AT" 命令,测试ARM与GPRS是否建立通信 */

write(fd,"AT/r",3);

printf("1. Send AT/n");

#ifdef SLEEP3S

sleep(3);

#endif

memset(cmd_buff,C_SIZE);

n_rw = read(fd,cmd_buff,C_SIZE);

printf("Receive %d bytes is %s/n",n_rw,cmd_buff);

/* 第二阶段:设置信息的模式 0:PDU,1:Plain */

write(fd,"AT+CMGF=0/r",10);

printf("2. Send AT+CMGF=0/n");

#ifdef SLEEP3S

sleep(3);

#endif

memset(cmd_buff,cmd_buff);

/* 第三阶段:PDU模式下发送消息密令 */

memset(cmd_buff,C_SIZE);

sprintf(cmd_buff,"AT+CMGS=%d/r",len);

write(fd,strlen(cmd_buff));

printf("3. Send %s/n",cmd_buff);

#ifdef SLEEP3S

sleep(3);

#endif

memset(cmd_buff,cmd_buff);

/* 第四阶段:发送消息内容,以0x1A结尾 */

strcat(content,"/x1a");

n_rw = write(fd,content,strlen(content));

printf("4. Send %d Message /n",n_rw);

#ifdef SLEEP3S

sleep(3);

#endif

memset(cmd_buff,cmd_buff);

/* 第五阶段:实现拨号 */

if ( NULL != dail )

{

sleep(10);

strncat(call_buff,dail,11);

printf("call_buff :%s/n",call_buff);

strcat(call_buff,";/r");

write(fd,call_buff,strlen(call_buff));

printf("Call some one!/n");

memset(cmd_buff,cmd_buff);

printf("/nEnd/n");

}

return ;

}

/* ----- end of function send_msg ----- */

/*}}}*/

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读