Java的JVM垃圾回收(CMS和G1)

垃圾回收算法



分代整理
新生代
新生代的对象基本上朝生夕死.
老年代
老年代的对象存活时间会比较久,只要清理就需要fullgc

CMS收集器
全称是(Concurrent Mark Sweep)收集器 ,所以是基于标记清理. 最短回收停顿时间为目标的收集器.

为了实现以上目的,那么需要尽可能的缩短停顿时间, 总共是两个阶段,标记阶段和清理阶段.

  1. 缩短标记阶段的停顿时间.
    1. 初始标记(CMS initial mark):独占CPU,stop-the-world, 仅标记GCroots能直接关联的对象,速度比较快.
    2. 并发标记(CMS concurrent mark):可以和用户线程并发执行,通过GCRoots Tracing 标记所有可达对象
    3. 重新标记(CMS remark):独占CPU,stop-the-world, 对并发标记阶段用户线程运行产生的垃圾对象进行标记修正,以及更新逃逸对象

 

  1. 清理阶段
    1. 并发清理(CMS concurrent sweep):可以和用户线程并发执行,清理在重复标记中被标记为可回收的对象

 

优点

  1. 并发.
  2. 低延迟


缺点

  1. 标记清理算法的缺点,会有内存碎片.
  2. CPU资源紧张时,会导致延迟卡顿严重.


适合什么场景?

  1. 高并发, 响应时间优先,能接受牺牲一定的吞吐量.
  2. 硬件敏感,那需要硬件配置比较高的情况.


G1算法
实现高吞吐、没有内存碎片、收集时间可控等功能

打破了原有的分代处理的情况, 把整个堆分为多个大小相等的独立区域

Region
传统的GC收集器将连续的内存空间划分为新生代、老年代和永久代(JDK 8去除了永久代,引入了元空间Metaspace),这种划分的特点是各代的存储地址(逻辑地址,下同)是连续的。如下图所示:



传统GC内存布局
而G1的各代存储地址是不连续的,每一代都使用了n个不连续的大小相同的Region,每个Region占有一块连续的虚拟内存地址。如下图所示:




g1 GC内存布局
region标明了H,它代表Humongous,这表示这些Region存储的是巨大对象(humongous object,H-obj),即大小大于等于region一半的对象。H-obj有如下几个特征: * H-obj直接分配到了old gen,防止了反复拷贝移动。 * H-obj在global concurrent marking阶段的cleanup 和 full GC阶段回收。 * 在分配H-obj之前先检查是否超过 initiating heap occupancy percent和the marking threshold, 如果超过的话,就启动global concurrent marking,为的是提早回收,防止 evacuation failures 和 full GC。

SATB
全称是Snapshot-At-The-Beginning,由字面理解,是GC开始时活着的对象的一个快照。它是通过Root Tracing得到的,作用是维持并发GC的正确性。 那么它是怎么维持并发GC的正确性的呢?根据三色标记算法,我们知道对象存在三种状态:

  • 白:对象没有被标记到,标记阶段结束后,会被当做垃圾回收掉。
  • 灰:对象被标记了,但是它的field还没有被标记或标记完。
  • 黑:对象被标记了,且它的所有field也被标记完了。


RSet
全称是Remembered Set,是辅助GC过程的一种结构,典型的空间换时间工具,和Card Table有些类似。还有一种数据结构也是辅助GC的:Collection Set(CSet),它记录了GC要收集的Region集合,集合里的Region可以是任意年代的。在GC的时候,对于old->young和old->old的跨代对象引用,只要扫描对应的CSet中的RSet即可。 逻辑上说每个Region都有一个RSet,RSet记录了其他Region中的对象引用本Region中对象的关系,属于points-into结构(谁引用了我的对象)。而Card Table则是一种points-out(我引用了谁的对象)的结构,每个Card 覆盖一定范围的Heap(一般为512Bytes)。G1的RSet是在Card Table的基础上实现的:每个Region会记录下别的Region有指向自己的指针,并标记这些指针分别在哪些Card的范围内。 这个RSet其实是一个Hash Table,Key是别的Region的起始地址,Value是一个集合,里面的元素是Card Table的Index。
下图表示了RSet、Card和Region的关系(出处):




G1日志的配置和查看
通过 G1 GC Log 重新认识 G1 垃圾回收器 - 墨天轮

-Xloggc:D:/gc.log -XX:+PrintGCDetails -XX:MaxGCPauseMillis=200m



[0.020s][info][gc,heap] Heap region size: 1M
[0.027s][info][gc ] Using G1
[0.027s][info][gc,heap,coops] Heap address: 0x000000070a200000, size: 3934 MB, Compressed Oops mode: Zero based, Oop shift amount: 3
[0.188s][info][gc,start ] GC(0) Pause Young (Concurrent Start) (G1 Humongous Allocation)
[0.188s][info][gc,task ] GC(0) Using 5 workers of 13 for evacuation
[0.190s][info][gc,phases ] GC(0) Pre Evacuate Collection Set: 0.0ms
[0.190s][info][gc,phases ] GC(0) Evacuate Collection Set: 1.3ms
[0.190s][info][gc,phases ] GC(0) Post Evacuate Collection Set: 0.1ms
[0.190s][info][gc,phases ] GC(0) Other: 0.6ms
[0.190s][info][gc,heap ] GC(0) Eden regions: 4->0(145)
[0.190s][info][gc,heap ] GC(0) Survivor regions: 0->2(15)
[0.191s][info][gc,heap ] GC(0) Old regions: 0->0
[0.191s][info][gc,heap ] GC(0) Humongous regions: 0->0
[0.191s][info][gc,metaspace ] GC(0) Metaspace: 6437K->6437K(1056768K)
[0.191s][info][gc ] GC(0) Pause Young (Concurrent Start) (G1 Humongous Allocation) 4M->1M(246M) 2.609ms
[0.191s][info][gc,cpu ] GC(0) User=0.00s Sys=0.00s Real=0.00s
[0.191s][info][gc ] GC(1) Concurrent Cycle
[0.191s][info][gc,marking ] GC(1) Concurrent Clear Claimed Marks
[0.191s][info][gc,marking ] GC(1) Concurrent Clear Claimed Marks 0.026ms
[0.191s][info][gc,marking ] GC(1) Concurrent Scan Root Regions
[0.193s][info][gc,marking ] GC(1) Concurrent Scan Root Regions 1.870ms
[0.193s][info][gc,marking ] GC(1) Concurrent Mark (0.193s)
[0.193s][info][gc,marking ] GC(1) Concurrent Mark From Roots
[0.193s][info][gc,task ] GC(1) Using 3 workers of 3 for marking
[0.193s][info][gc,marking ] GC(1) Concurrent Mark From Roots 0.279ms
[0.193s][info][gc,marking ] GC(1) Concurrent Preclean
[0.193s][info][gc,marking ] GC(1) Concurrent Preclean 0.067ms
[0.193s][info][gc,marking ] GC(1) Concurrent Mark (0.193s, 0.193s) 0.392ms
[0.519s][info][gc,start ] GC(1) Pause Remark

总结

posted @ 2022-09-02 17:50  小鹏713  阅读(389)  评论(0编辑  收藏  举报