长稳测试发现Java Native内存泄漏,总结一下内存分析的套路。 长稳内存测试可参考 进程内存打印。
业务启动命令:
java -Djava.library.path=../lib/ -classpath .:./quick_start_java.jar:../lib/mindspore-lite-java.jar com.mindspore.lite.demo.Main
1 查看jvm堆内存是否异常
jcmd命令
jcmd [pid] VM.native_memory detail
jcmd `jps | grep -v Jps | awk '{print $1}'` VM.native_memory detail # 注意如果jps查询返回多个进程id,此命令会执行失败
增加NativeMem参数,重新启动java,可以查看更详细内存。
java -XX:NativeMemoryTracking=[off | summary | detail]
jmap命令
查询堆内存占用,并按大小排序
jmap -histo [pid] | sort -n -r -k 2 | head -20
dump jvm内存,然后可以使用工具MemoryAnalyzer分析内存
jmap -dump:live,format=b,file=/xxx/export_weight2.hprof [pid]
如果上述dump日志中,还未发现异常内存占用,可以排除jvm内存异常可能,以下分析native内存。
2 tcmalloc 分析native内存
tcmalloc native内存分配的追踪,原理是hook系统 malloc、free等内存申请释放函数的实现,增加profile的逻辑。
配置并使能tcmalloc
HEAPPROFILE=./heap.log
HEAP_PROFILE_ALLOCATION_INTERVAL=104857600
LD_PRELOAD=./libtcmalloc_and_profiler.so
java -jar xxx ...
使用pprof命令转换heap文件为pdf
pprof --pdf /usr/lib/jvm/jdk1.8.0_272/bin/java ./heap.log.0040.heap > ./heap.log.0040.heap.pdf
分析上述内存报告,查看大块内存是在哪里malloc,分析对应代码即可。