一.jvm的两个Space
1.PermGen space
全称是Permanent Generation space。就是说是永久保存的区域,用于存放Class和Meta信息,Class在被Load的时候被放入该区域。GC(Garbage Collection)应该不会对PermGen space进行清理所以如果你的 APP会LOAD很多CLAsSS的话,就很可能出现PermGen space错误。
对于PermGen space,jvm对应的参数是:
-XX:PermSize=128M
-XX:MaxPermSize=128M
2.Heap space
存放class Instance。
Java Heap分为3个区,Young,Old和Permanent。Young保存刚实例化的对象。当该区被填满时,GC会将对象移到Old区。 Permanent区则负责保存反射对象。
二.jvm的两个GC线程
第一个线程负责回收Heap的Young区。
第二个线 程在Heap不足时,遍历Heap,将Young 区升级为Older区。
三.Heap jvm参数的设置与GC关系
heap容量(-Xms~-Xmx) = Young区容量(-Xmn) + Old区容量 + Permanent区容量,其中Permanent区容量固定,一般为64m,所以Older区的大小等于heap容量(-Xms~-Xmx)减去Young区容量(-Xmn),不能将-Xmn的值设的过大,因为第二个GC线程被迫运行会降低JVM的性能。
如果heap设置太小,GC的频率会很高,会影响系统的性能。增加Heap的大小虽然会降低GC的频率,但也增加了每次GC的时间。并且GC运行时,所有的用户线程将暂停,也就是GC期 间,Java应用程序不做任何工作。所以需要合理进行设置。
优化建议:
建议Server端JVM最好 将-Xms和-Xmx设为相同值。为了优化GC,最好让-Xmn值约等于-Xmx的1/3。一个GUI程序最好是每10到20秒间运行一次GC,每次在半 秒之内完成。
四.jvm一般用到的参数说明
1: heap size
a: -Xmx<n>
指定 jvm 的最大 heap 大小 , 如 :-Xmx=2g
b: -Xms<n>
指定 jvm 的最小 heap 大小 , 如 :-Xms=2g , 高并发应用, 建议和-Xmx一样, 防止因为内存收缩/突然增大带来的性能影响。
c: -Xmn<n>
指定 jvm 中 New Generation 的大小 , 如 :-Xmn256m。 这个参数很影响性能, 如果你的程序需要比较多的临时内存, 建议设置到512M, 如果用的少, 尽量降低这个数值, 一般来说128/256足以使用了。
d: -XX:PermSize=<n>
指定 jvm 中 Perm Generation 的最小值 , 如 :-XX:PermSize=32m。 这个参数需要看你的实际情况,。 可以通过jmap 命令看看到底需要多少。
e: -XX:MaxPermSize=<n>
指定 Perm Generation 的最大值 , 如 :-XX:MaxPermSize=64m
f: -Xss<n>
指定线程桟大小 , 如 :-Xss128k, 一般来说,webx框架下的应用需要256K。 如果你的程序有大规模的递归行为,请考虑设置到512K/1M。 这个需要全面的测试才能知道。 不过,256K已经很大了。 这个参数对性能的影响比较大的。
g: -XX:NewRatio=<n>
指定 jvm 中 Old Generation heap size 与 New Generation 的比例 , 在使用 CMS GC 的情况下此参数失效 , 如 :-XX:NewRatio=2
h: -XX:SurvivorRatio=<n>
指定 New Generation 中 Eden Space 与一个 Survivor Space 的 heap size 比例 ,-XX:SurvivorRatio=8, 那么在总共 New Generation 为 10m 的情况下 ,Eden Space 为 8m
i: -XX:MinHeapFreeRatio=<n>
指定 jvm heap 在使用率小于 n 的情况下 ,heap 进行收缩 ,Xmx==Xms 的情况下无效 , 如 :-XX:MinHeapFreeRatio=30
j: -XX:MaxHeapFreeRatio=<n>
指定 jvm heap 在使用率大于 n 的情况下 ,heap 进行扩张 ,Xmx==Xms 的情况下无效 , 如 :-XX:MaxHeapFreeRatio=70
k: -XX:LargePageSizeInBytes=<n>
指定 Java heap 的分页页面大小 , 如 :-XX:LargePageSizeInBytes=128m
2.jvm参数设置
堆内存分配
JVM初始分配的内存由-Xms指定,默认是物理内存的1/64;JVM最大分配的内存由-Xmx指定,默认是物理内存的1/4.默认空余堆内存小于40%时,JVM就会增大堆直到-Xmx的最大限制;空余堆内存大于70%时, JVM会减少堆直到-Xms的最小限制.因此服务器一般设置-Xms,-Xmx相等以避免在每次GC 后调整堆的大小.
非堆内存分配
JVM使用-XX:PermSize设置非堆内存初始值,默认是物理内存的1/64;由XX:MaxPermSize设置最大非堆内存的大小,默认是物理内存的1/4.
JVM内存限制(最大值)
首先JVM内存首先受限于实际的最大物理内存,假设物理内存无限大的话,JVM内存的最大值跟操作系统有很大的关系.简单的说就32位处理器虽然可控内存空间有4GB,但是具体的操作系统会给一个限制,这个限制一般是 2GB-3GB(一般来说Windows系统下为1.5G-2G,Linux系统下为2G-3G),而64bit以上的处理器就不会有限制了
五.进程与Heap之间的关系
Heap大小并不决定进程的内存使用量。进程的内存使用量要大于-Xmx定义的值,因为Java为其他任务分 配内存,例如每个线程的Stack等。