khugepaged
后台 THP 折叠线程
只产出 PMD 大页
扫描
一个 PMD 区间 · x86_64
每格 8 页
512 × 4KB = 2MB
折叠
2MB 大页
PMD order
扫描区间
逐个 PTE 查 occupied
统计 occupied 页数
对照 max_ptes_none
整段够格才折叠
不达标整段放弃,保持 4KB
全 PMD 或全不
够格 → 2MB;不够格 → 4KB
同一段 PMD 区间 · x86_64
每格 8 页(32KB)
512 PTE · 2MB
occupied
空洞
占用率撑不起整个 PMD
整段放弃,继续用 4KB 基页
连续 8 格 = 64 页
示例:够 order 6 的 256KB
mTHP 就在 4KB 与 2MB 之间
4KB
基页
mTHP
比 PMD 小、比基页大
2MB
PMD order
前台缺页:按需分配
后台折叠:只认 PMD
这些中等粒度的机会,被整段放弃一起丢掉
前台早已能分配 mTHP,缺的是后台折叠
旧:一次判定,答案只有两端
① 值不值得折 ② 折多大
扫描阶段就一并决定
2MB 或 0
全 PMD 一个答案
两个问题绑在一个整段 yes/no 里
新:先记全,再逐段决定
扫描阶段
只记录 bitmap
mthp_collapse
每个对齐窗口独立判定
逐段 mTHP
按窗口切分,段段独立
折多大
由 offset 对齐定 order 上限
值不值得
由窗口内 occupied 数定去留
≠
启用任意 mTHP order
max_ptes_none 放开到极限
遍历区间内每一个 PTE
PMD 是唯一启用的 order
沿用旧的 max_ptes_none 行为
对已有配置没有任何改变
PTE 区间 · 512 页
bitmap mthp_present_ptes
occupied → 置 1
空洞 → 置 0
整段占用如实记下
扫描不再提前放弃
每个 occupied 页:bitmap 对应位置 1
遍历完 512 个 PTE,整段占用全部在手
扫描阶段不再决定「整段放弃」
同一张 bitmap
扫描写满,mthp_collapse 只读
对齐决定能选多大
offset(页)
__ffs(offset)
最大 order
窗口
0
PMD 对齐
9(PMD)
2MB
4
2
2
16KB
order k 要求窗口起点是 2^k 的倍数
offset 0 对任何 2^k 都对齐,所以能用 PMD order
mthp_collapse 的走法
① 取对齐允许的最高 order
② 数窗口内的 occupied 页数
③ 达标 → 折叠
④ 不达标 → order -1,同段重试
⑤ 成功或最小 order 耗尽 → offset 前移
⑥ 新 offset 重算上限
offset 0:从最高 order 往下试
示例:max_ptes_none = 0;order 6/7/8 仅为示例
order 9
2MB
不达标
order 8
1MB
不达标
order 7
512KB
不达标
order 6
256KB
折叠 256KB
每失败一次:order -1、窗口减半、起点不动
成功或最小 order 耗尽后 offset 前移;下一段上限由新 offset 的 __ffs 重算
creep:折叠给自己造下一次机会
折叠成功
零散页聚成大页
空洞被填实
同一段 occupied 升高
更易达标更大 order
mTHP 被反复提拔
正反馈:越折越容易折
折叠自己制造了下一轮折叠的理由
闸 1 · max_ptes_none
只接受 0 或上限值(按 order 缩放)
collapse_max_ptes_none 落到每个 order
闸 2 · 跳过脏段
含换出页或共享页的段直接跳过
折叠会引入新空洞,是 creep 的温床
范围 · 仅匿名的后台折叠
madv_collapse 与文件、shmem 路径仍只走 PMD
作者未提供性能数据
以下收益均由代码逻辑推断,不含实测数字
Nico Pache · v19
作者自述的验证范围
x86_64 · aarch64 · ppc64le · s390x 多架构构建并测试
kernel-tests · selftests/mm · 自研压测脚本
未观察到显著回归
部分场景 collapse 延迟更优、单位工作量扫描更多页
① 兑现中粒度收益
占用率不足 PMD 的区间,连续数十页可折成 mTHP
② TLB 未命中有望下降
更多区域拿到 mTHP,内存访问延迟有望改善
③ 降低使用门槛
无须先启用 PMD THP,后台也能产出 mTHP
④ 可观测、可调优
per-order 失败统计与 tracepoints
值不值得折 ≠ 折多大:先记全,再按对齐窗口选最大 order
空格
播放/暂停
←
→
逐动作
R
重播
⚠
1x