xsocket死锁问题排查
来源:互联网 发布:华师大网络教育好不好 编辑:程序博客网 时间:2024/05/16 00:43
今天同事告诉我,生产环境的kafka队列中没有数据了。生产环境中和数据生产者相关的服务器有2台,最近这两台老搞事情:
客户端是基于xsocket开发的,服务端是直接使用NIO开发的。
背景交代完了,下面回顾一下我排查这个问题的思路 :
查日志
半天查不到什么有用信息,遂放弃。
检查socket是否还在
看日志之前就怀疑socket是不是断开了。这算是查这类问题的套路吧。
在A机上运行netstat,命令就不细说了:netstat -ntap | grep xxx #xxx是B机监听的端口号
还好socket还在。
然而,现在仍然判断不来AB机之间是否有问题,还得想办法。检查网络流量是否正常
我想,既然socket还在,那就看看socket上有没有流量。流量正常的话,基本可以排除客户端和服务器之间的问题。
使用iptraf命令查看socket流量,在A机上运行iptraf:
此处应有截图,然而我忘截了
iptraf的结果是,socket上面有数据流,但是远少于正常情况,隔一阵一小包数据。这说明问题出在A、B机之间。我猜想小包数据是登录报文或者心跳包一类的。
抓包看报文
为了验证刚才的猜想,我决定抓几个包来瞧瞧。在A机上运行下面命令:
tcpdump tcp port xxxx and host xxx.xxx.xxx.xxx
抓了好长时间,报文都是上面那样的,不是我猜的登录或心跳报文(报文数据长度为0)。我抓到的大概是tcp协议的心跳一类的吧。
当时分析,A、B之间没数据,大概会是这几种情况吧:- A机发数据线程没创建起来/已经终止
- A或B机阻塞在某处
- 特殊情况下代码逻辑跳过了发数据部分
- A机没有要发送的数据
仔细检查了代码逻辑,排除了后两种情况。
使用jstack查看线程堆栈
从socket上已经找不出更多线索了,只好去看jvm。在A机上连续使用jstack查看线程状态几次,发现发数据的那个线程的堆栈状态就没变过,仔细一看,线程发生了死锁!
找到问题的原因,还有了详细的堆栈调用层级,接下来就好办了。找到xsocket的源代码,找到死锁的那一行,发现那行下面就有一个警告日志:
synchronized flushing in NonThreaded mode could cause dead locks (hint: set flush mode to ASYNC).
在程序中设置flush mode为异步,问题得到解决~
- xsocket死锁问题排查
- 记一次死锁问题的排查
- 并发插入引发的死锁问题排查
- JVM 调优命令排查死锁问题
- 并发插入引发的死锁问题排查
- Java模拟排查线程死锁问题
- 记一次死锁问题的排查和解决
- MySQL redo lock 死锁问题排查 & 解决过程
- MySQL redo lock 死锁问题排查 & 解决过程
- 记录一次排查极光推送SDK死锁问题
- 排查mysql死锁
- Java死锁的排查
- 死锁原因排查
- mysql 排查死锁
- mysql死锁排查
- index_merge引发的死锁排查
- index_merge引发的死锁排查
- index_merge引发的死锁排查
- HDU 3466 Proud Merchants(变种01背包 + 无后效性)
- L1-016. 查验身份证
- 《剑指offer》005-从尾到头打印链表
- 分金子
- EL表达式
- xsocket死锁问题排查
- rails创建项目报"please update your path to include build tools...."
- CodeForces 785D Anton and School
- oc——类——__strong __weak __unsafe_unretained
- closehandle()函数
- 把数组排成最小的数
- C++纯虚函数
- 2017华为软件精英挑战赛官方case最优解
- 二分法查找