⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sms.cpp

📁 上位机vc6.0编程控制西门子GPRS模块实现短信收发
💻 CPP
📖 第 1 页 / 共 2 页
字号:
		nDstLength = tmp;
	}
	else if(pDst->TP_DCS == GSM_UCS2)
	{
		// UCS2解码
		nDstLength = gsmString2Bytes(pSrc, buf, tmp * 2);			// 格式转换
		nDstLength = gsmDecodeUcs2(buf, pDst->TP_UD, nDstLength);	// 转换到TP-DU,将unicode码转换成汉字
	}
	else
	{
		// 8-bit解码
		nDstLength = gsmString2Bytes(pSrc, buf, tmp * 2);			// 格式转换
		nDstLength = gsmDecode8bit(buf, pDst->TP_UD, nDstLength);	// 转换到TP-DU
	}

	// 返回目标字符串长度
	return nDstLength;
}

BOOL SendPduMessage()
{
	return TRUE;
}

// 发送短消息,仅发送命令,不读取应答
// 输入: pSrc - 源PDU参数指针
int GprsSendMessage(SM_PARAM* pSrc)
{
	int nPduLength;		// PDU串长度
	unsigned char nSmscLength;	// SMSC串长度
	char cmd[16];		// 命令串
	char pdu[512];		// PDU串
	char ans[128];		// 应答串

	nPduLength = gsmEncodePdu(pSrc, pdu);	// 根据PDU参数,编码PDU串
	strcat(pdu, "\x01a");		// 以Ctrl-Z结束

	gsmString2Bytes(pdu, &nSmscLength, 2);	// 取PDU串中的SMSC信息长度
	nSmscLength++;		// 加上长度字节本身

	// 命令中的长度,不包括SMSC信息长度,以数据字节计
	sprintf(cmd, "AT+CMGS=%d\r", nPduLength / 2 - nSmscLength);	// 生成命令

//	TRACE("%s", cmd);
//	TRACE("%s\n", pdu);

	for(int i=0;i<3;i++)				// 测试AT+I指令,允许重发两次,否则初始化失败,检查硬件连接
	{	
		WriteComm(cmd, strlen(cmd));	// 先输出命令串
		ReadComm(ans, 128);				// 读应答数据
		if (strstr(ans, ">") == NULL)// 返回ok,说明初始化成功	
		{
			if(i==2)
			{
				return FALSE;
			}
			Sleep(500);
		}
		else
		{
			break;
		}
	}
	
	WriteComm(pdu, strlen(pdu));		// 得到肯定回答,继续输出PDU串
	return 0;
}

// 读取短消息,仅发送命令,不读取应答
// 用+CMGL代替+CMGR,可一次性读出全部短消息
int gsmReadMessageList()
{
	return WriteComm("AT+CMGL=0\r", 10);
}

// 删除短消息,仅发送命令,不读取应答
// 输入: index - 短消息序号,1-255
int gsmDeleteMessage(int index)
{
	char cmd[16];		// 命令串

	sprintf(cmd, "AT+CMGD=%d\r", index);	// 生成命令

	// 输出命令串
	return WriteComm(cmd, strlen(cmd));
}

// 读取GSM MODEM的应答,可能是一部分
// 输出: pBuff - 接收应答缓冲区
// 返回: GSM MODEM的应答状态, GSM_WAIT/GSM_OK/GSM_ERR
// 备注: 可能需要多次调用才能完成读取一次应答,首次调用时应将pBuff初始化
int gsmGetResponse(SM_BUFF* pBuff)
{
	int nLength;		// 串口收到的数据长度
	int nState;

	// 从串口读数据,追加到缓冲区尾部
	nLength = ReadComm(&pBuff->data[pBuff->len], 128);	
	pBuff->len += nLength;

	// 确定GSM MODEM的应答状态
	nState = GSM_WAIT;
	if ((nLength > 0) && (pBuff->len >= 4))
	{
		if (strncmp(&pBuff->data[pBuff->len - 4], "OK\r\n", 4) == 0)  nState = GSM_OK;
		else if (strstr(pBuff->data, "ERROR") != NULL) nState = GSM_ERR;
	}

	return nState;
}

