CMS垃圾回收器

2020-12-24  本文已影响0人  得力小泡泡

枚举根结点

当执行系统停顿下来后,并不需要一个不漏地检查完所有执行上下文和全局的引用位置,虚拟机应当是有办法直接得知哪些地方存放着对象引用。在HotSpot的实现中,是使用一组称为OopMap的数据结构来达到这个目的的

安全点

image.png

安全区域

实际执行时:

CMS收集器

CMS收集器的动作步骤

如下图所示,在整个过程中耗时最长的并发标记和并发清除过程收集器线程都可以与用户线程一起工作,因此,从总体上看,CMS收集器的内存回收过程是与用户线程一起并发执行的:


image.png

解释:

CMS收集器收集完整步骤

Phase1 :Initial Mark【初始标记】
Phase2 : Concurrent Mark 【并发标记】
Phase3 : Concurrent Preclean【并发预先清除】
Phase4 : Concurrent Abortable Preclean【并发可能失败的预先清除】
Phase5 : Final Remark【最终重新标记】
Phase6 : Concurrent Sweep【并发清除】
Phase7 : Concurrent Reset【并发重置】

(前5个是标记阶段细的五个子阶段)

CMS垃圾收集器的优缺点

优点:并发收集、低停顿【注意:这里的停顿指的是停止用户线程】,Oracle公司的一些官方文档中也称之为并发低停顿收集器(Concurrent Low Pause Collector)。

缺点:
1、CMS收集器对CPU资源非常敏感。会因为占用了一部分线程而导致应用程序变慢,总吞吐量降低
2、CMS收集器无法处理浮动垃圾,浮动垃圾简述是该对象本来不是垃圾,但在判断完后且清除之前,该对象却变成了垃圾对象,然而该对象却不能被回收掉,只能等下一次的GC
(就是指在之前判断该对象不是垃圾,由于用户线程同时也是在运行过程中的,所以会导致判断不准确的, 可能在判断完成之后在清除之前这个对像已经变成了垃圾对象,所以有可能本该此垃圾被回收但是没有被回收,只能等待下一次GC再将该对象回收,所以这种对像就是浮动垃圾)
,可能出现“Concurrent Mode Failure”失败而导致另一次Full GC的产生。如果在应用中老年代增长不是太快,可能适当调高参数-XX:CMSInitiatingOccupancyFraction的值来提高触发百分比,以便降低内存回收次数从而获取更好的性能。要是CMS运行期间预留的内存无法满足程序需要时,虚拟机将启动后备预案:临时启用Serial Old收集器来重新进行老年代的垃圾收集,这样停顿时间就很长了。所以说参数-XX:CMSInitiatingOccupancyFraction设置得太高很容易导致大量“Concurrent Mode Failure”失败,性能反而降低。
3、收集结束时会有大量空间碎片产生,空间碎片过多时,将会给大对象分配带来很大麻烦,往往出现老年代还有很大空间剩余,但是无法找到足够大的连续空间来分配当前对象,不得不提前进行一次Full GC。CMS收集器提供了一个-XX:+UseCMSCompactAtFullCollection开关参数(默认就是开启的),用于在CMS收集器顶不住要进行Full GC时开启内存碎片的合并整理过程,内存整理的过程是无法并发的,空间碎片问题没有了,但停顿时间不得不变长。

空间分配担保:

在发生Minor GC之前,虚拟机会先检查老年代最大可用的连续空间是否大于新生代所有对象总空间,如果这个条件成立,那么Minor GC可以确保是安全的。当大量对象在Minor GC后仍然存活,就需要老年代进行空间分配担保,把Survivor无法容纳的对象直接进入老年代。如果老年代判断到剩余空间不足(根据以往每一次回收晋升到老年代对象空间的平均值作为经验值),则进行一次Full GC。

问题:有人会觉得既然Mark Sweep会造成内存碎片,那么为什么不把算法换成Mark Compart呢?

由于在CMS垃圾回收过程中,并发清除线程和用户线程是并发执行的,如果把并发清除变成并发整理,会导致用户线程使用的对象地址发生改变,会使得用户线程不能正常执行。

用实践验证

当老年代使用CMS垃圾收集器时,新生代默认使用ParNew垃圾收集器

vm参数

-verbose:gc
-Xms20M
-Xmx20M
-Xmn10M
-XX:+PrintGCDetails
-XX:SurvivorRatio=8
-XX:+UseConcMarkSweepGC
package com.gc;

public class MyTest1 {

    public static void main(String[] args) {
        int size = 1024 * 1024;

        byte[] myAlloc1 = new byte[4 * size];
        System.out.println("1111111");

        byte[] myAlloc2 = new byte[4 * size];
        System.out.println("22222222");

        byte[] myAlloc3 = new byte[2 * size];
        System.out.println("3333333");

        byte[] myAlloc4 = new byte[4 * size];
        System.out.println("4444444");
    }
}
1111111
[GC (Allocation Failure) [ParNew: 6445K->835K(9216K), 0.0035794 secs] 6445K->4933K(19456K), 0.0046871 secs] [Times: user=0.00 sys=0.00, real=0.00 secs] 
22222222
3333333
[GC (Allocation Failure) [ParNew (promotion failed): 7136K->6601K(9216K), 0.0035939 secs][CMS: 8646K->8634K(10240K), 0.0070299 secs] 11234K->11029K(19456K), [Metaspace: 3458K->3458K(1056768K)], 0.0110103 secs] [Times: user=0.02 sys=0.00, real=0.01 secs] 
[GC (CMS Initial Mark) [1 CMS-initial-mark: 8634K(10240K)] 15125K(19456K), 0.0005599 secs] [Times: user=0.00 sys=0.00, real=0.00 secs] 
[CMS-concurrent-mark-start]
4444444
Heap
 par new generation   total 9216K, used 6977K[CMS-concurrent-mark: 0.001/0.001 secs] [Times: user=0.00 sys=0.00, real=0.00 secs] 
[CMS-concurrent-preclean-start]
 [0x00000000fec00000, 0x00000000ff600000, 0x00000000ff600000)
  eden space 8192K,  85% used [0x00000000fec00000, 0x00000000ff2d0598, 0x00000000ff400000)
  from space 1024K,   0% used [0x00000000ff400000, 0x00000000ff400000, 0x00000000ff500000)
[CMS-concurrent-preclean: 0.001/0.001 secs] [Times: user=0.00 sys=0.00, real=0.00 secs] 
[CMS-concurrent-abortable-preclean-start]
[CMS-concurrent-abortable-preclean: 0.000/0.000 secs] [Times: user=0.00 sys=0.00, real=0.00 secs] 
  to   space 1024K,   0% used [0x00000000ff500000, 0x00000000ff500000, 0x00000000ff600000)
 concurrent mark-sweep generation total 10240K, used 8634K [0x00000000ff600000, 0x0000000100000000, 0x0000000100000000)
 Metaspace       used 3464K, capacity 4496K, committed 4864K, reserved 1056768K
  class space    used 378K, capacity 388K, committed 512K, reserved 1048576K

详细版看
https://www.cnblogs.com/webor2006/p/11110263.html

上一篇 下一篇

猜你喜欢

热点阅读