Linux 内核技术实战课
邵亚方
前蘑菇街技术专家,Linux Kernel 活跃贡献者
23704 人已学习
新⼈⾸单¥59
登录后,你可以任选4讲全文学习
课程目录
已完结/共 26 讲
Linux 内核技术实战课
15
15
1.0x
00:00/00:00
登录|注册

10 分析篇 | 内存泄漏时,我们该如何一步步找到根因?

复现问题并观察
使用 strace 跟踪系统调用
使用 /proc/[PID]/smaps 查看内存区域
使用 pidstat 追踪进程的内存行为
业务进程的虚拟地址空间异常
掌握通用的分析技巧
使用 top 工具和 /proc/meminfo 文件
实际案例分析
使用 top 工具观察进程内存
使用 /proc/meminfo
编写内存泄漏程序并观察 /proc/[pid]/maps 和 smaps 的变化
基础知识的重要性
分析方法要点
分析进程的内存泄漏原因
定位消耗内存的进程
课后作业
课堂总结
系统性分析内存泄漏问题的方法
理解内存泄漏
文章:内存泄漏时,该如何一步步找到根因?

该思维导图由 AI 生成,仅供参考

你好,我是邵亚方。
通过我们前面的基础篇以及案例篇的学习,你对内存泄漏应该有了自己的一些理解。这节课我来跟你聊一聊系统性地分析内存泄漏问题的方法:也就是说,在面对内存泄漏时,我们该如何一步步去找到根因?
不过,我不会深入到具体语言的实现细节,以及具体业务的代码逻辑中,而是会从 Linux 系统上通用的一些分析方法来入手。这样,不论你使用什么开发语言,不论你在开发什么,它总能给你提供一些帮助。

如何定位出是谁在消耗内存 ?

内存泄漏的外在表现通常是系统内存不够,严重的话可能会引起 OOM (Out of Memory),甚至系统宕机。那在发生这些现象时,惯用的分析套路是什么呢?
首先,我们需要去找出到底是谁在消耗内存,/proc/meminfo 可以帮助我们来快速定位出问题所在。
/proc/meminfo 中的项目很多,我们没必要全部都背下来,不过有些项是相对容易出问题的,也是你在遇到内存相关的问题时,需要重点去排查的。我将这些项列了一张表格,也给出了每一项有异常时的排查思路。
总之,如果进程的内存有问题,那使用 top 就可以观察出来;如果进程的内存没有问题,那你可以从 /proc/meminfo 入手来一步步地去深入分析。
确认放弃笔记?
放弃后所记笔记将不保留。
新功能上线,你的历史笔记已初始化为私密笔记,是否一键批量公开?
批量公开的笔记不会为你同步至部落
公开
同步至部落
取消
完成
0/2000
荧光笔
直线
曲线
笔记
复制
AI
  • 深入了解
  • 翻译
    • 英语
    • 中文简体
    • 中文繁体
    • 法语
    • 德语
    • 日语
    • 韩语
    • 俄语
    • 西班牙语
    • 阿拉伯语
  • 解释
  • 总结

本文详细介绍了如何系统性地分析内存泄漏问题的方法,从Linux系统上通用的分析方法入手。作者指出内存泄漏的外在表现通常是系统内存不够,甚至可能引起系统宕机。通过实际案例和命令行输出展示了如何使用pidstat、strace等工具来追踪进程的内存行为,以及如何通过/proc/PID/smaps和strace命令来定位内存泄漏的具体原因。总的来说,本文提供了一些通用的分析方法,无论使用何种开发语言,都能为读者提供帮助。文章强调了掌握通用的分析技巧对解决内存泄漏问题的重要性,同时也提到了基础知识的重要性。通过详细的分析过程,读者可以快速了解如何分析进程的内存泄漏原因,为解决类似问题提供了实用的方法和技巧。

仅可试看部分内容,如需阅读全部内容,请付费购买文章所属专栏
《Linux 内核技术实战课》
新⼈⾸单¥59
立即购买
登录 后留言

