基于DevKit Java性能分析工具的调优实践——锁竞争问题
发表于 2025/12/29
0
1 调优概述
鲲鹏DevKit是一款提供涵盖迁移、测试、性能调优及系统诊断等各环节的开发使能工具集。其中,DevKit Java性能分析工具是针对基于鲲鹏的服务器上运行的Java程序的性能分析和优化工具,能图形化显示Java程序的堆、线程、锁、垃圾回收等信息,收集热点函数、定位程序瓶颈点,帮助用户采取针对性优化。本文使用Java性能优化工具对运行中的Java程序进行在线分析和采样分析,找到程序中的锁竞争问题,并根据分析结果进行优化修改,从而实现Java程序最佳运行。
2 环境要求
项目 | 说明 |
服务器 | TaiShan 200 服务器(型号2280) |
CPU | Kunpeng 920 |
OS | CentOS 7.6 |
调优工具 | Kunpeng DevKit Java性能分析工具 |
3 前提条件
- 服务器和操作系统正常运行。
- PC端已经安装SSH远程登录工具。
- 需要优化的Java程序。
4 调优思路
- 使用Java性能优化工具对Java进程进行在线分析;
- 使用Java性能优化工具对Java进程进行采样分析;
- 针对性能的瓶颈点进行性能优化;
- 观察优化后的Java程序,判断问题是否解决。
5 调优过程
5.1 对程序进行在线分析,在概览页签下观察每种状态的线程数量
发现有大量线程处于阻塞状态,有锁竞争的可能

发现有大量线程处于等待状态,有锁竞争的可能

5.2 切换到CPU->线程列表,执行多次线程转储操作

5.3 切换到线程转储页签
观察多个时间点线程转储的锁分析图,发现有多个线程同时竞争同一把锁,的确出现了锁竞争的情况,还可以发现这把锁不是JUC提供的工具锁,程序中使用的是 synchronized,如果锁竞争比较激烈,该类锁就会升级成重量级,会导致上下文切换比较严重,从而影响性能和关键业务的阻塞。
如果程序使用的是JUC提供的锁,锁分析图如下:

5.4 切换到线程转储->原始数据
根据从锁分析图中找到的对应锁的地址,在原始数据中进行搜索,可以看出有多个线程在获取这把锁,这把锁的类型以及竞争这把锁的代码位置

5.5 发现问题并解决
根据线程转储中提供的锁的类型和位置,咱们就可以分析代码的业务逻辑,从而找到调优方案。下面介绍两种锁竞争的调优方法,仅供参考。
- 情况一:使用synchronized,但在业务上竞争比较激烈:
将 synchronized 替换成 JUC 提供的工具锁(ReentrantLock等)
- 情况二:使用JUC 提供的工具锁,但在业务上竞争比较激烈
这种情况需要加入其他策略去提高性能,如加入线程池,限制竞争锁的线程数;如果是读写分离的场景,可以考虑使用ReadWriteLock。从业务的实际情况去考虑。
6 实践总结
Java中的锁竞争问题一旦发生很难定位具体的代码位置,因为程序干扰因素比较多,但是可以根据线程转储去定位,其中的栈跟踪信息提供了发生锁竞争的代码位置。如果发现多个线程都试图锁住相同的锁地址,说明应用正面临锁竞争。
在进行其他程序调优时,需要根据鲲鹏DevKit性能优化工具采集分析的实际结果和对应的优化建议进行调优操作。具体的调优思路可以参考本次实践。


