转载自:zxh2075的专栏

在Socket心跳机制中,心跳包可以由服务器发送给客户端,也可以由客户端发送给服务器,不过比较起来,前者开销可能较大。本文实现的是由客户端给服务器发送心跳包,服务器不必返回应答包,而是通过判断客户在线会话记录中的计数标志值来实现心跳异常的检测,以此决定客户端是否已经断开连接以及删除其在线会话记录。

基本思路:

①客户端定时给服务器发送心跳包(案例中定时时间为3秒);

②服务器创建一个心跳检测的线程,线程中每隔3秒对用户在线会话记录中的计数器进行加1操作(初始值为0);

③服务器每次收到客户端的心跳包后,都将其在线会话记录中的计数器清零;

④当心跳检测线程中检测到某用户计数器已经累加到数值为5时(说明已经有15秒未收到该用户心跳包),就判定该用户已经断线,并将其从会话记录中清除出去。

(注:案例中的会话记录是用链表实现的)

C语言代码实现案例:

客户端:

/*
**功能:客户端心跳包发送线程函数
**参数:线程传参(可传套接字)
**返回值:空
*/
void *send_heart(void *addr)
{
while(){
pd->data_type = HEART; //HEART:数据包类型,pd为数据包结构体指针
write(client_sockfd,pd,sizeof(DATA_PACK));
sleep(); //定时3秒
}
return NULL;
} /***********************************************/
/***********************************************/ 服务器端: typefdef struct session{
char peerip[];
char name[];
int sockfd;
int count;
struct session *next;
}s_t; /*
**功能:处理用户心跳包事件,将其会话记录中的计数器清零
**参数:套接字和数据包指针
**返回值:无
*/
void heart_handler(int sockfd,DATA_PACK *pd)
{
s_t *cur = shead->next; // shead为用户在线会话记录全局变量头指针
while( NULL != cur){
if(strcmp(cur->name,pd->name) == ){
cur->count = ; //将计数器清零,表明用户名为pd->name的客户端还活着
printf("客户端IP: %s :用户 %s 连接正常\n",cur->peerip,pd->name);
}
cur = cur->next;
}
} /*
**功能:心跳检测线程函数
**参数:无
**返回值:无
*/
void *heart_check(void *p)
{
printf("心跳检测线程已开启!\n"); while(){
check_handler(); // 心跳检测处理函数
sleep(); //定时3秒
}
return NULL;
} /*
**功能:心跳检测处理函数
**参数:无
**返回值:无
*/
void check_handler(){
s_t *temp = NULL; // 用于释放结点
s_t **ppNode = &shead->next; while(NULL != (*ppNode)){
if((*ppNode)->count == ){
printf("客户端IP: %s :用户 %s 已经掉线!!\n",(*ppNode)->peerip,(*ppNode) ->name);
close((*ppNode)->sockfd); //关闭对端套接字
temp = *ppNode; //存储本结点地址
*ppNode = (*ppNode)->next; //移动指针
free(temp); //释放结点
temp = NULL;
continue;
}
else if((*ppNode)->count > ){
printf("客户端IP: %s :用户 %s 连接异常!\n",(*ppNode)->peerip,(*ppNode)- >name);
(*ppNode)->count++;
printf("count = %d\n",(*ppNode)->count); //查看计数器内容
ppNode = &((*ppNode)->next); // 成员指针
continue;
}
else if((*ppNode)->count == ){
(*ppNode)->count++;
printf("count = %d\n",(*ppNode)->count); //查看计数器内容
ppNode = &((*ppNode)->next); // 成员指针
}
else;
}
}

