Skip to content

Instantly share code, notes, and snippets.

@iamsixer
Last active November 16, 2023 08:05
Show Gist options
  • Star 2 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save iamsixer/e7c1b1d459f52effd1c345870387a2c3 to your computer and use it in GitHub Desktop.
Save iamsixer/e7c1b1d459f52effd1c345870387a2c3 to your computer and use it in GitHub Desktop.

jdk提供的各种工具存放在JAVA_HOME/bin/,使用时为了方便请将JAVA_HOME/bin/加入到Path

图形界面集成工具

  • 1、VisualVM:提供在Java 虚拟机(Java Virutal Machine, JVM) 上运行的Java 应用程序的详细信息
  • 2、jConsole:Java 自带性能监控工具
  • 3、TProfiler:阿里巴巴TProfiler是一个可以在生产环境长期使用的性能分析工具
  • 4、ha456.jar:IBM HeapAnalyzer
  • 5、BTrace:一个可以在不改代码、不重启应用的情况下,动态的查看程序运行细节的工具
  • 6、MAT:MAT(Memory Analyzer Tool)(Eclipse Memory Analyzer),一个基于Eclipse的内存分析工具,是一个快速、功能丰富的Java heap分析工具,它可以帮助我们查找内存泄漏和减少内存消耗

命令行工具

查看本机当前登录用户的java进程,显示当前所有Java进程的pid

命令格式:jps [ options ] [ hostid ] 注:如果不指定hostid就默认为当前主机或服务器,如果需要查看其他机器上的jvm进程,需要在待查看机器上启动jstatd。

