JVM之监控工具(下)

简介: JDK 提供了许多命令行工具来用于程序运行时的内存分析,这些工具能在处理应用程序性能问题、定位故障时发挥很大的作用。当 JDK 版本不同,操作系统不同,工具所支持的功能会有差别,这篇文章是基于Windows 10 的 JDK8 版本的环境。


三、可视化工具



JDK 提供大量的命令行工具外,还提供了两个功能强大的可视化工具 JConsole 和 VIsualVM,还有一个常用的商用工具 JProfiler,它们提供可视化界面,比前面的命令行工具使用起来更简单,监控内存数据更直观。


1. JConsole


JConsole(Java Monitoring and Management Console)是一种基于 JMX 的可视化监视、管理工具,我们可以在JAVA_HOME/bin目录下找到它,启动后可以直接连接本地虚拟机进程,也可以使用远程进程来连接远程服务器。它可以监控的内容有:

  • Memory:监视虚拟机内存,相当于 jstat 命令。
  • Threads:监控虚拟机线程,相当于 jstack 命令。
  • Classes:查看 Java 类加载的信息。
  • VM Summary:查看 JVM 摘要信息。
  • MBeans:查看所有 MBeans 的信息。

微信图片03.png


2. VisualVM


VisualVM(All-in-One Java Troubleshooting Tool)多合一故障处理工具是到目前为止随 JDK 发布的功能最强大的运行监视和故障处理工具,除此之外它还提供了很多其他方面的功能,如性能分析(Profiling),VisualVM 的性能分析功能比 JProfiler、YourKit 等专业且收费的工具都不会逊色,而且它不需要被监视的程序基于特殊 Agent 运行,因此它对应用程序的实际性能的影响很小,使得它可以直接应用在生产环境中。我们可以通过运行  JAVA_HOME/bin/jvisualvm.exe来启动它。

微信图片04.png

VisualVM 除了监视各种内存状况、查看类转储文件之外,还支持添加各种插件来扩展它的功能,例如添加 BTrace 插件来进行动态日志跟踪,它可以在不停止目标程序运行的前提下,通过 HotSpot 虚拟机的 HotSwap 技术动态加入原本并不存在的调试代码,我们经常会遇到程序出现问题,但排查错误的一些必要信息,比如方法参数、返回值等,在开发时并没有打印到日志当中,正常情况下需要停掉服务,加入日志代码来解决问题,而使用 BTrace 则不需要。假设我们存在下面代码程序:

public class Main {
    public static int add(int a, int b) {
        return a + b;
    }
    public static void main(String[] args) {
        System.out.println("Hello GC");
        try {
            Thread.sleep(30000);
            for (int i = 0, n = 10; i < n; i++) {
                System.out.println(add(1, 2));
            }
            Thread.sleep(Integer.MAX_VALUE);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}

在 VisualVM 中安装 BTrace 插件后,右击需要调试的程序点击Trace Application...菜单,进入 BTrace 面板,在里面编写代码如下:

微信图片05.png

BTrace 的用法还有很多,打印调用堆栈、参数、返回值只是最基本的应用,还可以用来性能监视、定位连接泄漏和内存泄漏、解决多线程竞争问题等。


3. JProfiler


JProfiler 是一个商业授权(收费)的 Java 性能分析工具,针对 Java SE 和 Java EE 应用程序开发,它的主要功能有:

  • 内存分析:显示所有对象数量和占用内存
  • 堆遍历:显示堆中所有类和它们的实例
  • CPU 分析:监控 CPU 使用情况
  • 线程分析:线程历史、线程监控、死锁探测等等

微信图片06.png

查看应用程序运行时类的实例个数和占用空间大小。

微信图片07.png


四、实战



Windows 下模拟及排查 CPU 占用高的问题


首先编写运行下面代码来模拟 CPU 占用高的场景:

public class CPU {
    public static void main(String[] args) {
        int i = 0;
        while (true) {
            i++;
        }
    }
}

在 Windows 系统下通过任务管理器来找到 CPU 占用高的 Java 进程,此时可以确定 CPU 占用高的应用程序进程号为 17368。

微信图片08.png

也可以使用命令jps -l来查看该进程下的 Java 应用程序。

微信图片09.png

在 Windows 下面不能直接查看到 CPU 占用高的应用程序中哪个线程 CPU 占用高,所以需要下载 Process Explorer 工具来查看,如下图,找到 CPU 占用高的应用进程。

微信图片010.png

然后右击进程进入属性界面,再点击Threads菜单项,就可以找到 CPU 占用高的线程 ID 为 17176。

微信图片011.png

通过计算器或其他方法将 17176 转换成十六进制格式为0x‭4318‬,最后使用jstack 17368来查看应用线程堆栈信息,定位到nid=0x4318的线程,就可以找到 CPU 占用高的程序代码了。

微信图片012.png


Linux 下模拟及排查 CPU 占用高的问题


在 Linux 下的操作过程和 Windows 下的一样,只是使用工具更简单,首先在服务器上运行同样的代码来模拟 CPU 占用过高的场景,然后使用top命令来定位,CPU 占用过高的 Java 程序进程为 18119。

微信图片013.png

使用top H -p 18119来查找该进程下的线程状态,可以定位到 CPU 占用过高的线程 ID 为 18120。

微信图片014.png

使用下面命令将 18120 转换成十六进制为46c8,最后使用 jstack 命令来定位出现 CPU 占用高的问题代码。

$ printf %x 18120
46c8
$ jstack 18119|grep -A10 46c8

微信图片015.png

线上发生问题时,需要冷静分析,配合使用工具来快速定位到线上问题,是一个合格的程序员所必备的技能。


目录
相关文章
|
Arthas 监控 Java
Jvm性能调优+监控工具Arthas【阿里开源】
Jvm性能调优+监控工具Arthas【阿里开源】
1019 0
|
6月前
|
Arthas 监控 数据可视化
JVM监控工具
Arthas 是一款线上监控诊断产品,通过全局视角实时查看应用 load、内存、gc、线程的状态信息,并能在不修改应用代码的情况下,对业务问题进行诊断,包括查看方法调用的出入参、异常,监测方法执行耗时,类加载信息等,大大提升线上问题排查效率。
50 0
|
监控 数据可视化 Java
JVM调优——JVM监控工具jvisualvm的使用及GC插件安装
JVM调优——JVM监控工具jvisualvm的使用及GC插件安装
207 1
JVM调优——JVM监控工具jvisualvm的使用及GC插件安装
|
存储 监控 Java
Java JVM监控工具JConsole简介
Java JVM监控工具JConsole简介
216 0
|
运维 监控 数据可视化
JVM之监控工具(上)
JDK 提供了许多命令行工具来用于程序运行时的内存分析,这些工具能在处理应用程序性能问题、定位故障时发挥很大的作用。当 JDK 版本不同,操作系统不同,工具所支持的功能会有差别,这篇文章是基于Windows 10 的 JDK8 版本的环境。
208 0
JVM之监控工具(上)
|
监控 Java 开发工具
推荐一个分布式JVM监控工具,实惠好用,开源(附源码)!
推荐一个分布式JVM监控工具,实惠好用,开源(附源码)!
307 0
推荐一个分布式JVM监控工具,实惠好用,开源(附源码)!
|
监控 算法 Java
5款强大的JVM 性能调优监控工具,您值得拥有 !
5款强大的JVM 性能调优监控工具,您值得拥有 !
410 0
5款强大的JVM 性能调优监控工具,您值得拥有 !
|
监控 Java
Java之JVM监控工具分享
Java之JVM监控工具分享VM的基本知识常用的也就是类加载机制,内存区域、分配、OOM,GC,JVM参数调优 几个链接自己看: 内存区域&类加载机制分配策略&垃圾回收算法、收集器今天结合代码讲一讲常用的java自带工具讲解,这些命令一般都是jdk/lib/tools.jar中。
3576 0
|
监控 Java 应用服务中间件
JVM性能调优监控工具jps、jstack、jmap、jhat、jstat、hprof使用详解
 现实企业级Java应用开发、维护中,有时候我们会碰到下面这些问题: OutOfMemoryError,内存不足 内存泄露 线程死锁 锁争用(Lock Contention) Java进程消耗CPU过高 ......     这些问题在日常开发、维护中可能被很多人忽视(比如有的人遇到上面的问题只是重启服务器或者调大内存,而不会深究问题根源),但能够理解并解决这些问题是Java程序员进阶的必备要求。
2846 0