news 2026/9/30 11:25:43

linux kernel struct 之 ptdesc

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
linux kernel struct 之 ptdesc

struct ptdesc的定义在 Linux 内核的include/linux/mm_types.h文件中(早期版本曾放在include/linux/pgtable.h)。它的设计目标是将页表元数据从struct page中拆分出来,目前通过完全覆盖(overlay)struct page的内存布局来实现。

定义代码

根据内核补丁(以 v6 版本为例),其完整定义如下:

struct ptdesc { unsigned long __page_flags; union { struct rcu_head pt_rcu_head; struct list_head pt_list; struct { unsigned long _pt_pad_1; pgtable_t pmd_huge_pte; }; }; unsigned long _pt_s390_gaddr; union { struct mm_struct *pt_mm; atomic_t pt_frag_refcount; unsigned long _pt_pad_2; }; #if ALLOC_SPLIT_PTLOCKS spinlock_t *ptl; #else spinlock_t ptl; #endif unsigned int __page_type; atomic_t _refcount; #ifdef CONFIG_MEMCG unsigned long pt_memcg_data; #endif };

核心字段说明

字段说明
__page_flags与page->flags相同,页表场景下通常未使用
pt_rcu_head用于延迟释放页表页的 RCU 回调(与pt_list共用内存)
pt_list串联已使用的页表,用于 s390 和 x86
pmd_huge_pte受ptl保护,用于透明大页(THP)场景
_pt_s390_gaddr仅 s390 架构使用,用于 gmap 地址追踪
pt_mm仅 x86 架构使用,用于 PGD(页全局目录)
pt_frag_refcount仅 PowerPC 和 s390 使用,用于碎片化页表追踪
ptl页表锁,保护页表操作(ALLOC_SPLIT_PTLOCKS控制是指针还是内嵌)
_refcount引用计数,与page->_refcount相同,s390 页表使用
pt_memcg_data内存 cgroup 数据,追踪页表的内存使用

关键设计约束

定义末尾有一条静态断言,这是整个设计的核心约束:

static_assert(sizeof(struct ptdesc) <= sizeof(struct page));

这意味着ptdesc的大小不能超过struct page,因为当前它完全复用struct page的内存空间。同时,代码通过TABLE_MATCH宏断言关键字段的偏移量与struct page中对应字段完全一致,确保两种类型可以安全地相互转换。

在NOMMU配置下,struct ptdesc的定义会被移到mm_types.h,因为spinlock_t和struct page的定义顺序会影响编译。

核心定位

struct ptdesc目前完全覆盖(overlay)在struct page之上,也就是说它暂时复用struct page的内存空间,但以独立的类型存在。它的长期目标是让页表可以独立于struct page进行动态分配,从而进一步精简struct page结构。

与pgtable_t的关系

在大多数架构上,pgtable_t原本就是struct page *的 typedef。struct ptdesc的引入是为了逐步用struct ptdesc *替代pgtable_t,使页表描述符的类型更加明确。

不过,这一转换面临架构差异的挑战:在 s390、PowerPC、sparc 和 m68k(除 SUN3)上,pgtable_t被定义为pte_t *,因为每个页表可能小于一个PAGE_SIZE,无法直接映射到单个struct page。因此,struct ptdesc的推广需要各架构的配合。

在内存管理中的角色

struct ptdesc是页表操作(分配、释放、遍历)的核心载体。在___pmd_free_tlb中,virt_to_ptdesc(pmd)就是将页表页的虚拟地址转换为struct ptdesc指针,然后通过tlb_remove_ptdesc加入延迟释放队列。这种设计使得页表的生命周期管理可以与struct page解耦,为未来更灵活的页表内存管理铺平道路。

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/9/30 11:25:15

C++高性能算法

多线程编程&#xff1a;C11/14/17 TL;DR 多线程优先任务并行&#xff0c;线程数约等于核数SIMD 先自动向量化&#xff0c;热点再用 intrinsics内存池适合高频小对象分配场景并发结构优先使用成熟库性能优化必须测量先行&#xff0c;再优化多线程编程&#xff1a;C11/14/17 核心…

作者头像 李华
网站建设 2026/9/30 11:22:53

SpringBoot+Vue宠物咖啡馆系统:前后端分离开发与部署实战指南

做课程设计那会儿&#xff0c;我翻遍了开源社区上的各种管理系统&#xff0c;大部分都是千篇一律的图书管理、宿舍管理、班级管理系统。直到我看到了“基于SpringBootVue的宠物咖啡馆平台管理系统”这套源码&#xff0c;才觉得有点意思。宠物咖啡馆这个题材&#xff0c;本质上是…

作者头像 李华
网站建设 2026/9/30 11:20:23

洗车店次卡怎么核算才不亏钱

洗车店次卡怎么核算才不亏钱&#xff0c;这个问题在洗美门店里比想象中普遍。卡卖出去的时候是现金&#xff0c;看着是赚了&#xff1b;但卖卡收的是预收&#xff0c;是负债&#xff0c;真正决定赚不赚钱的&#xff0c;是这张卡被核销了几次、每次的变动成本是多少。我见过太多…

作者头像 李华
网站建设 2026/9/30 11:18:36

GO [ 类型 ]

类型 前面我们已经学习了 Go 的变量、常量、数据类型、输入输出、条件控制、切片、字符串、映射表、指针、结构体、函数、方法和接口。接下来开始从更底层的角度理解 Go 语言中的一个核心概念&#xff1a;类型&#xff08;type&#xff09;。 很多初学者会把类型理解成 int、…

作者头像 李华
网站建设 2026/9/30 11:18:18

工业场景下的选型难题:为何温度湿度测量不容妥协

在中国制造业从规模扩张走向精细化运营的进程中&#xff0c;工业级温湿度测量正由边缘辅助功能逐步走向质量管控的核心环节。2024年下半年至2025年初&#xff0c;多家自动化设备商以及新能源、半导体、制药企业密集启动温湿度传感器选型与替换评估。他们关注的焦点并非消费级产…

作者头像 李华