首页 > 其他分享 >G1 垃圾收集器介绍?️讲得很粗需要细嚼

G1 垃圾收集器介绍?️讲得很粗需要细嚼

时间:2023-11-13 10:01:08浏览次数:23  
标签:Pause heap G1 收集器 细嚼 regions GC ms gc

本文讲那些东西?

  1. 堆布局(以 Region 为基础划分:新生代(Eden 区、Survivor 区)、年老代、Humongous 区域)
  2. 垃圾收集周期
  3. GC 运作过程:初始标记、并发标记、最终标记、筛选回收
  4. GC 类型:Minor GC、Full GC 、Mixed GC
  5. CSet (年轻代需要手机的 Region 集合就是 CSet)
  6. 跨代引用
  7. 停顿预测模型
  8. GC 日志分析

G1 内存堆布局

G1 的英文全称是 Garbagge First,是一个有分代,按照 Region 的方式进行内存布局的垃圾收集器。

G1 垃圾收集器介绍?️讲得很粗需要细嚼_垃圾收集

在上图中,我们注意到还有一些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。

GC 类型

  1. Young GC,垃圾收集范围:年轻代区域 + 大对象区
  2. Mixed GC,垃圾收集范围:年轻代区域 + 老年区 + 大对象区
  3. Full GC,垃圾收集范围:年轻代区域 + 老年区 + 大对象区 + 元空间

Collection Set

Collection Set 就是我们垃圾收集器的一个区域,在不同的垃圾回收阶段,会有不同的区域。

  • Young GC, 垃圾收集区域包括:年轻代区域 + 大对象区
  • Mixed GC, 垃圾收集区域包括:年轻代区域 + 老年区 + 大对象区

跨代引用

Young GC 主要是清理,新生代中的对象,我们知道整个堆空间包括老年代,新生代,我们在 Young GC 过程中会去找 GCRoots 然后判断对象是是否可达, 如果不可达,如果可达就标记。如果对于老年代中引用新生代的对象,我们如果要找出来就就需要对老年代进行全扫描,这样是不太现实的。所以G1 通过记忆集的形势记录了老年代对新生代的引用。具体在G1中通过 CarTable 来实现记忆集。

G1 垃圾收集器介绍?️讲得很粗需要细嚼_Real_02

RSet(记忆集)

记录了其它Region中的对象到Region的引用。RSet的价值在于使得垃圾回收不需要扫描整个堆,能够快速定位到真正引用它的堆对象地址。ReSet本身就是一个Hash表,存储在新生代的每个Region中。但是存储需要消耗空间,多的能达到百分之20。因此G1对内存的空间要求较高(小空间没资本玩),空间越大性能越彪悍。

CardTable

由于新生代GC时,需要扫描整个old区,效率非常低。所以old区就是用卡表的方式进行一次逻辑分区。一般一页卡表的大小是2的n次幂。每一个区域也是用Key,Value结构进行记录。每一区域记录为Key不重复,Value则记录这片区域的老年代对象与新生代对象是否存在引用关系,存在则标记为1,否则为0。记录完毕后把value为1的key作为ReSet的key进行记录,并且ReSet的value存储引用,从而提高跨代引用的查询效率。

停顿预测模型

所有的预测都是基于历史的拟合,HotSpot使用了基于方差与标准差的技术。参考:sdww2348115.github.io/jvm/g1/Paus…

G1 垃圾收集周期

G1 垃圾收集器介绍?️讲得很粗需要细嚼_后端_03

G1 有两个阶段,它会在这两个阶段往返,分别是 Young-only,Space Reclamation.

  1. Young-only 包含一系列的超过,如果长期存活的对象会逐渐转移到 Old gen
  2. Space Reclamation G1 会递进地回收 Old gen 的空间,同时也处理 Young region

图是来自 Oracle 上对 GC 周期的描述,实心圆都表示一次 GC 停顿

  • 蓝色 Young-only
  • 黄色 标记过程的停顿
  • 红色 Mixed GC 停顿

