pmap pid可查看进程内存映射的地址、大小、权限和来源;pmap -x显示rss和dirty用于定位泄漏;pmap -d显示设备信息;/proc/pid/smaps比pmap更精准,提供pss、private_dirty等关键指标。

怎么看进程的内存映射:用 pmap 快速定位段类型和大小
直接用 pmap PID 就能看到进程所有内存段的起始地址、大小(Kbytes)、权限(Mode)和来源(Mapping)。它本质是读取 /proc/PID/maps,但格式更友好。
常见陷阱是把 [heap] 和 [anon] 混为一谈:[heap] 是 brk/sbrk 分配的连续堆区;而 [anon] 泛指所有匿名映射,包括 malloc 大块内存(mmap 分配)、线程栈、JVM 堆外内存等。它们在 pmap 输出里都显示为 [anon],但实际行为完全不同。
-
pmap -x PID才能看到RSS(驻留物理内存)和Dirty(脏页),这是判断泄漏的关键——比如某[anon]行 RSS 持续上涨,大概率是堆外内存没释放 -
pmap -d PID会显示Device和Offset,若Device是00:00且Mapping是[anon],说明这段内存完全无文件 backing,纯靠内核分配物理页 - 别依赖
ps aux的RSS列——它只反映进程整体驻留内存,无法区分共享库、堆、栈各自占多少
为什么 /proc/PID/smaps 比 pmap 更准:它拆开了共享内存的摊销
/proc/PID/smaps 对每个虚拟内存区域(VMA)单独给出 Pss(Proportional Set Size),即把共享内存按参与进程数均摊。例如一个 20MB 的 libc.so 被 10 个进程加载,每个进程的 Pss 只算 2MB,而 RSS 仍记 20MB。
你真正该盯住的是这三列:
-
Rss:当前实际占用的物理内存(KB),总和 ≈pmap -x的 RSS 总和 -
Pss:更公平的“单进程内存开销”,排查谁拖垮了整机内存时必看 -
Private_Dirty:该 VMA 中未被共享、且被写过的内存(KB),它是内存泄漏最直接的信号——持续增长基本等于进程自己在疯狂 malloc + 写入却没 free
注意:smaps 文件每行对应一个 VMA,所以一个 Java 进程可能有上千行输出。用 grep -A 5 "heap" /proc/PID/smaps 或 awk '/^Name:/ && /heap/ { getline; print }' /proc/PID/smaps 快速过滤堆段更实用。
Zynq‑7000 / Zynq UltraScale+ 硬件调试技能。适用于 Xilinx Zynq(Cortex‑A9/A53 + FPGA)Linux 环境,调试 I2C、I2S、UART、GPIO 等外设。包括设备树配置、内核驱动、用户空间调试工具、交叉编译和常见问题排查,支持 PetaLinux 开发。
/proc/PID/maps 权限字段(perms)怎么看懂:rwxp vs rwxs
/proc/PID/maps 第二列的 4 字符权限(如 r-xp)比 pmap 多一层信息:p 表示 private 映射(写时复制),s 表示 shared 映射(多进程可协同修改同一块物理页)。
典型场景:
- 代码段(
r-xp):ELF 文件映射,只读 + 私有,改不了也不会影响其他进程 - 数据段(
rw-p):已初始化全局变量,私有,写操作触发 COW - 堆(
rw-p):brk 分配,私有;但大块 malloc(>128KB 默认)走 mmap,也是rw-p - 共享库的 .so 数据段(
rw-s):如果库用了MAP_SHARED映射,多个进程可互见修改(少见,多用于 IPC)
如果你看到某行 perms 是 rw-s 且 Mapping 是 [anon],基本是进程间通过 shm_open + mmap 创建了共享内存——这种内存不会出现在 pmap -x 的 [heap] 或 [stack] 里,得靠 maps 或 smaps 手动识别。
什么时候必须放弃 pmap,直接扒 /proc/PID/smaps
当你要确认某个具体内存区域是否真的“脏”、是否“私有”、是否“被引用过”,pmap 的信息就太粗了。smaps 每行末尾的 MMUPageSize 和 KernelPageSize 还能帮你判断是否启用了 THP(Transparent Huge Pages)——如果这两值都是 2048 kB,说明该 VMA 正在用大页,对延迟敏感服务(如 Redis、DPDK)很关键。
最容易被忽略的一点:smaps 里的 Referenced 字段表示该 VMA 中有多少页被 CPU 访问过(非只读访问也算)。如果某段 [anon] 的 Rss 很高但 Referenced 几乎为 0,大概率是内存碎片或已分配但从未触碰的“幽灵内存”,可以安全回收(比如调用 malloc_trim(0) 或 JVM 的 -XX:+UseG1GC -XX:MaxGCPauseMillis=50)。