// 从列表中解析出全部短消息
// 输入: pBuff - 短消息列表缓冲区
// 输出: pMsg - 短消息缓冲区
// 返回: 短消息条数
int gsmParseMessageList(SM_PARAM* pMsg, SM_BUFF* pBuff)
{
	int nMsg;			// 短消息计数值
	char* ptr;			// 内部用的数据指针

	nMsg = 0;
	ptr = pBuff->data;

	// 循环读取每一条短消息, 以"+CMGL:"开头
	while((ptr = strstr(ptr, "+CMGL:")) != NULL)
	{
		ptr += 6;		// 跳过"+CMGL:", 定位到序号
		sscanf(ptr, "%d", &pMsg->index);	// 读取序号,此序号在ptr内容的第一个字节保存
//		TRACE("  index=%d\n",pMsg->index);

		ptr = strstr(ptr, "\r\n");	// 找下一行
		if (ptr != NULL)
		{
			ptr += 2;		// 跳过"\r\n", 定位到PDU
			
			gsmDecodePdu(ptr, pMsg);	// PDU串解码

			pMsg++;		// 准备读下一条短消息
			nMsg++;		// 短消息计数加1
		}
	}


	return nMsg;
}

// 初始化Gprs
// 返回: TRUE 初始化成功 FALSE 初始化失败
BOOL InitGprs()
{
	char ans[30];
	char buffer[30];
	for(int i=0;i<3;i++)				// 测试AT+I指令,允许重发两次,否则初始化失败,检查硬件连接
	{
		WriteComm("AT+I\r",5);
		ReadComm(ans,20);
		if (strstr(ans, "I/OK") == NULL)// 返回ok,说明初始化成功	
		{
			if(i==2)
			{
				return FALSE;
			}
			Sleep(500);
		}
		else
		{
			break;
		}
	}
	
	for(i=0;i<3;i++)					// 测试AT+IMCM指令,进入手机模块AT命令直传状态
	{
		WriteComm("AT+IMCM\r",8);
		ReadComm(ans,20);
		if (strstr(ans, "I/OK") == NULL)
		{
			if(i==2)
			{
				return FALSE;
			}
			Sleep(500);
		}
		else
		{
			break;
		}
	}
	for(i=0;i<3;i++)					// 设置短消息中心号码,其格式为AT+CMGF="+8613800451500"
	{
		int length = sprintf(buffer,"AT+CSCA=%c+8613800451500%c\r",34,34);
		WriteComm(buffer,length);
		ReadComm(ans,30);
		if (strstr(ans, "OK") == NULL)	// 返回OK,说明设置成功
		{
			if(i==2)
			{
				return FALSE;
			}
			Sleep(500);
		}
		else
		{
			break;
		}
	}
	return TRUE;
}

// 设置短消息发送格式
// 格式:state,为0表示Text方式,不能发送汉字,为1表示PDU格式,可以发送汉字
// 返回: TRUE设置成功 FALSE 设置失败
BOOL SetMessageType(int state)
{
	char ans[30];
	for(int i=0;i<3;i++)			// 测试AT+CMGF=1指令,设置短消息发送方式
	{
		if(state==0)	WriteComm("AT+CMGF=1\r",25);	// Text发送
		else if(state==1) WriteComm("AT+CMGF=0\r",25);	// PDU发送
		ReadComm(ans,30);
		if (strstr(ans, "OK") == NULL)
		{
			if(i==2)
			{
				return FALSE;
			}
			Sleep(500);
		}
		else
		{
			break;
		}
	}
	return TRUE;
}

// 切换AT指令和ATI指令
// type:指令类型,为真为ATI指令集,为假则为AT指令集

BOOL ChangeCommandType(BOOL type)
{
	char ans[60];
	if (type)
	{
		for(int i=0;i<3;i++)					// 测试AT+IMCM指令,进入手机模块AT命令直传状态
		{
			WriteComm("AT+I\r",8);
			ReadComm(ans,20);
			if (strstr(ans, "I/OK") == NULL)
			{
				if(i==2)
				{
					return FALSE;
				}
				Sleep(500);
			}
			else
			{
				break;
			}
		}
	}
	else
	{
		for(int i=0;i<3;i++)					// 测试AT+IMCM指令,进入手机模块AT命令直传状态
		{
			WriteComm("AT+IMCM\r",8);
			ReadComm(ans,20);
			if (strstr(ans, "I/OK") == NULL)
			{
				if(i==2)
				{
					return FALSE;
				}
				Sleep(500);
			}
			else
			{
				break;
			}
		}
	}
	return TRUE;
}
// 以Text方式发送短消息
// number:对方手机号码
// content:短信内容
// 返回:TRUE 发送成功,FALSE 发送失败
BOOL SendTextMessage(CString number,CString content)
{
	char ans[60];
	char buffer[30];
	int length;
	for(int i=0;i<3;i++)			// 发送目标手机号
	{
		length = sprintf(buffer,"AT+CMGS=%c+86%s%c\r",34,number,34);
		WriteComm(buffer,length);
		ReadComm(ans,30);
		if (strstr(ans, ">") == NULL)
		{
			if(i==2)
			{
				return FALSE;
			}
			Sleep(500);
		}
		else
		{
			break;
		}
	}
	for(i=0;i<3;i++)				// 发送短消息内容
	{
		length = sprintf(buffer,"%s%c",content,26);
		WriteComm(buffer,length);
		Sleep(2000);
		ReadComm(ans,140);
		if (strstr(ans, "OK") == NULL)
		{
			if(i==2)
			{
				return FALSE;
			}
			Sleep(500);
		}
		else
		{
			break;
		}
	}
	return TRUE;
}