全部留言(12)

  • 最新
  • 精选
  • 石小
    “对于有经验的开发者而言,从这个 4K 的保护页就可以猜测出应该跟线程栈有关了。” 请问老师怎么理解这局话?

    作者回复: 这是为了防止栈溢出问题,当线程栈溢出后,就会写这个保护页,进而出发segfault。

    2021-04-08
    12
  • 飘云
    写应用层代码的时候会用到clone么,不都用pthread么? 用pthread不会出现例子中的问题吧。 另外,内存泄露很多时候是malloc了内存但是没有free,有什么好的方法快速定位是哪儿分配的内存忘了free呢?

    作者回复: pthread_create的时候可能会调用clone,clone是一个系统调用,pthread是lib库,库函数其实是对系统调用的封装。 物理内存泄露并没有什么高效的分析方式,只能通过追踪malloc/free来看在哪里申请的没有去释放。

    2020-10-30
    2
    5
  • 黑客不够黑
    老师好,这个案例讲的是虚拟内存泄露,我想问一下:虚拟内存分配后在使用前不会真正的分配物理内存,那这个案例是不是仅仅是进程的虚拟内存存在问题?整个Linux系统的内存应该没有异常对不对?

    作者回复: 对的 只是虚拟地址空间产生了问题 实际的物理内存并没有问题 整个系统的内存并没有异常

    2020-10-29
    5
  • Geek_circle
    老师好,当系统内存不足,发现kswapd0进程持续运行,使用率超过90%多,load过百,但是系统日志中并没有记录到oom killer 。想知道系统内存不足时,启动kswapd和oom killer条件和优先级是什么样的呢?

    作者回复: 内存水位不足后就会唤醒kswapd来回收内存,如果kswapd可以回收内存并且内存水位持续高,kswapd就会一直忙,它的使用率就会高。只有在回收不到内存的情况下,才会触发oom killer来杀进程。 你说的这种情况就是可以回收到内存,但是回收比较困难 所以才产生这种情况。

    2020-09-13
    3
  • dpzain
    现在生产环境 是jvm 程序 跑在docker容器, jvm 堆内内存 监控一切正常,但是每隔半个月 mem从50%到90% ,按照上面的方法发现确实有对外内存在缓慢的泄漏 非常慢(没5s - 20s 增加几kb甚至 几十个byte )找不出任何规律 怎么破;

    作者回复: jvm堆外内存泄漏,在明确哪些任务在泄漏内存后,最好能否结合代码来进行打点追踪,看看哪里有问题。

    2020-11-24
    1
  • jssfy
    问题分析过程很赞,开头的总结性图表也很赞!
    2020-09-13
    2
  • mong
    老师, 看了你的这些文章, 对线上内存的定位也有一些思路, 我正面临的一个Java应用程序内存有问题的, VIRT, RSS的内存很高, 用/proc/pid/smaps, 发现有很多64M的内存申请,占了将近3个G 如下: 7fe698000000-7fe69bffa000 rw-p 00000000 00:00 0 Size: 65512 kB KernelPageSize: 4 kB MMUPageSize: 4 kB Rss: 62456 kB Pss: 62456 kB Shared_Clean: 0 kB Shared_Dirty: 0 kB Private_Clean: 0 kB Private_Dirty: 62456 kB Referenced: 62448 kB Anonymous: 62456 kB LazyFree: 0 kB AnonHugePages: 0 kB ShmemPmdMapped: 0 kB Shared_Hugetlb: 0 kB Private_Hugetlb: 0 kB Swap: 0 kB SwapPss: 0 kB Locked: 0 kB VmFlags: rd wr mr mw me nr 但到这一步我无法继续的下去, 我用gdp dump了这段的地址的bin下来, 打开文件都Null, 所以我的java内存的堆的内存通过监控看也比较稳定, 所以目前没有什么头绪, 所以相让你指点一点, 接下来应该从哪里继续的排查;
    2022-09-16归属地:广东
    1
  • Bachue Zhou
    不太懂,smaps 的内容这么多,如何找到出问题的部分?是多次 cat smaps 然后做 diff 吗?
    2022-06-05
  • Felix
    真是读书万卷,其意自现
    2022-05-17
  • 我能走多远
    对底层的基础理论不牢靠,原来定位问题有这么多的方法。学习了
    2020-11-07
收起评论
显示
设置
留言
12
收藏
沉浸
阅读
分享
手机端
快捷键
回顶部