ZGC的内存划分

110 阅读3分钟

ZGC的内存划分

ZGC(Z Garbage Collector)的内存划分采用基于Region的动态分区策略,通过将堆内存划分为三类不同大小的Region来优化内存管理和垃圾回收效率。以下是其核心设计要点及工作原理:


⚙️ 一、Region类型与规格

ZGC将堆内存分为三类Region,每种针对不同大小的对象设计,具体规则如下:

Region类型固定容量适用对象大小特点
小型Region2MB< 256KB的小对象可存放多个对象
中型Region32MB256KB ≤ size < 4MB存放中等对象,减少碎片
大型Region动态(≥4MB)≥4MB的大对象独占式分配,每个Region仅存放一个对象

设计意图

  • 小型对象:通过小Region提高内存利用率,减少内部碎片。
  • 中型对象:避免大对象占用过多小Region导致管理开销。
  • 大型对象:独立分配避免拆分,回收后Region可立即重用。

🔍 二、Region的动态特性

1. 创建与销毁

  • 动态扩展:当某种类型的Region不足时,ZGC从操作系统申请新内存并动态创建Region。
  • 即时回收:Region内所有对象被回收后,该Region立即释放给操作系统(通过XX:ZUncommitDelay控制延迟时间)。

2. 容量自适应

  • 大型Region容量按需分配(如8MB对象占用4个2MB单元),但必须为2MB整数倍。
  • 堆总容量在Xms(最小堆)和Xmx(最大堆)间动态调整,避免固定分区导致的浪费。

🧩 三、Region分配策略

  1. 小/中对象分配
    • 优先选择同类型空闲Region,若无则申请新Region。
    • 通过线程本地缓存(类似TLAB但无分代)减少全局锁竞争。
  2. 大对象分配
    • 直接分配专属Large Region,若空间不足触发GC或扩展堆。
  3. NUMA优化
    • 默认启用NUMA感知(XX:+UseNUMA),对象分配在物理靠近CPU的Region,提升内存访问速度。

⚡️ 四、染色指针与内存管理

ZGC通过染色指针(Colored Pointers) 技术将GC状态信息嵌入64位指针的高4位:

标志位作用
Marked0/1标识对象存活状态(用于并发标记)
Remapped表示对象是否被重定位(转移至新Region)
Finalizable标识需通过finalize()访问的对象

关键技术支撑

  1. 内存多重映射(Multi-Mapping) 将同一物理内存映射到三个虚拟地址视图(Marked0、Marked1、Remapped),使染色指针可正常寻址。
  2. 自愈指针(Self-Healing) 应用线程访问旧对象指针时,读屏障自动将其修正为新地址,无需STW更新引用。

🚀 **五、设计优势与性能影响

  1. 即时回收空间 存活对象移出后,Region立即释放(无需等待引用更新),提高内存周转率。
  2. 低碎片化 大对象独占Region+中型Region预分配,显著减少外部碎片。
  3. 停顿时间可控 Region级回收允许并行清理,STW阶段仅处理Root引用(通常<1ms),且与堆大小无关。
  4. 扩展性 染色指针预留18位未使用空间,支持未来记录更多GC状态(如分代标记)。

💎 总结:ZGC Region设计的核心价值

ZGC通过动态三类Region划分 + 染色指针技术,实现了:

  • 亚毫秒级停顿:即使TB级堆,STW时间仍稳定在1ms内。
  • 高内存利用率:即时释放、按需分配,减少碎片和预留空间。
  • 无分代管理:简化设计,避免G1的Remembered Set维护开销。

​生产建议​​:

大堆场景(如>32GB)启用-XX:+UseLargePages提升性能,并通过-Xlog:gc*监控Region分配与回收频率,调整-XX:ConcGCThreads平衡GC与应用线程竞争。