标题 | 内容 |
---|
编者 | 炎芯随笔 |
发布时间 | 2020年8月26日13:53:31 |
版本 | V-1.0 |
1.前言
2.TCP
2.1头文件变量及函数声明
WSADATA wsd;
SOCKET m_socket;
SOCKADDR_IN ser_addr;
SOCKET m_socket_data;
SOCKADDR_IN m_socket_data_addr;
bool tcp_IF_Connected(SOCKET *m_socket);
bool tcp_Init(SOCKET *m_socket, int timeOut);
bool tcp_Bind(const char*ip, const char* port, SOCKADDR_IN *ser_addr);
bool tcp_Connect(SOCKET m_socket, SOCKADDR_IN ser_addr, char*say);
void tcp_Disconnect(SOCKET *m_socket, char*say);
2.2.函数接口实现
项目 | 内容 |
---|
函数名 | tcp_IF_Connected |
函数参数 | SOCKET *m_socket |
功能说明 | 判断tcp是否连接 |
使用情况 | 布尔值 |
示例 | 参见如下代码 |
bool CNFU_4G_PRODlg::tcp_IF_Connected(SOCKET *m_socket)
{
if (*m_socket)
{
sprintf_s(m_showStr, "已连接成功,请先断开再连接\n");
showCurLineChar(m_listbox, m_showStr);
return true;
}
return false;
}
项目 | 内容 |
---|
函数名 | tcp_Init |
函数参数 | SOCKET *m_socket,int timeOut |
功能说明 | 初始化套接字,设置超时时间 |
使用情况 | 布尔值 |
示例 | 参见如下代码 |
bool CNFU_4G_PRODlg::tcp_Init(SOCKET *m_socket, int timeOut)
{
if (timeOut <=0)
{
return FALSE;
}
*m_socket = socket(AF_INET, SOCK_STREAM, 0);
if (*m_socket == INVALID_SOCKET)
{
sprintf_s(m_showStr, "套接字初始化失败");
showCurLineChar(m_listbox, m_showStr);
return FALSE;
}
setTimeOut(m_socket, timeOut);
return TRUE;
}
项目 | 内容 |
---|
函数名 | tcp_Bind |
函数参数 | const charip, const char port, SOCKADDR_IN *ser_addr |
功能说明 | 绑定ip和端口号 |
使用情况 | 布尔值 |
示例 | 参见如下代码 |
bool CNFU_4G_PRODlg::tcp_Bind(const char*ip, const char* port, SOCKADDR_IN *ser_addr)
{
int n_serbAddlen = sizeof(SOCKADDR_IN);
ser_addr->sin_family = AF_INET;
ser_addr->sin_addr.S_un.S_addr = inet_addr(ip);
ser_addr->sin_port = htons(atoi(port));
return TRUE;
}
项目 | 内容 |
---|
函数名 | tcp_Connect |
函数参数 | SOCKET sock, SOCKADDR_IN ser_addr, char*say |
功能说明 | 创建tcp连接 |
使用情况 | 布尔值 |
示例 | 参见如下代码 |
bool CNFU_4G_PRODlg::tcp_Connect(SOCKET sock, SOCKADDR_IN ser_addr, char*say)
{
int n_serbAddlen = sizeof(SOCKADDR_IN);
int retValue = ::connect(sock, (SOCKADDR*)&ser_addr, n_serbAddlen);
if (SOCKET_ERROR == retValue)
{
DWORD err = GetLastError();
sprintf_s(m_showStr, "连接失败");
showCurLineChar(m_listbox, m_showStr);
closesocket(sock);
sock = NULL;
return FALSE;
}
sprintf_s(m_showStr, "%s:连接成功", say);
showCurLineChar(m_listbox, m_showStr);
return TRUE;
}
项目 | 内容 |
---|
函数名 | tcp_Disconnect |
函数参数 | SOCKET sock, charsay |
功能说明 | 断开tcp连接 |
使用情况 | 布尔值 |
示例 | 参见如下代码 |
void CNFU_4G_PRODlg::tcp_Disconnect(SOCKET *sock, char*say)
{
if (*sock)
{
closesocket(*sock);
*sock = NULL;
sprintf_s(m_showStr, "%s:断开连接",say);
showCurLineChar(m_listbox, m_showStr);
}
}
2.3.数据收发接口
项目 | 内容 |
---|
函数名 | sendData |
函数参数 | SOCKET m_socket, char* dataIn, int len |
功能说明 | 发送数据 |
使用情况 | 发送的字节数 |
示例 | 参见如下代码 |
int sendData(SOCKET m_socket, char* dataIn, int len)
{
if (!dataIn || len < 0 || m_socket < 0)
{
return -1;
}
int send_ret = 0;
int send_ret_add = 0;
int send_len = len;
while ((send_ret = send(m_socket, dataIn + send_ret_add, send_len - send_ret_add, 0)) < (send_len - send_ret_add))
{
if (send_ret < 0)
{
return -2;
}
send_ret_add += send_ret;
}
return send_ret_add;
}
项目 | 内容 |
---|
函数名 | recvData |
函数参数 | SOCKET m_socket, char* dataOUT, unsigned long recv_len |
功能说明 | 接收数据 |
使用情况 | 接收的字节数 |
示例 | 参见如下代码 |
int recvData(SOCKET m_socket, char* dataOUT, unsigned long recv_len)
{
if (recv_len < 0 || m_socket < 0){
return -1;
}
int recv_ret = 0;
unsigned long recv_ret_add = 0;
char *recvBuf = (char*)malloc(sizeof(char)*recv_len+1);
if (!recvBuf){
TRACE("malloc error\n");
return -1;
}
while ( 1 ){
recv_ret = recv(m_socket, recvBuf + recv_ret_add, recv_len - recv_ret_add, 0);
if (recv_ret < 0){
if (recv_ret_add > 0)
{
memcpy(dataOUT, recvBuf, sizeof(char)*recv_ret_add);
free(recvBuf);
return recv_ret_add;
}
free(recvBuf);
return -2;
}
recv_ret_add += recv_ret;
if (recv_ret_add >= recv_len){
break;
}
}
if (dataOUT != NULL){
memcpy(dataOUT, recvBuf, sizeof(char)*recv_ret_add);
}
free(recvBuf);
return recv_ret_add;
}
3.UDP
3.1头文件变量及函数声明
bool udp_IF_Connected(SOCKET *m_socket);
bool udp_Init(SOCKET *sock, int timeOut);
bool udp_Bind(SOCKET *sock, sockaddr_in *sAddr, char*ip, char* port, bool bind_flas);
void udp_Disconnect(SOCKET *m_socket, char*say);
3.2 函数接口实现
项目 | 内容 |
---|
函数名 | udp_IF_Connected |
函数参数 | SOCKET *sock |
功能说明 | 判断tcp是否连接 |
使用情况 | 布尔值 |
示例 | 参见如下代码 |
bool CNFU_4G_PRODlg::udp_IF_Connected(SOCKET *m_socket)
{
if (*m_socket)
{
sprintf_s(m_showStr, "已连接成功,请先断开再连接\n");
showCurLineChar(m_listbox, m_showStr);
return true;
}
return false;
}
项目 | 内容 |
---|
函数名 | udp_Init |
函数参数 | SOCKET *sock ,int timeOut |
功能说明 | 初始化udp套接字 |
使用情况 | 布尔值 |
示例 | 参见如下代码 |
bool CNFU_4G_PRODlg::udp_Init(SOCKET *sock,int timeOut)
{
DWORD m_dwErr;
*sock = socket(AF_INET, SOCK_DGRAM, 0);
if (INVALID_SOCKET == *sock)
{
m_dwErr = GetLastError();
AfxMessageBox(_T(" m_sock_adc is INVALID_SOCKET!"));
return false;
}
setTimeOut(sock, timeOut);
return true;
}
项目 | 内容 |
---|
函数名 | udp_Bind |
函数参数 | SOCKET *sock ,int timeOut |
功能说明 | 绑定udp套接字 |
使用情况 | 布尔值 |
示例 | 参见如下代码 |
bool CNFU_4G_PRODlg::udp_Bind(SOCKET *sock, sockaddr_in *sAddr, char*ip, char* port, bool bind_flas)
{
DWORD m_dwErr;
memset((char*)sAddr, 0, sizeof(sockaddr_in));
sAddr->sin_family = AF_INET;
sAddr->sin_port = htons(atoi(port));
sAddr->sin_addr.S_un.S_addr = inet_addr(ip);
if (bind_flas)
{
int ret = ::bind(*sock, (sockaddr*)sAddr, sizeof(sockaddr));
if (SOCKET_ERROR == ret)
{
m_dwErr = GetLastError();
AfxMessageBox(_T(" bind false!"));
return false;
}
}
return true;
}
项目 | 内容 |
---|
函数名 | udp_Disconnect |
函数参数 | SOCKET sock, charsay |
功能说明 | 断开udp套接字 |
使用情况 | 布尔值 |
示例 | 参见如下代码 |
void CNFU_4G_PRODlg::udp_Disconnect(SOCKET *sock, char*say)
{
if (*sock)
{
closesocket(*sock);
*sock = NULL;
sprintf_s(m_showStr, "%s:断开连接", say);
showCurLineChar(m_listbox, m_showStr);
}
}
4.心跳示例
4.1.创建线程
m_heartBeat = thread(th_heartBeat, this);
4.2.心跳接口实现
typedef struct stMsgHeartBeat
{
int heartBeat;
}stMsgHeartBeat;
int th_heartBeat(void* pparam)
{
if (!pparam)
return -1;
USES_CONVERSION;
CNFU_4G_PRODlg *pp = (CNFU_4G_PRODlg*)pparam;
stMsgHeartBeat msgHearBeat = { 0 };
int try_times_sleep = 0;
int ret = 0;
while (true)
{
while (pp->m_bHbing)
{
if (try_times_sleep == 0)
{
msgHearBeat.heartBeat++;
msgHearBeat.heartBeat = msgHearBeat.heartBeat % 10;
send(pp->m_socketHeart, (char*)&msgHearBeat, sizeof(msgHearBeat), 0);
try_times_sleep = 1;
ret = recvData(pp->m_socketHeart, (char*)&msgHearBeat, sizeof(stMsgHeartBeat));
if (ret < 0)
{
sprintf_s(pp->m_showStr, "心跳接收超时");
showCurLineChar(pp->m_listbox, pp->m_showStr);
pp->m_bStartRecv130 = false;
pp->OnBnClickedDisconnect();
break;
}
else if (ret >= 0)
{
}
}
Sleep(1000);
--try_times_sleep;
if (pp->time_sleep_flags>0)
{
--pp->time_sleep_flags;
}
}
if (pp->m_flags_IF_exit)
{
break;
}
Sleep(10);
}
return 0;
}
4.3.线程等待退出
if (m_heartBeat.joinable())
{
m_heartBeat.join();
}