HSDB: The top-level HotSpot Debugger
-
debugger
- gdb c,c++ based on ptrace
- jdb java jdi,jdwp,etc
- hsdb top-level
-
源碼
- openjdk/hotspot/agent/***/sun.jvm.hotspot/HSDB.java
-
Usage
- jps
- java -cp %JAVA_HOME%/lib/sa-jdi.jar sun.jvm.hotspot.HSDB help
通過HSDB來了解String值的真身在哪里
-
借HSDB來探索HotSpot VM的運行時數(shù)據(jù)
- javac -g xxx.java (Generate all debugging info 生成LocalVariableTable等調(diào)試信息)
- -XX:+UseSerialGC -Xmx10m
- 之前在GreenTeaJUG在杭州的活動演示Serviceability Agent的時候也講到過這是個非常便于探索HotSpot VM內(nèi)部實現(xiàn)的API,而HSDB則是在SA基礎(chǔ)上包裝起來的一個調(diào)試器。這次我們就用HSDB來做實驗
- SA的一個限制是它只實現(xiàn)了調(diào)試snapshot的功能:要么要讓被調(diào)試的目標(biāo)進程完全暫停,要么就調(diào)試core dump。
- 所以我們在用HSDB做實驗前,得先讓我們的Java程序運行到我們關(guān)注的點上才行。
- JPDA(java platform debugger architecture)
- jvmti(jvm tool interface)
- jdwp(java debugger wireless protocol)
- jdi(java debugger interface)
- IDE Debugger or jdb
- jdb
- jdb -XX:+UseSerialGC -Xmx10m
- stop in Test.fn
- run Main
- next
- jps
- java -cp .;%JAVA_HOME%/lib/sa-jdi.jar sun.jvm.hotspot.HSDB
- 連接上的pid進程顯示一些線程
- Signal Dispatcher Java的attach機制實現(xiàn)
- Attach Listener Java的attach機制實現(xiàn)
- Finalizer
- References Handler 堆外內(nèi)存 Cleaner對象的clean()方法調(diào)用
- main
- 查看main線程的棧 Stack Memory
- hsdb console
- 用universe命令來查看GC堆的地址范圍和使用情況
- 這里用的是HotSpot VM的serial GC。GC堆由young gen = DefNewGeneration(包括eden和兩個survivor space)、
- old gen = TenuredGeneration和perm gen = PermGen構(gòu)成。
- 其中young gen和old gen構(gòu)成了這種配置下HotSpot VM里的Java堆(Java heap),
- 而perm gen不屬于Java heap的一部分,它存儲的主要是元數(shù)據(jù)或者叫反射信息,主要用于實現(xiàn)JVM規(guī)范里的“方法區(qū)”概念
- scanoops
- scanoops 0x00000000fa400000 0x00000000fc2c0000 Test2
- scanoops接受兩個必選參數(shù)和一個可選參數(shù):必選參數(shù)是要掃描的地址范圍,一個是起始地址一個是結(jié)束地址;可選參數(shù)用于指定要掃描什么類型的對象實例。實際掃描的時候會掃出指定的類型及其派生類的實例。
- 左邊是對象的起始地址,右邊是對象的實際類型
- 通過whatis命令可以進一步知道它們都在eden之中分配給main線程的thread-local allocation buffer (TLAB)中
- 用inspect命令來查看對象的內(nèi)容
- 對象頭的第一個字段是mark word,記錄該對象的GC狀態(tài)、同步狀態(tài)、identity hash code之類的多種信息。
- 對象頭的第二個字段是個類型信息指針,klass pointer。這里因為默認開啟了壓縮指針,所以本來應(yīng)該是64位的指針存在了32位字段里。
- 最后還有4個字節(jié)是為了滿足對齊需求而做的填充(padding)。
- HotSpot VM內(nèi)部使用直接指針來實現(xiàn)Java引用
- 在64位環(huán)境中有可能啟用“壓縮指針”的功能把64位指針壓縮到只用32位來存。壓縮指針與非壓縮指針直接有非常簡單的1對1對應(yīng)關(guān)系,前者可以看作后者的特例
- 幸好HSDB內(nèi)建了revptrs命令,可以找出“反向指針”——如果a變量引用著b對象,那么從b對象出發(fā)去找a變量就是找一個“反向指針”
- revptrs 0x00000000fa49a710
- Oop for java/lang/Class @ 0x00000000fa499b00
- whatis / inspect
- Serviceability Agent對GenCollectedHeap系的GC支持得比較好,而對另外倆GC(Parallel GC和G1 GC)支持得沒那么好。
- 猜您是在用Parallel GC?其實稍微改造一下Serviceability Agent的Java部分就可以讓whatis正確顯示在哪里了。
-
References