线上dubbo线程池耗尽CyclicBarrier线程屏障异常解决记录
事件背景
系统相关使用人员反馈系统故障,日志显示从ams系统服务提示dubbo处理线程不足,具体异常信息如下:
问题定位
从上图可知,dubbo的处理线程池满了,默认200个线程,活动线程也是200个。这个现象非常不正常,我们的应用并发还没有到这个程度能同时占用200个线程处理请求。然后去读了下dubbo源码,发现dubbo也认为这种情况不正常,然后帮我们记录了应用的线程堆栈信息,这个非常赞。代码如下:
上面这段代码,在线程池不够用时,会每隔十分钟输出一份dump文件到用户目录,如:
在dump文件中,我们找到了耗尽DubboServerHandler线程池最后一个线程
通过分析得知:是我们应用程序有段代码导致的问题,在特定条件下会触发线程死锁,代码如下
代码中定义了一个线程屏障CyclicBarrier,同行数(调用await的线程数)是11,用来处理十个线程的运算,然后都计算完后拿到处理结果。本身代码没有什么问题,在没有并发的情况下,不会触发问题。但是注意中间那个箭头,执行线程的线程池是固定大小20的线程池,故当同时并发数多于2个的时候线程池的线程会不够用,导致线程等待,然后CyclicBarrier的main线程也会等待其他线程中的await。这就造成了相互等待,下一个请求过来还是继续等待,也就是死锁了。至此所有问题都以清晰明朗了。
解决问题
方案一:改CyclicBarrier为CountDownLatch,这个两个并发工具都是jdk1.5推出为了简化并发编程,CyclicBarrier的await会占用线程池中的线程不释放,导致线程不足,而CountDownLatch的count不会
方案二:改线程池类型为CachedThreadPool,不会应为线程池线程不够用,导致相互等待
文末结语
java并发包提供了丰富的api来简化多线程模型的开发,但是在针对多线程模型业务开发时,我们还需要多留心下多线程带来的坑。总之多核时代推荐大家多使用多线程开发,同时,也要对使用的工具有更多的了解
以上就是线上dubbo线程池耗尽CyclicBarrier线程屏障异常的详细内容,更多关于dubbo线程池耗尽CyclicBarrier线程屏障的资料请关注脚本之家其它相关文章!
相关文章
Elasticsearch写入瓶颈导致skywalking大盘空白
这篇文章主要为大家介绍了Elasticsearch写入瓶颈导致skywalking大盘空白的解决方案,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步2022-02-02Java中转义字符反斜杠\的代替方法及repalceAll内涵解析
这篇文章主要介绍了Java中转义字符反斜杠\的代替方法及repalceAll内涵解析,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧2019-08-08SpringBoot配置类中@Configuration和@Bean的作用
这篇文章主要介绍了SpringBoot配置类中@Configuration和@Bean的作用,@Configuration 指明当前类是一个配置类来替代之前的Spring配置文件,Spring boot的配置类,相当于Spring的配置文件,需要的朋友可以参考下2023-11-11
最新评论