-q:只显示pid,不显示class名称,jar文件名和传递给main 方法的参数,仅输出VM标识符,不包括classname,jar name,arguments in main method 
-m:输出传递给main 方法的参数,在嵌入式jvm上可能是null,输出main method的参数 
-l:输出应用程序main class的完整package名 或者 应用程序的jar文件完整路径名,输出完全的包名,应用主类名,jar的完全路径名 
-v:输出传递给JVM的参数,输出jvm参数 
-V:输出通过flag文件传递到JVM中的参数(.hotspotrc文件或-XX:Flags=所指定的文件 
-Joption:传递参数到vm,例如:-J-Xms512m

eg1:jps -m -l

2、jstack 参考:jstack命令(Java Stack Trace)

主要用来查看某个Java进程内的线程堆栈信息, jstack可以定位到线程堆栈,根据堆栈信息我们可以定位到具体代码,所以它在JVM性能调优中使用得非常多。

命令格式:jstack [option] pid

-l long listings,会打印出额外的锁信息,在发生死锁时可以用jstack -l pid来观察锁持有情况
-m mixed mode,不仅会输出Java堆栈信息,还会输出C/C++堆栈信息(比如Native方法)

3、jmap  参考:jmap命令(Java Memory Map)

用来查看或者导出堆内存使用状况,查看进程堆内存使用情况,包括使用的GC算法、堆配置参数和各代中堆内存使用情况,一般结合jhat使用

命令格式:jmap [option] pid 注:如果运行在64位JVM上,可能需要指定-J-d64命令选项参数。

eg1:jmap -heap pid 注:显示堆内存分布使用情况
eg2:jmap -permstat pid 注:打印进程的类加载器和类加载器加载的持久代对象信息,输出:类加载器名称、对象是否存活(不可靠)、对象地址、父类加载器、已加载的类大小等信息
eg3:jmap -histo pid >>1.txt 注:查看pid中类的内存占用
eg4:jmap -dump:format=b,file=heap.bin 3676 注:把pid为3676的jvm进程内存镜像以二进制的方式保存到本地heap.bin文件

4、jstat  参考:[jstat命令(Java Virtual Machine Statistics Monitoring Tool)(http://blog.csdn.net/fenglibing/article/details/6411951)

Jstat用于监控基于HotSpot的JVM,对其堆的使用情况进行实时的命令行的统计,使用jstat我们可以对指定的JVM做如下监控:

  • 类的加载及卸载情况
  • 查看新生代、老生代及持久代的容量及使用情况
  • 查看新生代、老生代及持久代的垃圾收集情况,包括垃圾回收的次数及垃圾回收所占用的时间
  • 查看新生代中Eden区及Survior区中容量及分配情况等 jstat工具特别强大,它有众多的可选项,通过提供多种不同的监控维度,使我们可以从不同的维度来了解到当前JVM堆的使用情况。详细查看堆内各个部分的使用量,使用的时候必须加上待统计的Java进程号,可选的不同维度参数以及可选的统计频率参数。
命令格式:jstat [ generalOption | outputOptions vmid [interval[s|ms] [count]] ]

eg1:jstat -gc 21711 250 4 注:pid为21711,采样时间间隔为250ms,采样数为4

1:堆内存 = 年轻代 + 年老代 + 永久代
2:年轻代 = Eden区 + 两个Survivor区(From和To)

各列含义:
1:S0C、S1C、S0U、S1U:Survivor 0/1区容量(Capacity)和使用量(Used)
2:EC、EU:Eden区容量和使用量
3:OC、OU:年老代容量和使用量
4:PC、PU:永久代容量和使用量
5:YGC、YGT:年轻代GC次数和GC耗时
6:FGC、FGCT:FullGC次数和Full GC耗时
7:GCT:GC总耗时

eg2:jstat -gcutil [pid] [internal(时间间隔)] 

各列含义:
S0: Survivor space 0 区已使用空间的百分比
S1: Survivor space 1 区已使用空间的百分比
E: Eden space 区已使用空间的百分比
O: Old space 区已使用空间的百分比
P: Perm space 区已使用空间的百分比
YGC: Young GC 的次数
YGCT: Young GC 所用的时间 单位秒
FGC: Full GC 的次数
FGCT: Full GC 所用的时间 单位秒
GCT: 用于垃圾回收的总时间 单位秒 

Sun提供的内存镜像分析工具,是用来分析Java堆的命令,可以将堆中的对象以html的形式显示出来,包括对象的数量,大小等等,并支持对象查询语言。用于对JAVA heap进行离线分析的工具,他可以对不同虚拟机中导出的heap信息文件进行分析,如Linux上导出的文件可以拿到WINDOWS上进行分析,可以查找诸如内存方面的问题

第一步:导出堆 jmap -dump:format=b,file=heap.bin 15491
第二步:分析堆文件 jhat heap.bin
第三步:查看html http://localhost:7000/

注:有时你dump出来的堆很大,在启动时会报堆空间不足的错误,可以使用如下参数:jhat -J-Xmx512m <heap dump file>

可以输出并修改运行时的java 进程的opts。用处比较简单,用于输出JAVA系统参数及命令行参数。

命令格式:jinfo -opt  pid

eg:jinfo -flag MaxPermSize 2788  查看2788的MaxPerm大小可以用

一个基于RMI(Remove Method Invocation)的服务程序,它用于监控基于HotSpot的JVM中资源的创建及销毁,并且提供了一个远程接口允许远程的监控工具连接到本地的JVM执行命令。 jstatd是基于RMI的,所以在运行jstatd的服务器上必须存在RMI注册中心,如果没有通过选项"-p port"指定要连接的端口,jstatd会尝试连接RMI注册中心的默认端口。后面会谈到如何连接到一个默认的RMI内部注册中心,如何禁止默认的RMI内部注册中心的创建,以及如何启动一个外部注册中心。

eg1:下面这个示例演示了通过内部RMI注册中心启动jstatd,这个示例假设没有其它的服务绑定到默认的RMI注册中心端口(默认端口是1099)。
jstatd -J-Djava.security.policy=jstatd.all.policy  

其他注意的地方:

  • 尽量减少Full GC的次数, 因为Full GC的消耗要比Monitor GC要大
  • 年轻代大小: 尽可能设大, 降低年轻代GC次数, 同时也减少达到老年代的对象?
  • 分配堆栈的最小值最好等于最大值, 因为动态分配也是需要耗费时间的. 如年轻代, 老年代, 持久代的最小最大值可设为一致

参考:

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment