第一次使用HSDB

今天看了几篇大佬关于HSDB使用的文章,本身也依样画葫芦的用来一下,强大的一匹!!!java

HSDB(Hotspot Debugger),JDK自带的工具,用于查看JVM运行时的状态。vim

HSDB位于C:\Program Files\Java\jdk1.8.0_212\lib里面,接下来启动HSDB:jvm

1 java -cp .\sa-jdi.jar sun.jvm.hotspot.HSDB

  正常启动以后界面是这样的:ide

  一篇空白,没啥好看的。固然有的同窗可能启动的时候会报错,我启动的时候也是报错了的:工具

  这个错是说有个.dll文件没找到,而后寻找的路径是C:\Program Files\Java\jre1.8.0_212\bin\,是去个人jre里面去找的,我在安装jdk的时候选择安装了外部的jre性能

  而后我就去jdk里面找了一下有没有这个dll文件,还真有,我就给copy到外部jre里面对应的目录里面了,接着启动HSDB就没有问题啦。spa

  接着上面的,咱们已经启动了HSDB,接下来能够关联到具体的JVM进程了,我这里准备了一段代码并启动,今天的用HSDB对JVM进行分析,就跟着这段代码走了线程

 1 public abstract class A {
 2 
 3     public void printMe() {
 4         System.out.println("I love vim");
 5     }
 6     public abstract void sayHello();
 7 
 8 }
 9 
10 public class B extends A{
11 
12     @Override
13     public void sayHello() {
14         System.out.println("hello, i am child B");
15     }
16 
17 }
18 
19 public class MyTest {
20 
21     public static void main(String[] args) throws IOException {
22         A obj = new B();
23         System.in.read();
24         System.out.println(obj);
25     }
26 
27 }

  运行代码以后,会卡在System.in.reda();这里,因而咱们能够查看JVM的进程,这里我是用jps命令来查看:3d

  能够看到刚才运行的代码的PID是5360,咱们在HSDB里面去关联进程:指针

  File > Attach to Hotspot process

  进来以后首先看到就是当前进程里面的线程:

  好,到此一步,咱们前面的准备工做已经OK了,接下来咱们的目的就是分析多态状况下的虚方法表,具体来讲就是分析B对象的vtable,首先找到B对象的

内存指针地址:

  Tools > Class Browser

  B对象的地址是0x0000000100062028,而后咱们去看这个对象的详细信息:

  Tools > Inspector

  找到有一行是vtable的,那就是该对象的虚方法表了,我这里是:

  咦,为何虚方法表现是方法有七个呢?这是由于,万物皆对象,对象都继承自Object,因此B对象继承了Object的5个方法,而后继承了A的一个方法,本身重写了

一个方法,因此是七个,如何验证呢?

  咱们能够用mem命令来查看,固然要先知道vtable的内存起始地址。这里能够这样算,由于vtable是在instanceKlass对象实例的尾部,而instanceKlass大小在

64 位系统的大小为 0x1B8,所以 vtable 的起始地址等于 instanceKlass 的内存首地址加上 0x1B8 等于 0x00000007C00605D0

  接下类咱们就用算出这个地址1000621E0去看:

  Windows > Console

  第一列是方法实际在堆中的内存地址,第二列则是内存指针地址,因而咱们拿到内存指针地址去A,B和Object中分别查看,能够看到前5行对应的是Object

的方法,第6行对应的是A对象中的方法,第7行则对应B对象中的方法,由此咱们能够得出如下结论:

1.vtable 是 Java 实现多态的基石,若是一个方法被继承和重写,会把 vtable 中指向父类的方法指针指向子类本身的实现。
2.Java 子类会继承父类的 vtable。Java 全部的类都会继承 java.lang.Object 类,Object 类有 5 个虚方法能够被继承和重写。当一个类不包含任何方法时,vtable 的长度也最小为 5,表示 Object 类的 5 
个虚方法
3.finalstatic 修饰的方法不会被放到 vtable 方法表里 4.当子类重写了父类方法,子类 vtable 本来指向父类的方法指针会被替换为子类的方法指针
5.子类的 vtable 保持了父类的 vtable 的顺序

  参考文章:

  jvm 性能调优工具之 jps

  借HSDB来探索HotSpot VM的运行时数据

  经过HSDB来了解String值的真身在哪里

  

  推荐小册:

  

相关文章
相关标签/搜索