You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

ARMV7架构用户虚拟地址转PFN代码异常及常驻内存虚拟地址咨询

问题解答

1. pte返回空是否表示虚拟地址已被换出?

前置说明

ARMV7架构实际仅使用2级页表机制,Linux内核为了兼容多架构页表设计,对PGD/PUD/PMD做了层级折叠处理,你观测到pgd_val(*pgd)、pud_val(*pud)、pmd_val(*pmd)取值一致属于正常现象,不是运行错误。

结论

该现象不代表虚拟地址被换出,核心原因如下:

  • 页面被换出时,页表项不会被清空为0,内核会在页表项中存储swap分区偏移、swap文件位置等换出标记信息,不会触发pte为空的判断
  • 你观测到pte_offset_kernel()返回空,通常是以下几类原因:
    • 传入的用户虚拟地址没有对应有效VMA(虚拟内存区域),本身属于非法地址
    • 虚拟地址对应的VMA存在,但还未触发缺页异常分配物理页,属于已预留未分配的地址范围
    • 遍历页表时没有持有current->mm->mmap_lock(旧版内核为mmap_sem)锁,遍历过程中页表刚好被回收、调整,导致偶发空指针问题
    • 接口使用错误:pte_offset_kernel()是专为内核地址空间页表遍历设计的接口,遍历用户态地址应使用pte_offset_map(),否则容易出现兼容性问题

2. 常驻内存不被换出的用户虚拟地址类型

满足以下任意条件的用户虚拟地址不会被系统换出:

  • 调用mlock()/mlock2()/mlockall()系统调用显式锁定的地址范围:锁定后页面不会被回收、换出,直到进程主动解锁或者进程退出。普通进程可锁定的内存大小受RLIMIT_MEMLOCK资源限制,超出限制的锁定操作需要进程持有CAP_IPC_LOCK权限
  • 调用mmap()映射内存时携带MAP_LOCKED标记的地址区域:映射完成后自动锁定,效果和mlock()完全一致
  • 特殊设备映射的内存区域:比如通过/dev/mem、/dev/vfio等字符设备映射的IO物理地址、设备内存,这类内存本身不参与系统页回收逻辑
  • 携带SHM_LOCK标记的System V共享内存、POSIX共享内存:所有挂载该共享内存的进程对应的虚拟地址都不会被换出

内容的提问来源于stack exchange,提问作者md.jamal

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.04 11:15:03