在几次 GC 后,Old gen 的对象占有比超过了 InitiatingHeapOccupancyPercent (简称为IHOP,默认值为45,这个值是启动并发标记的阈值,当老年代使用内存占用堆内存的45%启动并发标记。 # 如果该过大,可能会导致mixed gc跟不上内存分配的速度从而导致full gc),gc 就会进入并发标记准备 (Concurrent Mark)。

  • G1 在每一次 Young 回收中都会查找活对象 (有引用的对象)
  • G1 在 old region 并发查找存活对象
  • 叫 Concurrent Marking
  • 可能花费很长时间
  • 不会停止 Java 应用
  • G1 没有活对象的引用信息是不能进行垃圾回收的
  • Mixed GC 依赖 Concurrent Mark

回到 Full GC,从上面简单分析得出,Full GC 发生是没有足够的 free region,如果堆是足够大的,Mixed gc 没有回收足够的 old region,或者 concurrent mark 没法及时完成,都可能会导致 full gc。

GC 日志分析

下面是网上找的一个 GC 日志案例,解析如下(配合 G1 垃圾收集周期结合来看):

[gc,start      ] GC(44265) Pause Young (Normal) (G1 Evacuation Pause)
[gc,task       ] GC(44265) Using 13 workers of 13 for evacuation
[gc,phases     ] GC(44265)   Pre Evacuate Collection Set: 0.1ms
[gc,phases     ] GC(44265)   Evacuate Collection Set: 101.8ms
[gc,phases     ] GC(44265)   Post Evacuate Collection Set: 3.2ms
[gc,phases     ] GC(44265)   Other: 2.7ms
[gc,heap       ] GC(44265) Eden regions: 1850->0(1851)
[gc,heap       ] GC(44265) Survivor regions: 70->69(240)
[gc,heap       ] GC(44265) Old regions: 766->768
[gc,heap       ] GC(44265) Humongous regions: 20->19
[gc,metaspace  ] GC(44265) Metaspace: 193280K->193280K(1230848K)
[gc            ] GC(44265) Pause Young (Normal) (G1 Evacuation Pause) 21642M->6843M(25600M) 107.561ms
[gc,cpu        ] GC(44265) User=1.31s Sys=0.00s Real=0.11s

[gc,start      ] GC(44266) Pause Young (Normal) (G1 Evacuation Pause)
[gc,task       ] GC(44266) Using 13 workers of 13 for evacuation
[gc,phases     ] GC(44266)   Pre Evacuate Collection Set: 0.1ms
[gc,phases     ] GC(44266)   Evacuate Collection Set: 99.8ms
[gc,phases     ] GC(44266)   Post Evacuate Collection Set: 3.3ms
[gc,phases     ] GC(44266)   Other: 2.7ms
[gc,heap       ] GC(44266) Eden regions: 1851->0(1854)
[gc,heap       ] GC(44266) Survivor regions: 69->66(240)
[gc,heap       ] GC(44266) Old regions: 768->772
[gc,heap       ] GC(44266) Humongous regions: 20->19
[gc,metaspace  ] GC(44266) Metaspace: 193280K->193280K(1230848K)
[gc            ] GC(44266) Pause Young (Normal) (G1 Evacuation Pause) 21659M->6848M(25600M) 105.713ms
[gc,cpu        ] GC(44266) User=1.29s Sys=0.01s Real=0.10s

[gc,start      ] GC(44267) Pause Young (Normal) (G1 Evacuation Pause)
[gc,task       ] GC(44267) Using 13 workers of 13 for evacuation
[gc,phases     ] GC(44267)   Pre Evacuate Collection Set: 0.1ms  //初始标记,查找 gc root 
[gc,phases     ] GC(44267)   Evacuate Collection Set: 89.8ms     //并发标记
[gc,phases     ] GC(44267)   Post Evacuate Collection Set: 3.5ms //清理工作
[gc,phases     ] GC(44267)   Other: 2.7ms
[gc,heap       ] GC(44267) Eden regions: 1854->0(1856)
[gc,heap       ] GC(44267) Survivor regions: 66->64(240)
[gc,heap       ] GC(44267) Old regions: 772->775
[gc,heap       ] GC(44267) Humongous regions: 20->19
[gc,metaspace  ] GC(44267) Metaspace: 193280K->193280K(1230848K)
[gc            ] GC(44267) Pause Young (Normal) (G1 Evacuation Pause) 21688M->6859M(25600M) 95.891ms
[gc,cpu        ] GC(44267) User=1.16s Sys=0.00s Real=0.10s

[gc,start      ] GC(44268) Pause Young (Normal) (G1 Evacuation Pause)                 // Young GC
[gc,task       ] GC(44268) Using 13 workers of 13 for evacuation
[gc,phases     ] GC(44268)   Pre Evacuate Collection Set: 0.1ms
[gc,phases     ] GC(44268)   Evacuate Collection Set: 100.5ms
[gc,phases     ] GC(44268)   Post Evacuate Collection Set: 3.8ms
[gc,phases     ] GC(44268)   Other: 2.8ms
[gc,heap       ] GC(44268) Eden regions: 1856->0(1855)
[gc,heap       ] GC(44268) Survivor regions: 64->65(240)
[gc,heap       ] GC(44268) Old regions: 775->777
[gc,heap       ] GC(44268) Humongous regions: 20->19
[gc,metaspace  ] GC(44268) Metaspace: 193280K->193280K(1230848K)
[gc            ] GC(44268) Pause Young (Normal) (G1 Evacuation Pause) 21715M->6876M(25600M) 107.037ms
[gc,cpu        ] GC(44268) User=1.30s Sys=0.00s Real=0.11s

[gc,start      ] GC(44269) Pause Young (Concurrent Start) (G1 Humongous Allocation)  // 并发阶段
[gc,task       ] GC(44269) Using 13 workers of 13 for evacuation
[gc,phases     ] GC(44269)   Pre Evacuate Collection Set: 0.6ms
[gc,phases     ] GC(44269)   Evacuate Collection Set: 90.9ms
[gc,phases     ] GC(44269)   Post Evacuate Collection Set: 3.2ms
[gc,phases     ] GC(44269)   Other: 2.9ms
[gc,heap       ] GC(44269) Eden regions: 1519->0(1855)
[gc,heap       ] GC(44269) Survivor regions: 65->65(240)
[gc,heap       ] GC(44269) Old regions: 777->777
[gc,heap       ] GC(44269) Humongous regions: 19->19
[gc,metaspace  ] GC(44269) Metaspace: 193280K->193280K(1230848K)
[gc            ] GC(44269) Pause Young (Concurrent Start) (G1 Humongous Allocation) 19024M->6883M(25600M) 97.391ms
[gc,cpu        ] GC(44269) User=1.16s Sys=0.01s Real=0.10s

[gc            ] GC(44270) Concurrent Cycle                                          // 完成 clearup
[gc,marking    ] GC(44270) Concurrent Clear Claimed Marks
[gc,marking    ] GC(44270) Concurrent Clear Claimed Marks 0.562ms
[gc,marking    ] GC(44270) Concurrent Scan Root Regions
[gc,marking    ] GC(44270) Concurrent Scan Root Regions 719.931ms
[gc,marking    ] GC(44270) Concurrent Mark (280799.914s)
[gc,marking    ] GC(44270) Concurrent Mark From Roots
[gc,task       ] GC(44270) Using 3 workers of 3 for marking
[gc,marking    ] GC(44270) Concurrent Mark From Roots 2268.905ms
[gc,marking    ] GC(44270) Concurrent Preclean
[gc,marking    ] GC(44270) Concurrent Preclean 3.078ms
[gc,marking    ] GC(44270) Concurrent Mark (280799.914s, 280802.186s) 2272.068ms
[gc,start      ] GC(44270) Pause Remark
[gc,stringtable] GC(44270) Cleaned string and symbol table, strings: 87967 processed, 92 removed, symbols: 442773 processed, 13 removed
[gc            ] GC(44270) Pause Remark 13740M->13740M(25600M) 32.599ms
[gc,cpu        ] GC(44270) User=0.29s Sys=0.00s Real=0.04s
[gc,marking    ] GC(44270) Concurrent Rebuild Remembered Sets            //重构记忆集
[gc,marking    ] GC(44270) Concurrent Rebuild Remembered Sets 1906.792ms
[gc,start      ] GC(44270) Pause Cleanup
[gc            ] GC(44270) Pause Cleanup 18019M->18019M(25600M) 0.782ms
[gc,cpu        ] GC(44270) User=0.00s Sys=0.01s Real=0.00s
[gc,marking    ] GC(44270) Concurrent Cleanup for Next Mark
[gc,marking    ] GC(44270) Concurrent Cleanup for Next Mark 25.530ms
[gc            ] GC(44270) Concurrent Cycle 4963.833ms

[gc,start      ] GC(44271) Pause Young (Prepare Mixed) (G1 Evacuation Pause)  // Space Reclamation 阶段了,多个 Mixed GC 会进行
[gc,task       ] GC(44271) Using 13 workers of 13 for evacuation
[gc,phases     ] GC(44271)   Pre Evacuate Collection Set: 0.1ms
[gc,phases     ] GC(44271)   Evacuate Collection Set: 102.6ms
[gc,phases     ] GC(44271)   Post Evacuate Collection Set: 3.7ms
[gc,phases     ] GC(44271)   Other: 3.9ms
[gc,heap       ] GC(44271) Eden regions: 1855->0(98)
[gc,heap       ] GC(44271) Survivor regions: 65->62(240)
[gc,heap       ] GC(44271) Old regions: 777->778
[gc,heap       ] GC(44271) Humongous regions: 21->19
[gc,metaspace  ] GC(44271) Metaspace: 193271K->193271K(1230848K)
[gc            ] GC(44271) Pause Young (Prepare Mixed) (G1 Evacuation Pause) 21739M->6869M(25600M) 110.034ms
[gc,cpu        ] GC(44271) User=1.32s Sys=0.01s Real=0.10s

[gc,start      ] GC(44272) Pause Young (Mixed) (G1 Evacuation Pause)
[gc,task       ] GC(44272) Using 13 workers of 13 for evacuation
[gc,phases     ] GC(44272)   Pre Evacuate Collection Set: 0.4ms
[gc,phases     ] GC(44272)   Evacuate Collection Set: 150.8ms
[gc,phases     ] GC(44272)   Post Evacuate Collection Set: 3.2ms
[gc,phases     ] GC(44272)   Other: 2.3ms
[gc,heap       ] GC(44272) Eden regions: 98->0(149)
[gc,heap       ] GC(44272) Survivor regions: 62->11(20)
[gc,heap       ] GC(44272) Old regions: 778->547
[gc,heap       ] GC(44272) Humongous regions: 19->19
[gc,metaspace  ] GC(44272) Metaspace: 193271K->193271K(1230848K)
[gc            ] GC(44272) Pause Young (Mixed) (G1 Evacuation Pause) 7653M->4605M(25600M) 156.486ms
[gc,cpu        ] GC(44272) User=1.95s Sys=0.01s Real=0.15s
[gc,start      ] GC(44273) Pause Young (Mixed) (G1 Evacuation Pause)
[gc,task       ] GC(44273) Using 13 workers of 13 for evacuation
[gc,phases     ] GC(44273)   Pre Evacuate Collection Set: 0.2ms
[gc,phases     ] GC(44273)   Evacuate Collection Set: 122.9ms
[gc,phases     ] GC(44273)   Post Evacuate Collection Set: 2.0ms
[gc,phases     ] GC(44273)   Other: 3.1ms
[gc,heap       ] GC(44273) Eden regions: 149->0(1900)
[gc,heap       ] GC(44273) Survivor regions: 11->20(20)
[gc,heap       ] GC(44273) Old regions: 547->520
[gc,heap       ] GC(44273) Humongous regions: 19->19
[gc,metaspace  ] GC(44273) Metaspace: 193271K->193271K(1230848K)
[gc            ] GC(44273) Pause Young (Mixed) (G1 Evacuation Pause) 5797M->4468M(25600M) 128.036ms
[gc,cpu        ] GC(44273) User=1.57s Sys=0.01s Real=0.12s

上面是连续几次 GC 的日志,可以对照着 GC 周期来看。

  • GC (44265) 是一次普通的 Young GC里面信息有各种 Region 的变化

这里简单说一下 humongous 对象的处理,humongous 对象在 G1 中是被特殊对待的,G1 只决定它们是否生存,回收他们占用的空间,从不会移动它们。

  • Young-Only 阶段,humongous regions 可能会被回收
  • Space-Reclamation,humongous regions 可能会被回收
  • GC (44269) 开始进入并发阶段
  • GC (44270) 完成了 Cleanup,紧接着一个 Prepare Mixed GC (44271) 的垃圾收集,对应周期虚线右边的蓝实心圆
  • GC (44272) 之后就是 Space Reclamation 阶段了,多个 Mixed GC 会进行

JVM 性能监控工具

参考资料

【GC 停顿预测模型】

  1. www.narihiro.info/g1gc-impl-b…
  2. sdww2348115.github.io/jvm/g1/Paus…

【垃圾收集器执行过程】

  1. bugs.openjdk.org/browse/JDK-…

【跨代引用】

【空闲时自动将Java堆内存返回给操作系统】

  1. openjdk.org/jeps/346

【其他】

  1. docs.oracle.com/javacompone…
  2. www.redhat.com/en/blog/par…
  3. cs.williams.edu/~dbarowy/cs…
  4. tech.meituan.com/2016/09/23/…
  5. hllvm-group.iteye.com/group/topic…

标签:Pause,heap,G1,收集器,细嚼,regions,GC,ms,gc
From: https://blog.51cto.com/u_11720620/8337414

相关文章

  • BLOG1110
    推歌:《碧血黄花》——姚敏/沈伦这是个啥啊(难视)这是个纪念黄花岗起义的曲子,但是朗朗上口我就推了。b站有个叫碧血黄花序的视频,是历史向音MAD,技术力高,好看。——————————————————————————————————————————————这几天在家输液挺闲......
  • BLOG1029<-主席树,
    这个比splay好学多了(主席树就是把每次修改的版本保留下来,版本就是线段树曾经的一个状态。如果打暴力的话可以想把每个状态的线段树都保留下来,炸飞了。主席树单点修改的话就是发现了每次修改只改了包含这个点的层,线段树上,这是\(\logn\)级的,我们可以只创建这些新节点。每次修......
  • Acwing127周赛第三题 构造矩阵 (套路)
    题目链接:构造矩阵题目描述我们希望构造一个n×m的整数矩阵。构造出的矩阵需满足:每一行上的所有元素之积均等于k。每一列上的所有元素之积均等于k。保证k为1或−1。请你计算,一共可以构成出多少种不同的满足条件的矩阵。由于结果可能很大,你只需要输出对109+7......
  • BLOG1028
    不是为什么Sonnety每天都要写博客啊。跟了。我其实没啥好写的,不过我可以每天看一下今天干了什么。今天写了疯狂的颜色序列,一个类似HH项链离线做法的东西,第一次在某个版本之内区间查询。然后这个删除上次出现位置的时候也得创建新节点。还有TotheMoon,和那个游戏没关系呢。那个......
  • Java Hotspot G1 GC 原理
    目录原理概念初始堆占用情况标记RememberSet原理CardTableCollectSet停顿预测模型G1的垃圾回收过程对象分配线程本地分配缓冲区Eden区中分配Humongous区分配堆内存结构传统的GC收集器G1收集器G1垃圾收集周期YoungGCYoungGC总结MixedGC全局并发标记初始标记根区域扫描......
  • G1垃圾回收器特性
    G1具备以下几种特性1、并行与并发G1能充利用CPU、多核环境下的硬件优势,使用多个CPU(CPU或者CPU核心)来缩短Stop-The-World停顿时间。G1收集器可以通过并行和并发的方式让应用程序继续执行。2、分代收集虽然G1可以不需要其他收集器配合就能独立管理整个GC堆,但是还是保留了分代的概念。......
  • CF1867C Salyg1n and the MEX Game
    CF1867CSalyg1nandtheMEXGame简单博弈论题。设给出序列的\(\text{mex}\)为\(x\),那么Alice第一次操作时加入\(x\)一定是最优的。此时显然有\(\text{mex(s)}\gex\)。因为如果加入的数\(y<x\),此时数列中有不小于\(2\)个\(y\)。如果Bob删掉了一个数,那么Al......
  • 对于ogg19 mysql 中如果mysql中存在json数据类型,进程会abend问题报错信息 OGG-00774
    对于ogg19mysql是不支持json的这个数据类型还是比较常见的,这个数据类型是在ogg21才开始支持,对于这种报错可以打补丁进行修复Bug29998662:MySQLExtractAbendsWithoutErrorwithJSONdatatypesinbinlog 参考自:MySQLExtractAbendsWithoutErrorWithJSONDataT......
  • 【Vagrant】 Build PG15 on rhel8
    vagrant创建一套singlePG15,同时创建一个新的数据库db_pg15(密同)Vagrant.configure("2")do|config|vms=[#{name:"app01",box:"centos-8",hostname:"app01",ip:"192.168.33.11"},#{name:"gitla......
  • 21207328-吴义隆-blog1
    一、前言:三次pta题目集知识点丰富,包括了一开始如何创建Java基本形式,接着相关的命名及其使用,以及后面的知识结合。并且三次题目集的题量还算中规中矩,一开始,较为基础,题目多一点,方便学生进行学习和理解;接着进阶一点,难度提升的同时,适当减少了习题量;到最后,基本上题目以第二题的课......