[转] Socket心跳包异常检测的C语言实现,服务器与客户端代码案例的更多相关文章

  1. Socket心跳包异常检测的C语言实现,服务器与客户端代码案例

    在Socket心跳机制中,心跳包可以由服务器发送给客户端,也可以由客户端发送给服务器,不过比较起来,前者开销可能较大.本文实现的是由客户端给服务器发送心跳包,服务器不必返回应答包,而是通过判断客户在线 ...

  2. web socket 心跳包的实现方案

    web socket 心跳包的实现方案05/30/2010 现在网络环境错综复杂,socket心跳包是获得健康强壮的连接的有效解决方案,今天,我们就在web socket中实现心跳包方案,是的,尽管我 ...

  3. socket 心跳包机制

    心跳包的发送,通常有两种技术 方法1:应用层自己实现的心跳包  由应用程序自己发送心跳包来检测连接是否正常,大致的方法是:服务器在一个 Timer事件中定时 向客户端发送一个短小精悍的数据包,然后启动 ...

  4. Socket心跳包机制【转】

    转自:https://blog.csdn.net/xuyuefei1988/article/details/8279812 心跳包的发送,通常有两种技术 方法1:应用层自己实现的心跳包 由应用程序自己 ...

  5. Socket心跳包机制

    心跳包的发送,通常有两种技术方法1:应用层自己实现的心跳包 由应用程序自己发送心跳包来检测连接是否正常,大致的方法是:服务器在一个 Timer事件中定时 向客户端发送一个短小精悍的数据包,然后启动一个 ...

  6. TCP socket心跳包示例程序

    在做游戏开发时,经常需要在应用层实现自己的心跳机制,即定时发送一个自定义的结构体(心跳包),让对方知道自己还活着,以确保连接的有效性. 在TCP socket心跳机制中,心跳包可以由服务器发送给客户端 ...

  7. socket心跳包机制实践与理解

    实现Socket心跳包主要分为两大类,第一采用tcp自带的KeepAlive,第二是自定义心跳包,恰巧我在产品VICA中都使用过,下面就这两种心跳包机制谈谈个人的理解与感受. 首先第一种KeepAli ...

  8. Socket心跳包机制总结【转】

    转自:https://blog.csdn.net/qq_23167527/article/details/54290726 跳包之所以叫心跳包是因为:它像心跳一样每隔固定时间发一次,以此来告诉服务器, ...

  9. Socket 心跳包机制总结

    跳包之所以叫心跳包是因为:它像心跳一样每隔固定时间发一次,以此来告诉服务器,这个客户端还活着.事实上这是为了保持长连接,至于这个包的内容,是没有什么特别规定的,不过一般都是很小的包,或者只包含包头的一 ...

随机推荐

  1. Linux进程间通信简介

    本人仅做简介.转自:http://www.linuxidc.com/Linux/2013-06/85904p2.htm   管道( pipe ):   (Linux进程间通信) 管道是一种半双工的通信 ...

  2. LibreOJ #6220. sum(数论+构造)

    题目大意:在数组中找出一些数,使它们的和能被n整除 这题标签是数学,那我就标题就写数论好了... 显然如果数组中有n的倍数直接取就行. 那假设数组中没有n的倍数,把数组中的数求前缀和后全部%n,会得到 ...

  3. java中new一个对象放在循环体里面与外面的区别

    首先说下问题: 这次在做项目的是出现了一个new对象在循环里面与外面造成的不同影响. 大家可以看到这个new的对象放在不同的位置产生的效果是不一样的. 经过多方查询与验证可以得出结论: * EasyU ...

  4. js的数据类型--字符串

    js的数据类型——字符串 这篇我们来说说js的第二种数据类型——字符串. js的内置功能之一就是字符串拼接.如果将加号(+)运算符用于数字,表示两数相加.但将它作用于字符串,则表示字符串拼接,将第二个 ...

  5. UVA 1393 Highways

    https://vjudge.net/problem/UVA-1393 题意: a*b的点阵中能画多少条非水平非竖直的直线 方向‘/’ 和 方向 ‘\’ 对称 枚举直线所在矩形的i*j 直线可能重复的 ...

  6. HDU1164

    //HDU 1164 //输入一个数(1<x<=65535) 转化为素数的乘积() #include "iostream" #include "cstdio& ...

  7. linux 执行shell脚本的4种方法总结

    bash shell 脚本的方法有多种,假设我们编写好的shell脚本的文件名为hello.sh,文件位置在/data/shell目录中并已有执行权限. 方法一:切换到shell脚本所在的目录(此时, ...

  8. GPU硬件加速

    现代浏览器大都可以利用GPU来加速页面渲染.每个人都痴迷于60桢每秒的顺滑动画.在GPU的众多特性之中,它可以存储一定数量的纹理(一个矩形的像素点集合)并且高效地操作这些纹理(比如进行特定的移动.缩放 ...

  9. hdu 1159 Common Subsequence(最长公共子序列 DP)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1159 Common Subsequence Time Limit: 2000/1000 MS (Jav ...

  10. SpringCloud Fegin超时重试源码

    springCloud中最重要的就是微服务之间的调用,因为网络延迟或者调用超时会直接导致程序异常,因此超时的配置及处理就至关重要. 在开发过程中被调用的微服务打断点发现会又多次重试的情况,测试环境有的 ...