mm: Use a folio in the softleaf_is_device_private path

内存管理 · folio API 迁移 · device-private 页 swap-in 路径

💡 一句话总结

在从 device-private 内存(如 GPU、持久内存的私有页)swap-in 时,内核 do_swap_page() 需要对目标页加锁、迁移回 RAM。本补丁把这段路径从旧 page API(trylock_page/get_page)迁移到 folio API(folio_trylock/folio_get),是内核全面 folio 化的持续推进——已被 David Hildenbrand(Acked-by)和 Lorenzo Stoakes(Reviewed-by)两位 mm 维护者认可。

📋 补丁基本信息

项目内容
补丁类型重构(folio API 迁移,语义不变)
状态In Review(v4,获维护者认可)
当前版本v4 · lore 链接
版本演进 v2(07-23,Acked-by David Hildenbrand)→ v3(07-27)→ v4(08-03,Reviewed-by Lorenzo Stoakes)
作者机构Hongfu Li
提交日期2026-08-03
改动范围1 文件(mm/memory.c),+6/-5 行
核心函数do_swap_page() / page_folio()

📊 速览卡片

核心机制
folio API
优化目标
语义统一
适用场景
device-private
实测提升
无(重构)

🎯 解决什么问题

背景 / 原始动机
内核正在**全面从 struct page 迁移到 struct folio**(Matthew Wilcox 主导的 folio 化)。folio 代表"一页或多页"的复合单位,用 folio API 操作更安全(避免误把复合页的 tail 当 head)。本补丁是这场大迁移在 device-private swap-in 路径的一小步。
系统层面:do_swap_page 的 device-private 分支
do_swap_page() 处理"从 swap 换入页"。其中 device-private 分支(is_device_private_page)处理 GPU/持久内存的私有页:需对页加锁(trylock_page)、拿引用(get_page)、调用 migrate_to_ram 迁回 RAM。本补丁把这段的 page API 换成 folio API——先 page_folio() 拿到 folio,再 folio_trylock/folio_get。
场景层面
使用 device-private 内存的场景(CXL 内存、GPU 显存、持久内存的私有映射)在缺页换入时走此路径。folio 化保证这些路径与内核其他部分语义一致,为后续 folio 化改造铺路。

🧩 核心机制

核心是 API 语义迁移,不改行为:page API → folio API,锁/引用计数语义等价。

从系统层面看(逐行对应)
旧 page API新 folio API语义
trylock_page(vmf->page)folio_trylock(folio)尝试加页锁(防并发释放)
get_page(vmf->page)folio_get(folio)拿引用(防迁移期间释放)
unlock_page / put_pagefolio_unlock / folio_put解锁 + 释放引用
关键:page_folio(vmf->page) 返回 folio 头页。对单页 folio,行为完全等价;对复合页,folio API 保证操作在整个 folio 上一致(更安全)。

🔬 关键代码

@@ -4873,18 +4873,19 @@ vm_fault_t do_swap_page(struct vm_fault *vmf)
-			if (trylock_page(vmf->page)) {
+			folio = page_folio(vmf->page);
+			if (folio_trylock(folio)) {
 				struct dev_pagemap *pgmap;
 
-				get_page(vmf->page);
+				folio_get(folio);
 				pte_unmap_unlock(vmf->pte, vmf->ptl);
 				pgmap = page_pgmap(vmf->page);
 				ret = pgmap->ops->migrate_to_ram(vmf);
-				unlock_page(vmf->page);
-				put_page(vmf->page);
+				folio_unlock(folio);
+				folio_put(folio);

▲ 关键:page_folio() 取 folio 头,后续锁/引用计数都在 folio 上做,保证复合页一致性。

📈 性能影响

**补丁未提供基准数据**。本补丁是 folio API 迁移(语义等价,无运行时行为变化),不改变 device-private swap-in 路径的性能特征。价值在于与内核 folio 化大方向保持一致,为后续针对复合页的优化铺路(解读(AI 分析))。

🔄 方案演进

v2 → v4 演进脉络
v2(07-23):初始版,获 David Hildenbrand Acked-by(mm 内存管理权威)
v3(07-27):微调,保持 Acked-by
v4(08-03):获 Lorenzo Stoakes Reviewed-by(folio API 方向权威)
讨论 / review 意义
两位维护者的背书说明这是**符合内核 folio 化方向的正确改动**。Lorenzo Stoakes 是 folio API 相关工作的核心维护者,他的 Reviewed-by 代表方向认可。

🔗 交叉引用

📌 关联工作
mm: remove wait_on_page_writeback() — 同日报另一篇 folio 化收尾,同为 page→folio API 迁移
PATCH v4 lore — 本补丁原始链接(Reviewed-by Lorenzo Stoakes, Acked-by David Hildenbrand)

⚠️ 风险与局限

潜在回归 / 边界
行为等价:folio 迁移语义不变,对单页无差异;对复合页更安全(防止 tail 页误操作)。回归风险极低(解读(AI 分析))。
范围小:仅 device-private 分支,不影响通用 swap-in 路径。
严重度:MINOR · 维护者已背书(Acked+Reviewed)

✅ 关键洞察

  • 发现:device-private swap-in 路径 page→folio API 迁移,是内核 folio 化的一小步
  • 证据:语义等价(无行为变化);获 David Hildenbrand Acked + Lorenzo Stoakes Reviewed
  • 边界:仅 device-private 分支;单页行为不变,复合页更安全
  • 风险 / 建议:低风险重构,符合 folio 化大方向,值得合入
⚠️ 免责声明

本站内容均由 AI 基于公开知识辅助生成,仅供学习参考,请勿直接引用作为依据。作者不对信息的准确性、完整性及适用性作保证,亦不对因使用本站内容产生的任何损失承担责任。