jps
命令用于查詢正在運(yùn)行的JVM進(jìn)程
命令格式
options參數(shù)解釋:
-l : 輸出主類全名或jar路徑
-q : 只輸出LVMID
-m : 輸出JVM啟動(dòng)時(shí)傳遞給main()的參數(shù)
-v : 輸出JVM啟動(dòng)時(shí)顯示指定的JVM參數(shù)
jps
>jps
10856 Launcher
14840 Jps
15016 KotlinCompileDaemon
12368 ThisMonitor
13260 JConsole
13324 Launcher
5756
jps -l
>jps -l
1856 jdk.jcmd/sun.tools.jps.Jps
10856 org.jetbrains.jps.cmdline.Launcher
15016 org.jetbrains.kotlin.daemon.KotlinCompileDaemon
12368 com.james.example.thread.jcp_multithread_architecture.chapter4.ThisMonitor
13260 jdk.jconsole/sun.tools.jconsole.JConsole
13324 org.jetbrains.jps.cmdline.Launcher
5756
jinfo
用于查詢當(dāng)前運(yùn)行這的JVM屬性和參數(shù)的值
options參數(shù)解釋:
-flag 打印指定名稱的參數(shù)
-flag [+|-] 打開或關(guān)閉參數(shù)
-flag = 設(shè)置參數(shù)
-flags 打印所有參數(shù)
-sysprops 打印系統(tǒng)配置
jinfo -flags 12368
> jinfo -flags 12368
VM Flags:
-XX:CICompilerCount=4 -XX:ConcGCThreads=3 -XX:G1ConcRefinementThreads=10 -XX:G1HeapRegionSize=1048576 -XX:GCDrainStackTargetSize=64 -XX:InitialHeapSize=266338304 -XX:MarkStackSize=4194304 -XX:MaxHeapSize=
4255121408 -XX:MaxNewSize=2552233984 -XX:MinHeapDeltaBytes=1048576 -XX:NonNMethodCodeHeapSize=5836300 -XX:NonProfiledCodeHeapSize=122910970 -XX:ProfiledCodeHeapSize=122910970 -XX:ReservedCodeCacheSize=251
658240 -XX:+SegmentedCodeCache -XX:+UseCompressedClassPointers -XX:+UseCompressedOops -XX:+UseG1GC -XX:-UseLargePagesIndividualAllocation
jinfo -sysprops 12368
> jinfo -sysprops 12368
Java System Properties:
sun.desktop=windows
awt.toolkit=sun.awt.windows.WToolkit
java.specification.version=11
sun.cpu.isalist=amd64
sun.jnu.encoding=GBK
java.class.path=D\:\\workspace\\thread-exercise\\target\\classes
java.vm.vendor=Amazon.com Inc.
sun.arch.data.model=64
user.variant=
java.vendor.url=https\://aws.amazon.com/corretto/
user.timezone=Asia/Shanghai
java.vm.specification.version=11
os.name=Windows 10
sun.java.launcher=SUN_STANDARD
user.country=CN
sun.boot.library.path=D\:\\DevelopTools\\jdk\\jdk11.0.9_11\\bin
sun.java.command=com.james.example.thread.jcp_multithread_architecture.chapter4.ThisMonitor
jdk.debug=release
sun.cpu.endian=little
user.home=C\:\\Users\\Andy
user.language=zh
java.specification.vendor=Oracle Corporation
java.version.date=2020-10-20
java.home=D\:\\DevelopTools\\jdk\\jdk11.0.9_11
file.separator=\\
java.vm.compressedOopsMode=Zero based
line.separator=\r\n
java.specification.name=Java Platform API Specification
java.vm.specification.vendor=Oracle Corporation
java.awt.graphicsenv=sun.awt.Win32GraphicsEnvironment
user.script=
sun.management.compiler=HotSpot 64-Bit Tiered Compilers
java.runtime.version=11.0.9+11-LTS
user.name=James
path.separator=;
os.version=10.0
java.runtime.name=OpenJDK Runtime Environment
file.encoding=UTF-8
java.vm.name=OpenJDK 64-Bit Server VM
java.version=11.0.9
user.dir=D\:\\workspace\\thread-exercise
os.arch=amd64
java.vm.specification.name=Java Virtual Machine Specification
java.awt.printerjob=sun.awt.windows.WPrinterJob
sun.os.patch.level=
java.library.path=
java.vm.info=mixed mode
java.vendor=Amazon.com Inc.
java.vm.version=11.0.9+11-LTS
sun.io.unicode.encoding=UnicodeLittle
java.class.version=55.0
jstat
可以實(shí)時(shí)顯示本地或遠(yuǎn)程JVM進(jìn)程中類裝載敷存、內(nèi)存翠储、垃圾收集栖袋、JIT編譯等數(shù)據(jù)
-<option> required
Usage: jstat --help|-options
jstat -<option> [-t] [-h<lines>] <vmid> [<interval> [<count>]]
其中vmid是進(jìn)程id剂娄,interval是打印間隔時(shí)間(毫秒)警绩,count是打印次數(shù)(默認(rèn)一直打印)
option
-class class loader的行為統(tǒng)計(jì)
-compiler HotSpt JIT編譯器行為統(tǒng)計(jì)
-gc 垃圾回收堆的行為統(tǒng)計(jì)
-gccapacity 各個(gè)垃圾回收代容量(young,old,perm)和他們相應(yīng)的空間統(tǒng)計(jì)
-gcutil 垃圾回收統(tǒng)計(jì)概述
-gccause 垃圾收集統(tǒng)計(jì)概述(同-gcutil)曲聂,附加最近兩次垃圾回收事件的原因
-gcnew 新生代行為統(tǒng)計(jì)
-gcnewcapacity 新生代與其相應(yīng)的內(nèi)存空間的統(tǒng)計(jì)
-gcold 年老代和永生代行為統(tǒng)計(jì)
-gcoldcapacity 年老代行為統(tǒng)計(jì)
-gcpermcapacity 永生代行為統(tǒng)計(jì)
-printcompilation HotSpot編譯方法統(tǒng)計(jì)
jstat -class 12368 3000 3 類加載統(tǒng)計(jì)
>jstat -class 12368 3000 3
Loaded Bytes Unloaded Bytes Time
934 2162.8 0 0.0 0.06
934 2162.8 0 0.0 0.06
934 2162.8 0 0.0 0.06
Loaded 加載類的數(shù)量
Bytes 加載類合計(jì)大小
Unloaded 卸載類的數(shù)量
Bytes 卸載類合計(jì)大小
Time 表示加載和卸載類總共的耗時(shí)
jstat -compiler 12368 3000 3 編譯統(tǒng)計(jì)
>jstat -compiler 12368 3000 3
Compiled Failed Invalid Time FailedType FailedMethod
216 0 0 0.06 0
216 0 0 0.06 0
216 0 0 0.06 0
Compiled 表示編譯任務(wù)執(zhí)行的次數(shù)
Failed 表示編譯失敗的次數(shù)
Invalid 表示編譯不可用的次數(shù)
Time 表示編譯的總耗時(shí)
FailedType 表示最后一次編譯的類型
FailedMethod 表示最后一次編譯失敗的類名和方法名
jstat -gc 12368 3000 3 垃圾回收統(tǒng)計(jì)
>jstat -gc 12368
S0C S1C S0U S1U EC EU OC OU MC MU CCSC CCSU YGC YGCT FGC FGCT CGC CGCT GCT
0.0 0.0 0.0 0.0 26624.0 4096.0 233472.0 0.0 0.0 0.0 0.0 0.0 0 0.000 0 0.000 0 0.000 0.000
0.0 0.0 0.0 0.0 26624.0 4096.0 233472.0 0.0 0.0 0.0 0.0 0.0 0 0.000 0 0.000 0 0.000 0.000
0.0 0.0 0.0 0.0 26624.0 4096.0 233472.0 0.0 0.0 0.0 0.0 0.0 0 0.000 0 0.000 0 0.000 0.000
字段解釋:
S0C survivor0大小
S1C survivor1大小
S0U survivor0已使用大小
S1U survivor1已使用大小
EC Eden區(qū)大小
EU Eden區(qū)已使用大小
OC 老年代大小
OU 老年代已使用大小
MC 方法區(qū)大小
MU 方法區(qū)已使用大小
CCSC 壓縮類空間大小
CCSU 壓縮類空間已使用大小
YGC 年輕代垃圾回收次數(shù)
YGCT 年輕代垃圾回收消耗時(shí)間
FGC 老年代垃圾回收次數(shù)
FGCT 老年代垃圾回收消耗時(shí)間
GCT 垃圾回收消耗總時(shí)間
jstat -gccapacity 12368 3000 3 堆內(nèi)存統(tǒng)計(jì)
>jstat -gccapacity 12368 3000 3
NGCMN NGCMX NGC S0C S1C EC OGCMN OGCMX OGC OC MCMN MCMX MC CCSMN CCSMX CCSC YGC FGC CGC
0.0 4155392.0 26624.0 0.0 0.0 26624.0 0.0 4155392.0 233472.0 233472.0 0.0 1056768.0 0.0 0.0 1048576.0 0.0 0 0 0
0.0 4155392.0 26624.0 0.0 0.0 26624.0 0.0 4155392.0 233472.0 233472.0 0.0 1056768.0 0.0 0.0 1048576.0 0.0 0 0 0
0.0 4155392.0 26624.0 0.0 0.0 26624.0 0.0 4155392.0 233472.0 233472.0 0.0 1056768.0 0.0 0.0 1048576.0 0.0 0 0 0
NGCMN:新生代最小值(KB)
NGVMX:新生代最大值(KB)
NGC:當(dāng)前新生代大兴盗濉(KB)
S0C:同上
S1C:同上
EC:同上
OGCMN:老年代最小值(KB)
OGCMX:老年代最大值(KB)
OGC:當(dāng)前老年代大小(KB)
OC:同上
MCMN :方法區(qū)最小值(KB)
MCMX :方法區(qū)最大值(KB)
MCC :當(dāng)前方法區(qū)大谢侣(KB)
CCSMN : 壓縮類空間最大值
CCSMX : 壓縮類空間最小值
CCSC :當(dāng)前壓縮類空間大小
YGC:年輕代垃圾回收次數(shù)
FGC:老年代垃圾回收次數(shù)
jstat -gccause 12368 3000 3 顯示垃圾回收的相關(guān)信息
>jstat -gccause 12368 3000 3
S0 S1 E O M CCS YGC YGCT FGC FGCT CGC CGCT GCT LGCC GCC
0.00 0.00 15.38 0.00 - - 0 0.000 0 0.000 0 0.000 0.000 No GC No GC
0.00 0.00 15.38 0.00 - - 0 0.000 0 0.000 0 0.000 0.000 No GC No GC
0.00 0.00 15.38 0.00 - - 0 0.000 0 0.000 0 0.000 0.000 No GC No GC
LGCC:上一次GC的原因宙址,是G1垃圾回收器回收
GCC :當(dāng)前GC的原因
jstat -gcnew 12368 3000 3 顯示新生代的詳細(xì)信息
>jstat -gcnew 12368 3000 3
S0C S1C S0U S1U TT MTT DSS EC EU YGC YGCT
0.0 0.0 0.0 0.0 15 15 0.0 26624.0 4096.0 0 0.000
0.0 0.0 0.0 0.0 15 15 0.0 26624.0 4096.0 0 0.000
0.0 0.0 0.0 0.0 15 15 0.0 26624.0 4096.0 0 0.000
S0C:第一個(gè)幸存區(qū)大小
S1C:第二個(gè)幸存區(qū)的大小
S0U:第一個(gè)幸存區(qū)的使用大小
S1U:第二個(gè)幸存區(qū)的使用大小
TT:對(duì)象在新生代存活的次數(shù)
MTT:對(duì)象在新生代存活的最大次數(shù)
DSS:期望的幸存區(qū)大小
EC:伊甸園區(qū)的大小
EU:伊甸園區(qū)的使用大小
YGC:年輕代垃圾回收次數(shù)
YGCT:年輕代垃圾回收消耗時(shí)間
jstat -gcnewcapacity 12368 3000 3 新生代各個(gè)區(qū)的詳細(xì)信息
>jstat -gcnewcapacity 12368 3000 3
NGCMN NGCMX NGC S0CMX S0C S1CMX S1C ECMX EC YGC FGC CGC
0.0 4155392.0 26624.0 0.0 0.0 4155392.0 0.0 4155392.0 26624.0 0 0 0
0.0 4155392.0 26624.0 0.0 0.0 4155392.0 0.0 4155392.0 26624.0 0 0 0
0.0 4155392.0 26624.0 0.0 0.0 4155392.0 0.0 4155392.0 26624.0 0 0 0
NGCMN:新生代最小容量
NGCMX:新生代最大容量
NGC:當(dāng)前新生代容量
S0CMX:最大幸存1區(qū)大小
S0C:當(dāng)前幸存1區(qū)大小
S1CMX:最大幸存2區(qū)大小
S1C:當(dāng)前幸存2區(qū)大小
ECMX:最大伊甸園區(qū)大小
EC:當(dāng)前伊甸園區(qū)大小
YGC:年輕代垃圾回收次數(shù)
FGC:老年代回收次數(shù)
jstat -gcold 12368 3000 3 老年代垃圾回收統(tǒng)計(jì)
>jstat -gcold 12368 3000 3
MC MU CCSC CCSU OC OU YGC FGC FGCT CGC CGCT GCT
0.0 0.0 0.0 0.0 233472.0 0.0 0 0 0.000 0 0.000 0.000
0.0 0.0 0.0 0.0 233472.0 0.0 0 0 0.000 0 0.000 0.000
0.0 0.0 0.0 0.0 233472.0 0.0 0 0 0.000 0 0.000 0.000
MC:方法區(qū)大小
MU:方法區(qū)使用大小
CCSC:壓縮類空間大小
CCSU:壓縮類空間使用大小
OC:老年代大小
OU:老年代使用大小
YGC:年輕代垃圾回收次數(shù)
FGC:老年代垃圾回收次數(shù)
FGCT:老年代垃圾回收消耗時(shí)間
GCT:垃圾回收消耗總時(shí)間
jstat -gcoldcapacity 12368 3000 3 老年代各個(gè)區(qū)的詳細(xì)信息
> jstat -gcoldcapacity 12368 3000 3
OGCMN OGCMX OGC OC YGC FGC FGCT CGC CGCT GCT
0.0 4155392.0 233472.0 233472.0 0 0 0.000 0 0.000 0.000
0.0 4155392.0 233472.0 233472.0 0 0 0.000 0 0.000 0.000
0.0 4155392.0 233472.0 233472.0 0 0 0.000 0 0.000 0.000
OGCMN:老年代最小容量
OGCMX:老年代最大容量
OGC:當(dāng)前老年代大小
OC:老年代大小
YGC:年輕代垃圾回收次數(shù)
FGC:老年代垃圾回收次數(shù)
FGCT:老年代垃圾回收消耗時(shí)間
GCT:垃圾回收消耗總時(shí)間
jstat -gcmetacapacity 12368 3000 3 元數(shù)據(jù)空間統(tǒng)計(jì)
>jstat -gcmetacapacity 12368 3000 3
MCMN MCMX MC CCSMN CCSMX CCSC YGC FGC FGCT CGC CGCT GCT
0.0 1056768.0 0.0 0.0 1048576.0 0.0 0 0 0.000 0 0.000 0.000
0.0 1056768.0 0.0 0.0 1048576.0 0.0 0 0 0.000 0 0.000 0.000
0.0 1056768.0 0.0 0.0 1048576.0 0.0 0 0 0.000 0 0.000 0.000
MCMN:最小元數(shù)據(jù)容量
MCMX:最大元數(shù)據(jù)容量
MC:當(dāng)前元數(shù)據(jù)空間大小
CCSMN:最小壓縮類空間大小
CCSMX:最大壓縮類空間大小
CCSC:當(dāng)前壓縮類空間大小
YGC:年輕代垃圾回收次數(shù)
FGC:老年代垃圾回收次數(shù)
FGCT:老年代垃圾回收消耗時(shí)間
GCT:垃圾回收消耗總時(shí)間
jstat -gcutil 12368 3000 3 總體垃圾回收統(tǒng)計(jì)
>jstat -gcutil 12368 3000 3
S0 S1 E O M CCS YGC YGCT FGC FGCT CGC CGCT GCT
0.00 0.00 15.38 0.00 - - 0 0.000 0 0.000 0 0.000 0.000
0.00 0.00 15.38 0.00 - - 0 0.000 0 0.000 0 0.000 0.000
0.00 0.00 15.38 0.00 - - 0 0.000 0 0.000 0 0.000 0.000
S0 survivor0使用百分比
S1 survivor1使用百分比
E Eden區(qū)使用百分比
O 老年代使用百分比
M 元數(shù)據(jù)區(qū)使用百分比
CCS 壓縮使用百分比
YGC 年輕代垃圾回收次數(shù)
YGCT 年輕代垃圾回收消耗時(shí)間
FGC 老年代垃圾回收次數(shù)
FGCT 老年代垃圾回收消耗時(shí)間
GCT 垃圾回收消耗總時(shí)間
jstat -printcompilation 12368 3000 3 編譯方法統(tǒng)計(jì)
>jstat -printcompilation 12368 3000 3
Compiled Size Type Method
221 382 1 java/util/HashMap putVal
221 382 1 java/util/HashMap putVal
221 382 1 java/util/HashMap putVal
Compiled:最近編譯方法的數(shù)量
Size:最近編譯方法的字節(jié)碼數(shù)量
Type:最近編譯方法的編譯類型。
Method:方法名標(biāo)識(shí)调卑。
jstack
通過(guò)jstack可以觀察到j(luò)vm中當(dāng)前所有線程的運(yùn)行情況和線程當(dāng)前狀態(tài),可以用來(lái)分析線程問(wèn)題(如死鎖)抡砂。
想要通過(guò)jstack命令來(lái)分析線程的情況的話,首先要知道線程都有哪些狀態(tài)恬涧, 如果有不清楚的可以參考下面連接: 多線程——線程的生命周期.
jstack [ option ] pid
-l long listings注益,會(huì)打印出額外的鎖信息,在發(fā)生死鎖時(shí)可以用jstack -l pid來(lái)觀察鎖持有情況
-m mixed mode溯捆,不僅會(huì)輸出Java堆棧信息丑搔,還會(huì)輸出C/C++堆棧信息(比如Native方法)
D:\workspace\thread-exercise>jstack 12368
Full thread dump OpenJDK 64-Bit Server VM (11.0.9+11-LTS mixed mode):
Threads class SMR info:
_java_thread_list=0x000002052fc3c090, length=14, elements={
0x000002052fa3e800, 0x000002052fa47800, 0x000002052fab4000, 0x000002052fab5000,
0x000002052fab7000, 0x000002052fabe000, 0x000002052fabf800, 0x000002052fa00800,
0x000002052fd57000, 0x000002052fdd2800, 0x000002052fde4000, 0x000002052fdec000,
0x000002052fddd800, 0x000002052fddf000
}
"Reference Handler" #2 daemon prio=10 os_prio=2 cpu=0.00ms elapsed=917.24s tid=0x000002052fa3e800 nid=0x2a9c waiting on condition [0x000000bd0ecff000]
java.lang.Thread.State: RUNNABLE
at java.lang.ref.Reference.waitForReferencePendingList(java.base@11.0.9/Native Method)
at java.lang.ref.Reference.processPendingReferences(java.base@11.0.9/Reference.java:241)
at java.lang.ref.Reference$ReferenceHandler.run(java.base@11.0.9/Reference.java:213)
"Finalizer" #3 daemon prio=8 os_prio=1 cpu=0.00ms elapsed=917.24s tid=0x000002052fa47800 nid=0x2f88 in Object.wait() [0x000000bd0edfe000]
java.lang.Thread.State: WAITING (on object monitor)
at java.lang.Object.wait(java.base@11.0.9/Native Method)
- waiting on <0x0000000712308f18> (a java.lang.ref.ReferenceQueue$Lock)
at java.lang.ref.ReferenceQueue.remove(java.base@11.0.9/ReferenceQueue.java:155)
- waiting to re-lock in wait() <0x0000000712308f18> (a java.lang.ref.ReferenceQueue$Lock)
at java.lang.ref.ReferenceQueue.remove(java.base@11.0.9/ReferenceQueue.java:176)
at java.lang.ref.Finalizer$FinalizerThread.run(java.base@11.0.9/Finalizer.java:170)
"Signal Dispatcher" #4 daemon prio=9 os_prio=2 cpu=0.00ms elapsed=917.22s tid=0x000002052fab4000 nid=0x138 runnable [0x0000000000000000]
java.lang.Thread.State: RUNNABLE
"Attach Listener" #5 daemon prio=5 os_prio=2 cpu=15.63ms elapsed=917.22s tid=0x000002052fab5000 nid=0x47c0 waiting on condition [0x0000000000000000]
java.lang.Thread.State: RUNNABLE
"C2 CompilerThread0" #6 daemon prio=9 os_prio=2 cpu=31.25ms elapsed=917.22s tid=0x000002052fab7000 nid=0x4594 waiting on condition [0x0000000000000000]
java.lang.Thread.State: RUNNABLE
No compile task
"C1 CompilerThread0" #9 daemon prio=9 os_prio=2 cpu=62.50ms elapsed=917.22s tid=0x000002052fabe000 nid=0x43b0 waiting on condition [0x0000000000000000]
java.lang.Thread.State: RUNNABLE
No compile task
"Sweeper thread" #10 daemon prio=9 os_prio=2 cpu=0.00ms elapsed=917.22s tid=0x000002052fabf800 nid=0x1b04 runnable [0x0000000000000000]
java.lang.Thread.State: RUNNABLE
"Common-Cleaner" #11 daemon prio=8 os_prio=1 cpu=0.00ms elapsed=917.19s tid=0x000002052fa00800 nid=0x46fc in Object.wait() [0x000000bd0f3ff000]
java.lang.Thread.State: TIMED_WAITING (on object monitor)
at java.lang.Object.wait(java.base@11.0.9/Native Method)
- waiting on <0x000000071222ef90> (a java.lang.ref.ReferenceQueue$Lock)
at java.lang.ref.ReferenceQueue.remove(java.base@11.0.9/ReferenceQueue.java:155)
- waiting to re-lock in wait() <0x000000071222ef90> (a java.lang.ref.ReferenceQueue$Lock)
at jdk.internal.ref.CleanerImpl.run(java.base@11.0.9/CleanerImpl.java:148)
at java.lang.Thread.run(java.base@11.0.9/Thread.java:829)
at jdk.internal.misc.InnocuousThread.run(java.base@11.0.9/InnocuousThread.java:134)
"Monitor Ctrl-Break" #12 daemon prio=5 os_prio=0 cpu=15.63ms elapsed=917.14s tid=0x000002052fd57000 nid=0x427c runnable [0x000000bd0f5fe000]
java.lang.Thread.State: RUNNABLE
at java.net.SocketInputStream.socketRead0(java.base@11.0.9/Native Method)
at java.net.SocketInputStream.socketRead(java.base@11.0.9/SocketInputStream.java:115)
at java.net.SocketInputStream.read(java.base@11.0.9/SocketInputStream.java:168)
at java.net.SocketInputStream.read(java.base@11.0.9/SocketInputStream.java:140)
at sun.nio.cs.StreamDecoder.readBytes(java.base@11.0.9/StreamDecoder.java:284)
at sun.nio.cs.StreamDecoder.implRead(java.base@11.0.9/StreamDecoder.java:326)
at sun.nio.cs.StreamDecoder.read(java.base@11.0.9/StreamDecoder.java:178)
- locked <0x0000000712081138> (a java.io.InputStreamReader)
at java.io.InputStreamReader.read(java.base@11.0.9/InputStreamReader.java:185)
at java.io.BufferedReader.fill(java.base@11.0.9/BufferedReader.java:161)
at java.io.BufferedReader.readLine(java.base@11.0.9/BufferedReader.java:326)
- locked <0x0000000712081138> (a java.io.InputStreamReader)
at java.io.BufferedReader.readLine(java.base@11.0.9/BufferedReader.java:392)
at com.intellij.rt.execution.application.AppMainV2$1.run(AppMainV2.java:64)
"Service Thread" #13 daemon prio=9 os_prio=0 cpu=0.00ms elapsed=917.14s tid=0x000002052fdd2800 nid=0x4110 runnable [0x0000000000000000]
java.lang.Thread.State: RUNNABLE
"T1" #14 prio=5 os_prio=0 cpu=0.00ms elapsed=917.14s tid=0x000002052fde4000 nid=0x25f4 waiting on condition [0x000000bd0f8fe000]
java.lang.Thread.State: TIMED_WAITING (sleeping)
at java.lang.Thread.sleep(java.base@11.0.9/Native Method)
at java.lang.Thread.sleep(java.base@11.0.9/Thread.java:334)
at java.util.concurrent.TimeUnit.sleep(java.base@11.0.9/TimeUnit.java:446)
at com.james.example.thread.jcp_multithread_architecture.chapter4.ThisMonitor.method1(ThisMonitor.java:15)
- locked <0x0000000712191f68> (a com.james.example.thread.jcp_multithread_architecture.chapter4.ThisMonitor)
at com.james.example.thread.jcp_multithread_architecture.chapter4.ThisMonitor$$Lambda$14/0x0000000800066c40.run(Unknown Source)
at java.lang.Thread.run(java.base@11.0.9/Thread.java:829)
"T2" #15 prio=5 os_prio=0 cpu=0.00ms elapsed=917.14s tid=0x000002052fdec000 nid=0x3710 waiting for monitor entry [0x000000bd0f9ff000]
java.lang.Thread.State: BLOCKED (on object monitor)
at com.james.example.thread.jcp_multithread_architecture.chapter4.ThisMonitor.method2(ThisMonitor.java:23)
- waiting to lock <0x0000000712191f68> (a com.james.example.thread.jcp_multithread_architecture.chapter4.ThisMonitor)
at com.james.example.thread.jcp_multithread_architecture.chapter4.ThisMonitor$$Lambda$15/0x0000000800066040.run(Unknown Source)
at java.lang.Thread.run(java.base@11.0.9/Thread.java:829)
"T3" #16 prio=5 os_prio=0 cpu=15.63ms elapsed=917.14s tid=0x000002052fddd800 nid=0x4758 waiting for monitor entry [0x000000bd0faff000]
java.lang.Thread.State: BLOCKED (on object monitor)
at com.james.example.thread.jcp_multithread_architecture.chapter4.ThisMonitor.method2(ThisMonitor.java:23)
- waiting to lock <0x0000000712191f68> (a com.james.example.thread.jcp_multithread_architecture.chapter4.ThisMonitor)
at com.james.example.thread.jcp_multithread_architecture.chapter4.ThisMonitor$$Lambda$16/0x0000000800066440.run(Unknown Source)
at java.lang.Thread.run(java.base@11.0.9/Thread.java:829)
"DestroyJavaVM" #17 prio=5 os_prio=0 cpu=140.63ms elapsed=917.14s tid=0x000002052fddf000 nid=0x1744 waiting on condition [0x0000000000000000]
java.lang.Thread.State: RUNNABLE
"VM Thread" os_prio=2 cpu=0.00ms elapsed=917.25s tid=0x000002052fa1d800 nid=0x32ec runnable
"GC Thread#0" os_prio=2 cpu=0.00ms elapsed=917.26s tid=0x000002050b0f6800 nid=0x47e0 runnable
"G1 Main Marker" os_prio=2 cpu=0.00ms elapsed=917.26s tid=0x000002050b158000 nid=0x44e4 runnable
"G1 Conc#0" os_prio=2 cpu=0.00ms elapsed=917.26s tid=0x000002050b15a800 nid=0x478 runnable
"G1 Refine#0" os_prio=2 cpu=0.00ms elapsed=917.26s tid=0x000002052ea07800 nid=0x31b8 runnable
"G1 Young RemSet Sampling" os_prio=2 cpu=0.00ms elapsed=917.26s tid=0x000002052ea08800 nid=0x1854 runnable
"VM Periodic Task Thread" os_prio=2 cpu=0.00ms elapsed=917.14s tid=0x000002052fdd4800 nid=0x1a10 waiting on condition
JNI global refs: 16, weak refs: 0
jmap
Usage:
jmap -clstats <pid>
to connect to running process and print class loader statistics
jmap -finalizerinfo <pid>
to connect to running process and print information on objects awaiting finalization
jmap -histo[:live] <pid>
to connect to running process and print histogram of java object heap
if the "live" suboption is specified, only count live objects
jmap -dump:<dump-options> <pid>
to connect to running process and dump java heap
jmap -? -h --help
to print this help message
dump-options:
live dump only live objects; if not specified,
all objects in the heap are dumped.
format=b binary format
file=<file> dump heap to <file>
Example: jmap -dump:live,format=b,file=heap.bin <pid>
heap: 顯示Java堆詳細(xì)信息
histo[:live]: 顯示堆中對(duì)象的統(tǒng)計(jì)信息
clstats:打印類加載器信息
finalizerinfo: 顯示在F-Queue隊(duì)列等待Finalizer線程執(zhí)行finalizer方法的對(duì)象
dump:<dump-options>:生成堆轉(zhuǎn)儲(chǔ)快照
jmap -dump:live,format=b,file=heap.bin <pid>
jmap -histo 12368
可以觀察heap中所有對(duì)象的情況(heap中所有生存的對(duì)象的情況)。包括對(duì)象數(shù)量和所占空間大小
>jmap -histo[:live] 12368
num #instances #bytes class name (module)
-------------------------------------------------------
1: 1067 2741928 [I (java.base@11.0.9)
2: 9389 689632 [B (java.base@11.0.9)
3: 8938 286016 java.util.HashMap$Node (java.base@11.0.9)
4: 315 249592 [C (java.base@11.0.9)
5: 7634 183216 java.lang.String (java.base@11.0.9)
6: 890 169400 [Ljava.util.HashMap$Node; (java.base@11.0.9)
7: 2573 137248 [Ljava.lang.Object; (java.base@11.0.9)
8: 1055 129008 java.lang.Class (java.base@11.0.9)
9: 1148 45920 java.util.LinkedHashMap$Entry (java.base@11.0.9)
10: 1309 41888 java.util.concurrent.ConcurrentHashMap$Node (java.base@11.0.9)
jmap -dump:live,format=b,file=heap.dump 12368
命令執(zhí)行 內(nèi)存信息dump到heap.dump 文件中提揍。JVM會(huì)將整個(gè)heap的信息dump寫入到一個(gè)文件啤月,heap如果比較大的話,就會(huì)導(dǎo)致這個(gè)過(guò)程比較耗時(shí)劳跃,并且執(zhí)行的過(guò)程中為了保證dump的信息是可靠的顽冶,所以會(huì)暫停應(yīng)用。
>jmap -dump:live,format=b,file=heap.dump 12368
Heap dump file created
導(dǎo)出的dump可通過(guò)jvisualvm.exe 分析
jconsole
jvisualvm
JVM常用調(diào)優(yōu)配置解析
Xms Xmx Xmn Xss
-Xms 堆內(nèi)存的初始大小售碳,默認(rèn)為物理內(nèi)存的1/64
-Xmx 堆內(nèi)存的最大大小强重,默認(rèn)為物理內(nèi)存的1/4
-Xmn 堆內(nèi)新生代的大小绞呈。通過(guò)這個(gè)值也可以得到老生代的大小:-Xmx減去-Xmn
-Xss 設(shè)置每個(gè)線程可使用的內(nèi)存大小间景,即棧的大小佃声。在相同物理內(nèi)存下,減小這個(gè)值能生成更多的線程倘要,當(dāng)然操作系統(tǒng)對(duì)一個(gè)進(jìn)程內(nèi)的線程數(shù)還是有限制的圾亏,不能無(wú)限生成。線程棧的大小是個(gè)雙刃劍封拧,如果設(shè)置過(guò)小志鹃,可能會(huì)出現(xiàn)棧溢出,特別是在該線程內(nèi)有遞歸泽西、大的循環(huán)時(shí)出現(xiàn)溢出的可能性更大曹铃,如果該值設(shè)置過(guò)大,就有影響到創(chuàng)建棧的數(shù)量捧杉,如果是多線程的應(yīng)用陕见,就會(huì)出現(xiàn)內(nèi)存溢出的錯(cuò)誤。
堆設(shè)置
-Xms:初始堆大小
-Xmx:最大堆大小
-Xmn:新生代大小
-XX:NewRatio:設(shè)置新生代和老年代的比值味抖。如:為3评甜,表示年輕代與老年代比值為1:3
-XX:SurvivorRatio:新生代中Eden區(qū)與兩個(gè)Survivor區(qū)的比值。注意Survivor區(qū)有兩個(gè)仔涩。如:為3忍坷,表示Eden:Survivor=3:2,一個(gè)Survivor區(qū)占整個(gè)新生代的1/5
-XX:MaxTenuringThreshold:設(shè)置轉(zhuǎn)入老年代的存活次數(shù)熔脂。如果是0承匣,則直接跳過(guò)新生代進(jìn)入老年代
-XX:PermSize、-XX:MaxPermSize:分別設(shè)置永久代最小大小與最大大写盖摹(Java8以前)
-XX:MetaspaceSize韧骗、-XX:MaxMetaspaceSize:分別設(shè)置元空間最小大小與最大大小(Java8以后)
收集器設(shè)置
-XX:+UseSerialGC:設(shè)置串行收集器
-XX:+UseParallelGC:設(shè)置并行收集器
-XX:+UseParalledlOldGC:設(shè)置并行老年代收集器
-XX:+UseConcMarkSweepGC:設(shè)置并發(fā)收集器
垃圾回收統(tǒng)計(jì)信息
-XX:+PrintGC
-XX:+PrintGCDetails
-XX:+PrintGCTimeStamps
-Xloggc:filename
并行收集器設(shè)置
-XX:ParallelGCThreads=n:設(shè)置并行收集器收集時(shí)使用的CPU數(shù)零聚。并行收集線程數(shù)袍暴。
-XX:MaxGCPauseMillis=n:設(shè)置并行收集最大暫停時(shí)間
-XX:GCTimeRatio=n:設(shè)置垃圾回收時(shí)間占程序運(yùn)行時(shí)間的百分比。公式為1/(1+n)
并發(fā)收集器設(shè)置
-XX:+CMSIncrementalMode:設(shè)置為增量模式隶症。適用于單CPU情況政模。
-XX:ParallelGCThreads=n:設(shè)置并發(fā)收集器新生代收集方式為并行收集時(shí),使用的CPU數(shù)蚂会。并行收集線程數(shù)淋样。
idea中運(yùn)行程序時(shí)設(shè)置VM options
-Xms512M -Xmx512M -Xmn256M -Xss2M -XX:PermSize=128M