Linux内核MMU内存管理与页表机制 - 第1节
1.1 计算机内存层次结构
现代计算机系统为了在性能、容量和成本之间取得平衡,构建了一个多级存储层次。从最靠近CPU的寄存器到最远的磁盘,每一级在速度、容量和每比特成本上都有数量级的差异。理解这个层次是掌握MMU(内存管理单元)工作原理的前提。
1.1.1 层次结构与关键指标
下表对比了存储层次中每一级的典型容量、访问延迟和带宽。数据基于现代服务器级系统(2020年代)。
| 存储层级 | 典型容量 | 访问延迟 | 带宽(典型) | 管理实体 |
|---|---|---|---|---|
| 寄存器 | 几百字节(如 32×64位) | ~0.3 ns(1个CPU周期) | 数千 GB/s | 编译器 / 程序员 |
| L1 缓存(指令/数据) | 32 KB – 64 KB(每核) | ~1 ns(3-4 周期) | ~1000 GB/s | 硬件(SRAM) |
| L2 缓存 | 256 KB – 1 MB(每核) | ~3-4 ns(10-12 周期) | ~500 GB/s | 硬件(SRAM) |
| L3 缓存(LLC) | 8 MB – 64 MB(共享) | ~10-15 ns(30-50 周期) | ~200 GB/s | 硬件(SRAM) |
| 主存(DRAM) | 8 GB – 2 TB | ~50-100 ns | ~50 GB/s(DDR5) | MMU + 内核 |
| 固态盘(SSD) | 256 GB – 8 TB | ~10-100 μs | ~3-7 GB/s(NVMe) | 内核(VFS + 块层) |
| 机械硬盘(HDD) | 1 TB – 20 TB | ~5-15 ms | ~200 MB/s | 内核(VFS + 块层) |
1.1.2 存储层次结构全景图
下图展示了从CPU核心到磁盘的完整存储层次,以及数据流动的方向。注意,缓存和主存中的数据最终都来源于磁盘上的可执行文件和交换空间。
1.2 各层次的工作原理
1.2.1 寄存器:最快的存储
寄存器是CPU内部由触发器(Flip-Flop)构成的存储单元,与CPU核心同频工作。编译器负责寄存器分配(Register Allocation),将最频繁使用的变量和中间结果保存在寄存器中。
- 特点:零延迟访问(单周期)、容量极小(通常几十到几百字节)、完全由软件(编译器)管理。
- 在Linux内核中的角色:上下文切换时,内核需要保存和恢复所有通用寄存器(如 x86-64 的 rax, rbx, rcx, rdx, rsi, rdi, rbp, rsp, r8-r15 等)。
1.2.2 缓存:弥合速度鸿沟
缓存使用静态随机存取存储器(SRAM),速度比DRAM快5-10倍,但成本更高、密度更低。现代CPU采用多级缓存架构:L1最快最小,L3最慢最大。
缓存工作的核心是缓存行(Cache Line),通常为64字节。当CPU访问一个内存地址时,整个缓存行都会被加载到缓存中,以利用空间局部性。
1.2.3 主存:物理内存的舞台
主存(DRAM)是操作系统和应用程序运行的主要场所。物理内存被划分为固定大小的页帧(Page Frame),通常为4KB。内核通过页表(Page Table)将虚拟页映射到物理页帧。
物理内存的分配与回收是内核内存管理子系统的核心职责,包括:
- 伙伴系统(Buddy System):管理连续物理页帧的分配与释放,避免外部碎片。
- slab分配器:在内核内部为小对象(如进程描述符、inode)提供高速缓存,避免频繁调用伙伴系统。
- 页回收(Page Reclaim):当内存不足时,通过LRU算法将不活跃的页面换出到磁盘交换空间。
1.2.4 磁盘:虚拟内存的基石
磁盘(包括SSD和HDD)作为存储层次的最底层,容量最大但速度最慢。在内存管理中,磁盘承担两个关键角色:
- 交换空间(Swap Space):当物理内存不足时,内核将不活跃的内存页换出到磁盘上的交换分区或交换文件。当进程再次访问这些页时,触发缺页异常(Page Fault),内核将数据从磁盘换入内存。
- 文件映射(File-backed Mapping):可执行文件和共享库的代码段、数据段通过内存映射文件(mmap)直接映射到进程的虚拟地址空间。页面按需从磁盘加载,称为按需调页(Demand Paging)。
1.3 MMU在内存管理中的核心地位
MMU(Memory Management Unit)是CPU内部的一个硬件模块,负责执行虚拟地址到物理地址的转换。它是整个内存层次结构的“交通警察”,所有CPU发出的内存访问请求都必须经过MMU的检查与转换。
1.3.1 MMU的核心职责
| 职责 | 描述 | 硬件/软件协作 |
|---|---|---|
| 地址转换 | 将CPU发出的虚拟地址(VA)转换为物理地址(PA) | 硬件:TLB + 页表遍历器;软件:内核维护页表 |
| 权限检查 | 检查访问类型(读/写/执行)是否与页表项中的权限位匹配 | 硬件:在转换过程中并行检查;软件:内核设置页表权限 |
| 隔离保护 | 确保进程A无法访问进程B的物理内存,用户态无法访问内核空间 | 硬件:通过页表基地址寄存器(如CR3)切换地址空间 |
| 缓存控制 | 控制页面的缓存策略(可缓存、写透、写回、不可缓存) | 硬件:读取页表项中的缓存属性位;软件:设置属性 |
| 缺页异常处理 | 当页表项无效(未映射或换出)时,触发异常,由内核软件处理 | 硬件:触发缺页异常(#PF);软件:内核缺页异常处理程序 |
1.3.2 MMU在存储层次中的位置
下图展示了MMU在CPU与缓存/主存之间的精确位置。注意,现代CPU通常将MMU与L1缓存紧密集成,以支持虚拟索引物理标签(VIPT)或物理索引物理标签(PIPT)的缓存策略。
1.3.3 MMU 与操作系统的协作
MMU 是硬件,但它需要操作系统的软件配合才能完成完整的内存管理功能。这种软硬件协作体现在以下关键接口上:
- 页表基地址寄存器:在 x86-64 架构中,CR3 寄存器保存当前进程的顶级页表(PML4)的物理地址。进程切换时,内核必须更新 CR3,使 MMU 指向新进程的页表。
- TLB 刷新:当页表内容被修改(如取消映射、修改权限)后,内核必须执行 TLB 刷新指令(如 invlpg 或 mov cr3, ...),使 MMU 的缓存失效,否则可能使用过时的转换结果。
- 缺页异常处理:当 MMU 在页表中遇到无效项(Present 位为 0)时,会触发缺页异常(#PF)。内核的缺页异常处理程序负责:分配物理页帧、从磁盘加载数据、更新页表、恢复进程执行。
1.4 本章小结
计算机内存层次结构通过多级存储(寄存器→缓存→主存→磁盘)在速度、容量和成本之间取得平衡。MMU 位于 CPU 与缓存/主存之间,是虚拟内存系统的核心硬件组件,负责地址转换、权限检查、隔离保护和缺页异常触发。理解这一层次结构以及 MMU 在其中扮演的角色,是深入学习 Linux 内核页表机制、内存分配与回收策略的前提。
| 层级 | 核心组件 | MMU 的参与 |
|---|---|---|
| CPU 内部 | 寄存器、TLB | TLB 是 MMU 内部的地址转换缓存 |
| 缓存 | L1/L2/L3 SRAM | MMU 输出物理地址供缓存索引;缓存属性由页表控制 |
| 主存 | DRAM、页表 | 页表存储在主存中;MMU 通过硬件遍历器访问页表 |
| 磁盘 | SSD/HDD、交换空间 | 缺页异常由 MMU 触发,内核负责磁盘 I/O 和页表更新 |