JVM参数设置-jdk8参数设置JVM参数设置
1.基本参数
参数名称含义默认值
-Xms初始堆⼤⼩内存的
1/64默认(MinHeapFreeRatio参数可以调整)空余堆内存⼩于40%时,JVM就会增⼤堆直到-Xmx的最⼤限制.
-Xmx最⼤堆⼤⼩内存的
1/4默认(MaxHeapFreeRatio参数可以调整)空余堆内存⼤于70%时,JVM会减少堆直到 -Xms的最⼩限制
-Xmn年轻代⼤⼩注意:此处的⼤⼩是(eden+ 2 survivor space).与jmap -heap中显⽰的New gen是不同的。
整个堆⼤⼩=年轻代⼤⼩ + 年⽼代⼤⼩ + 持久代⼤⼩.
增⼤年轻代后,将会减⼩年⽼代⼤⼩.此值对系统性能影响较⼤,Sun官⽅推荐配置为整个堆的3/8
-XX:NewSize设置年轻代⼤⼩-XX:MaxNewSize年轻代最⼤值
-XX:PermSize设置持久代(perm
gen)初始值内存的1/64
-XX:MaxPermSize设置持久代最⼤值内存的
1/4
-Xss每个线程的堆栈⼤
⼩JDK5.0以后每个线程堆栈⼤⼩为1M,以前每个线程堆栈⼤⼩为256K.更具应⽤的线程所需内存⼤⼩进⾏调整.在相同物理内存下,减⼩这个值能⽣成更多的线程.但是操作系统对⼀个进程内的线程数还是有限制的,不能⽆限⽣成,经验值在3000~5000左右
⼀般⼩的应⽤,如果栈不是很深,应该是128k够⽤的⼤的应⽤建议使⽤256k。这个选项对性能影响⽐较⼤,需要严格的测试。(校长)
和threadstacksize选项解释很类似,官⽅⽂档似乎没有解释,在论坛中有这样⼀句话:"”
-
Xss is translated in a VM flag named ThreadStackSize”
⼀般设置这个值就可以了。
-XX:ThreadStackSize Thread Stack Size (0 means use default stack size) [Sparc: 512; Solaris x86: 320 (was 256 prior in 5.0 and earlier); Sparc 64 bit: 1024; Linux amd64: 1024 (was 0 in 5.0 and earlier); all others 0.]
-XX:NewRatio 年轻代(包括Eden和
两个Survivor区)与
年⽼代的⽐值(除去
持久代)
-XX:NewRatio=4表⽰年轻代与年⽼代所占⽐值为
1:4,年轻代占整个堆栈的1/5
Xms=Xmx并且设置了Xmn的情况下,该参数不需
要进⾏设置。
-XX:SurvivorRatio Eden区与Survivor
区的⼤⼩⽐值
设置为8,则两个Survivor区与⼀个Eden区的⽐值为
2:8,⼀个Survivor区占整个年轻代的1/10
-XX:LargePageSizeInBytes 内存页的⼤⼩不可
设置过⼤,会影响
Perm的⼤⼩
=128m
-XX:+UseFastAccessorMethods原始类型的快速优
化
-
XX:+DisableExplicitGC关闭()这个参数需要严格的测试
-XX:+ExplicitGCInvokesConcurrent关闭()disabled Enables invoking of concurrent GC by using () request. This option is disabled by default and can be enabled only together with the -XX:+UseConcMarkSweepGC option.
-
XX:+ExplicitGCInvokesConcurrentAndUnloadsClasses关闭()disabled Enables invoking of concurrent GC by using () request and unloading of classes during the concurrent GC cycle. This option is disabled by default and can be enabled only together with the -XX:+UseConcMarkSweepGC option.
如果设置为0的话,则年轻代对象不经过Survivor区,
-XX:MaxTenuringThreshold垃圾最⼤年龄如果设置为0的话,则年轻代对象不经过Survivor区,直接进⼊年⽼代. 对于年⽼代⽐较多的应⽤,可以提⾼效率.如果将此值设置为⼀个较⼤值,则年轻代对象会在Survivor区进⾏多次复制,这样可以增加对象再年轻代的存活时间,增加在年轻代即被回收的概率该参数只有在串⾏GC时才有效.
-
XX:+AggressiveOpts加快编译
-XX:+UseBiasedLocking锁机制的性能改善-Xnoclassgc禁⽤垃圾回收
-XX:SoftRefLRUPolicyMSPerMB 每兆堆空闲空间中
SoftReference的存
活时间
1s
softly reachable objects will remain alive for some
amount of time after the last time they were
referenced. The default value is one second of
lifetime per free megabyte in the heap
-XX:PretenureSizeThreshold对象超过多⼤是直
接在旧⽣代分配0
单位字节新⽣代采⽤Parallel Scavenge GC时⽆效
另⼀种直接在旧⽣代分配的情况是⼤的数组对象,且
数组中⽆外部引⽤对象.
-XX:TLABWasteTargetPercent TLAB占eden区的百
分⽐
1%
-XX:+CollectGen0First FullGC时是否先
YGC
false
Jdk7版本的主要参数
参数名称含义默认值
-XX:PermSize设置持久代Jdk7版本及以前版本-XX:MaxPermSize设置最⼤持久代Jdk7版本及以前版本Jdk8版本的重要特有参数
参数名称含义默认值
-XX:MetaspaceSize元空间⼤⼩Jdk8版本-XX:MaxMetaspaceSize最⼤元空间Jdk8版本2.并⾏收集器相关参数
参数名称含义默认值
-XX:+UseParallelGC Full GC采⽤parallel MSC
(此项待验证)
选择垃圾收集器为并⾏收集器.此配置仅对年轻代有效.即上述配置下,年轻
代使⽤并发收集,⽽年⽼代仍旧使⽤串⾏收集.(此项待验证)
-XX:+UseParNewGC设置年轻代为并⾏收集可与CMS收集同时使⽤
JDK5.0以上,JVM会根据系统配置⾃⾏设置,所以⽆需再设置此值-XX:ParallelGCThreads并⾏收集器的线程数此值最好配置与处理器数⽬相等同样适⽤于CMS
-XX:+UseParallelOldGC 年⽼代垃圾收集⽅式为并
⾏收集(Parallel
Compacting)
这个是JAVA 6出现的参数选项
-XX:MaxGCPauseMillis每次年轻代垃圾回收的最
长时间(最⼤暂停时间)
如果⽆法满⾜此时间,JVM会⾃动调整年轻代⼤⼩,以满⾜此值.
-
XX:+UseAdaptiveSizePolicy ⾃动选择年轻代区⼤⼩和
相应的Survivor区⽐例
设置此选项后,并⾏收集器会⾃动选择年轻代区⼤⼩和相应的Survivor区⽐
例,以达到⽬标系统规定的最低相应时间或者收集频率等,此值建议使⽤并⾏
收集器时,⼀直打开.
-XX:GCTimeRatio设置垃圾回收时间占程序
运⾏时间的百分⽐
公式为1/(1+n)
-
XX:+ScavengeBeforeFullGC
Full GC前调⽤YGC true Do young generation GC prior to a full GC. (Introduced in 1.4.1.)
3.CMS相关参数
参数名称含义默认值
值
-XX:+UseConcMarkSweepGC使⽤CMS内存收集测试中配置这个以后,-XX:NewRatio=4的配置失效了,原因不明.所
以,此时年轻代⼤⼩最好⽤-Xmn设置.
-XX:+AggressiveHeap 试图是使⽤⼤量的物理内存
长时间⼤内存使⽤的优化,能检查计算资源(内存,处理器数量)
⾄少需要256MB内存
⼤量的CPU/内存,(在1.4.1在4CPU的机器上已经显⽰有提升)
-XX:CMSFullGCsBeforeCompaction多少次后进⾏内存压缩由于并发收集器不对内存空间进⾏压缩,整理,所以运⾏⼀段时间以后会产⽣"碎⽚",使得运⾏效率降低.此值设置运⾏多少次GC以后对内存空间进⾏压缩,整理.
-XX:+CMSParallelRemarkEnabled降低标记停顿
-
XX+UseCMSCompactAtFullCollection在FULL GC的时候,
对年⽼代的压缩CMS是不会移动内存的,因此,这个⾮常容易产⽣碎⽚,导致内存不够⽤,因此,内存的压缩这个时候就会被启⽤。增加这个参数是个好习惯。
可能会影响性能,但是可以消除碎⽚
-XX:+UseCMSInitiatingOccupancyOnly使⽤⼿动定义初始化定
义开始CMS收集
禁⽌hostspot⾃⾏触发CMS GC
-XX:CMSInitiatingOccupancyFraction=70使⽤cms作为垃圾回收
使⽤70%后开始CMS
收集
92为了保证不出现promotion failed(见下⾯介绍)错误,该值的设置需
要满⾜以下公式
-
XX:CMSInitiatingPermOccupancyFraction 设置Perm Gen使⽤到
达多少⽐率时触发
92
-XX:+CMSIncrementalMode设置为增量模式⽤于单CPU情况-XX:+CMSClassUnloadingEnabled
4.辅助信息
参数名称含义默认值
-XX:+PrintGC 输出形式:
[GC 118250K->113543K(130112K), 0.0094143 secs] [Full GC 121376K->10414K(130112K), 0.0650971 secs]
-XX:+PrintGCDetails 输出形式:[GC [DefNew: 8614K->781K(9088K), 0.0123035 secs] 118250K->113543K(130112K), 0.0124633 secs]
[GC [DefNew: 8614K->8614K(9088K), 0.0000665 secs][Tenured: 112761K->10414K(121024K), 0.0433488 secs] 121376K-
>10414K(130112K), 0.0436268 secs]
-XX:+PrintGCTimeStamps
-XX:+PrintGC:PrintGCTimeStamps 可与-XX:+PrintGC -XX:+PrintGCDetails混合使⽤
输出形式:11.851: [GC 98328K->93620K(130112K), 0.0082960 secs]
-XX:+PrintGCApplicationStoppedTime 打印垃圾回收期间程序
暂停的时间.可与上⾯混
合使⽤
输出形式:Total time for which application threads were stopped:
0.0468229 seconds
-
XX:+PrintGCApplicationConcurrentTime 打印每次垃圾回收前,程
序未中断的执⾏时间.可
与上⾯混合使⽤
输出形式:Application time: 0.5291524 seconds
-XX:+PrintHeapAtGC打印GC前后的详细堆栈
信息
-Xloggc:filename 把相关⽇志信息记录到⽂件以便分析.
与上⾯⼏个配合使⽤
-XX:+PrintClassHistogram garbage collects before printing the histogram.
-XX:+PrintTLAB查看TLAB空间的使⽤
情况
XX:+PrintTenuringDistribution查看每次minor GC后新
的存活周期的阈值Desired survivor size 1048576 bytes, new threshold 7 (max 15) new threshold 7即标识新的存活周期的阈值为7。
5.启动参数例⼦
jdk8启动 -server -Xms1366m -Xmx2g -Xmn768m -Xss256k -XX:MetaspaceSize=256m -XX:MaxMetaspaceSize=256M -
XX:SurvivorRatio=8 -XX:MaxTenuringThreshold=5 -XX:GCTimeRatio=19 -Xnoclassgc -XX:+DisableExplicitGC -XX:+UseParNewGC -XX:+UseConcMarkSweepGC -XX:+UseCMSCompactAtFullCollection -XX:CMSFullGCsBeforeCompaction=0 -XX:-CMSParallelRemarkEnabled -XX:CMSInitiatingOccupancyFraction=70 -XX:SoftRefLRUPolicyMSPerMB=0 -XX:+PrintClassHistogram -XX:+PrintGCDetails -XX:+PrintGCDateStamps -XX:+PrintHeapAtGC -Xloggc:/data/logs/api-gc.log
6.GC性能⽅⾯的考虑
GC性能⽅⾯的考虑
对于GC的性能主要有2个⽅⾯的指标:吞吐量throughput(⼯作时间不算gc的时间占总的时间⽐)和暂停pause(gc发⽣时app对外显⽰的⽆法响应)。
1.Total Heap
默认情况下,vm会增加/减少heap⼤⼩以维持free space在整个vm中占的⽐例,这个⽐例由MinHeapFreeRatio和MaxHeapFreeRatio指定。
⼀般⽽⾔,server端的app会有以下规则:
对vm分配尽可能多的memory;
将Xms和Xmx设为⼀样的值。如果虚拟机启动时设置使⽤的内存⽐较⼩,这个时候⼜需要初始化很多对象,虚拟机就必须重复地增加内存。
处理器核数增加,内存也跟着增⼤。
2.The Young Generation
另外⼀个对于app流畅性运⾏影响的因素是young generation的⼤⼩。young generation越⼤,minor coll
ection越少;但是在固定heap size情况下,更⼤的young generation就意味着⼩的tenured generation,就意味着更多的major collection(major collection会引发minor collection)。
NewRatio反映的是young和tenured generation的⼤⼩⽐例。NewSize和MaxNewSize反映的是young generation⼤⼩的下限和上限,将这两个值设为⼀样就固定了young generation的⼤⼩(同Xms和Xmx设为⼀样)。
如果希望,SurvivorRatio也可以优化survivor的⼤⼩,不过这对于性能的影响不是很⼤。SurvivorRatio是eden和survior⼤⼩⽐例。
⼀般⽽⾔,server端的app会有以下规则:
⾸先决定能分配给vm的最⼤的heap size,然后设定最佳的young generation的⼤⼩;
如果heap size固定后,增加young generation的⼤⼩意味着减⼩tenured generation⼤⼩。让tenured generation在任何时候够⼤,能够容纳所有live的data(留10%-20%的空余)。
经验&&规则
1. 年⽼代⼤⼩选择
1. 响应时间优先的应⽤:年⽼代使⽤并发收集器,所以其⼤⼩需要⼩⼼设置,⼀般要考虑并发会话率和会话持续时间等⼀些参数.如果堆
设置⼩了,可以会造成内存碎⽚,⾼回收频率以及应⽤暂停⽽使⽤传统的标记清除⽅式;
如果堆⼤了,则需要较长的收集时间.最优化的⽅案,⼀般需要参考以下数据获得:
并发垃圾收集信息、持久代并发收集次数、传统GC信息、花在年轻代和年⽼代回收上的时间⽐例。
2. 吞吐量优先的应⽤:⼀般吞吐量优先的应⽤都有⼀个很⼤的年轻代和⼀个较⼩的年⽼代.原因是,这样可以尽可能回收掉⼤部分短期
对象,减少中期的对象,⽽年⽼代尽存放长期存活对象.
2. 较⼩堆引起的碎⽚问题
因为年⽼代的并发收集器使⽤标记,清除算法,所以不会对堆进⾏压缩.当收集器回收时,他会把相邻的空间进⾏合并,这样可以分配给较⼤的对象.但是,当堆空间较⼩时,运⾏⼀段时间以后,就会出现"碎⽚",如果并发收集器不到⾜够的空间,那么并发收集器将会停⽌,然后使⽤传统的标记,清除⽅式进⾏回收. 如果出现"碎⽚",可能需要进⾏如下配置:
-XX:+UseCMSCompactAtFullCollection:使⽤并发收集器时,开启对年⽼代的压缩.
-XX:CMSFullGCsBeforeCompaction=0:上⾯配置开启的情况下,这⾥设置多少次Full GC后,对年⽼代进⾏压缩
3. ⽤64位操作系统,Linux下64位的jdk⽐32位jdk要慢⼀些,但是吃得内存更多,吞吐量更⼤
4. XMX和XMS设置⼀样⼤,MaxPermSize和MinPermSize设置⼀样⼤,这样可以减轻伸缩堆⼤⼩带来的压⼒
5. 使⽤CMS的好处是⽤尽量少的新⽣代,经验值是128M-256M,然后⽼⽣代利⽤CMS并⾏收集,这样能保证系统低延迟的吞吐效
率。实际上cms的收集停顿时间⾮常的短,2G的内存,⼤约20-80ms的应⽤程序停顿时间
6. 系统停顿的时候可能是GC的问题也可能是程序的问题,多⽤jmap和jstack查看,或者kill all -3 java,然后查看java控制台⽇志,能看
出很多问题。(相关⼯具的使⽤⽅法将在后⾯的blog中介绍)
7. 仔细了解⾃⼰的应⽤,如果⽤了缓存,那么年⽼代应该⼤⼀些,缓存的HashMap不应该⽆限制长,建议采⽤LRU算法的Map做缓
存,LRUMap的最⼤长度也要根据实际情况设定。
8. 采⽤并发回收时,年轻代⼩⼀点,年⽼代要⼤,因为年⽼⼤⽤的是并发回收,即使时间长点也不会影响其他程序继续运⾏,⽹站不会
停顿
jvm调优参数9. JVM参数的设置(特别是 –Xmx –Xms –Xmn -XX:SurvivorRatio -XX:MaxTenuringThreshold等参数的设置没有⼀个固定的公式,需要
根据PV old区实际数据 YGC次数等多⽅⾯来衡量。为了避免promotion faild可能会导致xmn设置偏⼩,也意味着YGC的次数会增多,处理并发访问的能⼒下降等问题。每个参数的调整都需要经过详细的性能测试,才能到特定应⽤的最佳配置。
promotion failed:
垃圾回收时promotion failed是个很头痛的问题,⼀般可能是两种原因产⽣,
1. 第⼀个原因是救助空间不够,救助空间⾥的对象还不应该被移动到年⽼代,但年轻代⼜有很多对象需要放⼊救助空间;
2. 第⼆个原因是年⽼代没有⾜够的空间接纳来⾃年轻代的对象;这两种情况都会转向Full GC,⽹站停顿时间较长。
解决⽅⽅案⼀:
第⼀个原因我的最终解决办法是去掉救助空间,设置-XX:SurvivorRatio=65536 -XX:MaxTenuringThreshold=0即可,第⼆个原因我的解决办法是设置CMSInitiatingOccupancyFraction为某个值(假设70),这样年⽼代空间到70%时就开始执⾏CMS,年⽼代有⾜够的空间接纳来⾃年轻代的对象。
解决⽅案⼀的改进⽅案:
⼜有改进了,上⾯⽅法不太好,因为没有⽤到救助空间,所以年⽼代容易满,CMS执⾏会⽐较频繁。我改善了⼀下,还是⽤救助空间,但是把救助空间加⼤,这样也不会有promotion failed。具体操作上,32位Linux和64位Linux好像不⼀样,64位系统似乎只要配置MaxTenuringThreshold参数,CMS还是有暂停。为了解决暂停问题和promotion failed问题,最后我设置-XX:SurvivorRatio=1 ,并把MaxTenuringTh
reshold去掉,这样即没有暂停⼜不会有promotoin failed,⽽且更重要的是,年⽼代和永久代上升⾮常慢(因为好多对象到
不了年⽼代就被回收了),所以CMS执⾏频率⾮常低,好⼏个⼩时才执⾏⼀次,这样,服务器都不⽤重启了。
-Xmx4000M -Xms4000M -Xmn600M -XX:PermSize=500M -XX:MaxPermSize=500M -Xss256K -XX:+DisableExplicitGC -
XX:SurvivorRatio=1 -XX:+UseConcMarkSweepGC -XX:+UseParNewGC -XX:+CMSParallelRemarkEnabled -
XX:+UseCMSCompactAtFullCollection -XX:CMSFullGCsBeforeCompaction=0 -XX:+CMSClassUnloadingEnabled -
XX:LargePageSizeInBytes=128M -XX:+UseFastAccessorMethods -XX:+UseCMSInitiatingOccupancyOnly -
XX:CMSInitiatingOccupancyFraction=80 -XX:SoftRefLRUPolicyMSPerMB=0 -XX:+PrintClassHistogram -XX:+PrintGCDetails -
XX:+PrintGCTimeStamps -XX:+PrintHeapAtGC -Xloggc:log/gc.log
CMSInitiatingOccupancyFraction值与Xmn的关系公式
上⾯介绍了promontion faild产⽣的原因是EDEN空间不⾜的情况下将EDEN与From survivor中的存活对象存⼊To survivor区时,To survivor区的空间不⾜,再次晋升到old gen区,⽽old gen区内存也不够的情况下产⽣了promontion faild从⽽导致full gc.那可以推断出:eden+from survivor < old gen区剩余内存时,不会出现promontion faild的情况,即:
(Xmx-Xmn)*(1-CMSInitiatingOccupancyFraction/100)>=(Xmn-Xmn/(SurvivorRatior+2)) 进⽽推断出:
CMSInitiatingOccupancyFraction <=((Xmx-Xmn)-(Xmn-Xmn/(SurvivorRatior+2)))/(Xmx-Xmn)*100
例如:
当xmx=128 xmn=36 SurvivorRatior=1时 CMSInitiatingOccupancyFraction<=((128.0-36)-(36-36/(1+2)))/(128-36)*100 =73.913
当xmx=128 xmn=24 SurvivorRatior=1时 CMSInitiatingOccupancyFraction<=((128.0-24)-(24-24/(1+2)))/(128-24)*100=84.615…
当xmx=3000 xmn=600 SurvivorRatior=1时 CMSInitiatingOccupancyFraction<=((3000.0-600)-(600-600/(1+2)))/(3000-600)*100=83.33 CMSInitiatingOccupancyFraction低于70% 需要调整xmn或SurvivorRatior值。
⽹上⼀童鞋推断出的公式是::(Xmx-Xmn)*(100-CMSInitiatingOccupancyFraction)/100>=Xmn 这个公式个⼈认为不是很严谨,在内存⼩的时候会影响xmn的计算。
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论