// 打开并建立一个SOCKET连接
// 输入: pSocket 需要建立的pSocket连接的参数
// 仅发送命令,不接收应答
// 指令:AT+ISTCP:xxx.xxx.xxx.xxx,<Port Number> <CR>句柄,此指令返回socket句柄 
BOOL ConnectSocket(SOCKET_PARAM* pSocket)
{
	char ans[60];
	for(int i=0;i<3;i++)			// 切换到AT+I指令
	{
		WriteComm("AT+I\r",5);
		ReadComm(ans,30);
		if (strstr(ans, "OK") == NULL)
		{
			if(i==2)
			{
				return FALSE;
			}
			Sleep(500);
		}
		else
		{
			break;
		}
	}
	char buffer[40];
	int length = sprintf(buffer,"AT+ISTCP:%s,%s\r",pSocket->IP_ADDRESS,pSocket->PORT_NUMBER);
	WriteComm(buffer,length);
	return TRUE;
}

// 关闭一个SOCKET连接
// 输入: pSocket 需要建立的pSocket连接的参数
// 仅发送命令,不接收应答
// 指令:AT+ISCLS:000<CR>,句柄000为socket等待返回I/DONE	
void CloseSocket(SOCKET_PARAM* pSocket)
{
	char buffer[20];
	int length = sprintf(buffer,"AT+ISCLS:%s\r",pSocket->SOCKET_HANDLE);
	WriteComm(buffer,length);
}

// 通过指定socket发送数据
// 输入: pSocket 需要发送的数据以及相应的socket信息
// 仅发送命令,不接收应答
// 指令:AT+ISSND%:xxx,<string Length>:<CR>
void SocketSendData(SOCKETDATA_PARAM* pSocket)
{
	char buffer[5000];				// 长度以后需要指定
	int length = sprintf(buffer,"AT+ISSND%c:%s,%d:%s\r",37,pSocket->SOCKET_HANDLE,strlen(pSocket->SEND_DATA),pSocket->SEND_DATA);
	WriteComm(buffer,length);
}

// 从缓冲区数据列表中解析出数据包
// 输入: pBuff - 数据列表缓冲区
// 输入: pSocket - 当前的socket信息
// 输出: pData - 数据包缓冲区
// 返回: 数据包个数
int SocketParseMessageList(SOCKET_PARAM* pSocket,SOCKETDATA_PARAM* pData, SOCKET_BUFF* pBuff)
{
	int nMsg = 0;					// 数据包计数值
	char *ptr;
	int length;						// 记录缓冲区中字节数据长度
	ptr = strstr(pBuff->data,"I/");
	ptr +=2;
	sscanf(ptr,"%d",&length);
	if(length>0)
	{
		ptr = strstr(ptr,":");
		ptr += 1;
		strcpy(pData->SEND_DATA,ptr);
		strcpy(pData->IP_ADDRESS,pSocket->IP_ADDRESS);
		strcpy(pData->PORT_NUMBER,pSocket->PORT_NUMBER);
		strcpy(pData->SOCKET_HANDLE,pSocket->SOCKET_HANDLE);
		nMsg = 1;
	}
	return nMsg;
	
}

// 读取缓冲区中的数据,仅发送命令,不读取应答
// 一次性的读出缓冲区中的所有数据
// 指令AT+ISRCV:xxx<CR>
void SocketReadDataList(SOCKET_PARAM* pSocket)
{
	CString str;
	str.Format("AT+ISRCV:%s\r",pSocket->SOCKET_HANDLE);
	WriteComm(str.GetBuffer(15),str.GetLength());
}


// 读取Socket通讯时应答
// 输出: pBuff - 接收应答缓冲区
// 备注: 可能需要多次调用才能完成读取一次应答,首次调用时应将pBuff初始化
void SocketGetResponse(SOCKET_BUFF* pBuff)
{
	int nLength;		// 串口收到的数据长度
	// 从串口读数据,追加到缓冲区尾部
	nLength = ReadComm(&pBuff->data[pBuff->len], 128);	
	pBuff->len += nLength;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -