记录一个关于线程内存泄漏问题的定位过程 , 以及过程中的收获 。
1. 初步定位是否存在内存泄漏:想到内存泄漏 , 首先查看/proc/meminfo , 通过/proc/meminfo可以看出总体内存在下降 。确定内存泄漏确实存在 。top中可以显示多种形式内存 , 进而可以判断是那种泄漏 。比如vss/rss/pss等 。
确定哪个进程内存泄漏:通过top即可查看到是哪个进程在泄漏 。至此基本可以确定到哪个进程 。
确定进程泄漏内存类型:然后查看进程的/proc/<pid>/maps , 通过maps可以看出泄漏的内存类型(堆、栈、匿名内存等等) , 有时候运气好可以直接判断泄漏点 。
如果是slab:可以通过/proc/slabinfo , 可以看出进程的动态变化情况 。如果确定是哪一个slab , 那么可以在/sys/kernel/slab/<slab name>/alloc_calls和free_calls中直接找到调用点 。当然看到的是内核空间的函数 。
使用mcheck():可以检查malloc/free造成的泄漏问题 。
通过如下脚本 , 然后对每次抓取内容进行Beyond Compare 。每个一定周期抓取相关内存消耗信息 。
#!/bin/bashecho > mem_log.txtwhile truedocat /proc/meminfo >>mem_log.txtcat /proc/<pid>/maps >>mem_log.txtcat /proc/slabinfo >>mem_log.txtsleep 240done
当然还有其他工具gcc Sanitier、Valgrind等等 , 由于嵌入式环境受限未能使用 。
2. 深入定位同步查看meminfo、maps、slabinfo , 发觉进程虚拟内存损耗很快 , 远比系统MemFree损耗快 。而且slabinfo没有和maps同步损耗 。
所以问题重点检查maps问题 。
00010000-00083000 r-xp 00000000 b3:11 22/heop/package/AiApp/AiApp00092000-00099000 rwxp 00072000 b3:11 22/heop/package/AiApp/AiApp00099000-00b25000 rwxp 00000000 00:00 0[heap]00b51000-00b52000 ---p 00000000 00:00 0 00b52000-01351000 rwxp 00000000 00:00 0[stack:30451]01351000-01352000 ---p 00000000 00:00 0 01352000-01b51000 rwxp 00000000 00:00 0 01b51000-01b52000 ---p 00000000 00:00 0 01b52000-02351000 rwxp 00000000 00:00 0[stack:30432]02351000-02352000 ---p 00000000 00:00 0 02352000-02b51000 rwxp 00000000 00:00 0 02b51000-02b52000 ---p 00000000 00:00 0 ...64f55000-65754000 rwxp 00000000 00:00 0[stack:28646]65754000-65755000 ---p 00000000 00:00 0 65755000-65f54000 rwxp 00000000 00:00 0[stack:28645]65f54000-65f55000 ---p 00000000 00:00 0 65f55000-66754000 rwxp 00000000 00:00 0[stack:28642]66754000-6675a000 r-xp 00000000 00:02 5000324/usr/lib/AiApp/gstreamer-1.0/libgsticcsink.so6675a000-66769000 ---p 00000000 00:00 0 ...6699f000-669a0000 rwxp 00000000 00:02 4999516/usr/lib/AiApp/gstreamer-1.0/libgstapp.so669a0000-66a2e000 rwxp 00000000 00:02 4999517/usr/lib/AiApp/gstreamer-1.0/libgstlive555src.so66a2e000-66a3e000 ---p 00000000 00:00 0 66a3e000-66a44000 rwxp 0008e000 00:02 4999517/usr/lib/AiApp/gstreamer-1.0/libgstlive555src.so66a44000-66a45000 rwxp 00000000 00:00 0 66a45000-66a46000 ---p 00000000 00:00 0 66a46000-67245000 rwxp 00000000 00:00 0[stack:28631]67245000-67246000 ---p 00000000 00:00 0 67246000-67a45000 rwxp 00000000 00:00 0[stack:28630]...6b245000-6b246000 ---p 00000000 00:00 0 6b246000-6ba45000 rwxp 00000000 00:00 0[stack:28613]6ba45000-6ba46000 ---p 00000000 00:00 0 6ba46000-6c245000 rwxp 00000000 00:00 0[stack:28610]6c245000-71066000 rwxs 00000000 00:01 196614/SYSV5553fc99 (deleted)71066000-71067000 ---p 00000000 00:00 0 71067000-71866000 rwxp 00000000 00:00 0[stack:28609]71866000-71867000 ---p 00000000 00:00 0 71867000-72066000 rwxp 00000000 00:00 0[stack:28608]72066000-72228000 rwxs e3dc4000 00:02 6918/dev/mmz_userdev72228000-725ac000 rwxs e3a40000 00:02 6918/dev/mmz_userdev725ac000-75cac000 rwxs 00000000 00:01 131076/SYSV6702121c (deleted)75cac000-75e8a000 rwxs 00000000 00:01 98307/SYSV6602121c (deleted)75e8a000-7608e000 rwxp 00000000 00:00 0...76eeb000-76efb000 ---p 00000000 00:00 0 76efb000-76eff000 r-xp 000ce000 00:02 1234/lib/libstdc++.so.6.0.2076eff000-76f01000 rwxp 000d2000 00:02 1234/lib/libstdc++.so.6.0.2076f01000-76f08000 rwxp 00000000 00:00 0 76f08000-76f0f000 r-xp 00000000 00:02 1235/lib/ld-uClibc-0.9.33.2.so76f1a000-76f1e000 rwxp 00000000 00:00 0 76f1e000-76f1f000 rwxp 00006000 00:02 1235/lib/ld-uClibc-0.9.33.2.so76f1f000-76f20000 ---p 00000000 00:00 0...7c720000-7cf1f000 rwxp 00000000 00:00 0[stack:30574]7cf1f000-7cf20000 ---p 00000000 00:00 0 7cf20000-7e121000 rwxp 00000000 00:00 0[stack:30575]7eef7000-7ef18000 rwxp 00000000 00:00 0[stack]7efb7000-7efb8000 r-xp 00000000 00:00 0[sigpage]ffff0000-ffff1000 r-xp 00000000 00:00 0[vectors]
通过多次maps对比 , 可以发现[stack:TID]类型的内存以及一个匿名内存在不停增加消耗内存 。
其中[stack:TID]类型的内存 , 在内核查找相关代码没有明确对应属性 。初步判断是线程的栈 , TID表示线程id号 。
所以这里应该是某个线程泄漏 。
推荐阅读
- 康熙的和硕二十三公主,和硕和恪公主生了一个公主
- 员工行为准则的详细介绍
- 电影|五一多部大片跑路 电影《珠峰队长》逆流而上:做了一个不理智的决定
- 皇后是不是皇上的第一个老婆,太宗皇后叫什么名字
- 张良在史记中是什么世家,史记留侯世家张良是一个怎样的存在
- C语言预编译处理,如何定义一个带参数 宏?如何取消宏定义?
- 自己搭建一个网站需要多少钱
- 服务器出问题了,作为IT,怎样才能第一个知道?免得被骂
- 刘彻后面一个皇帝是谁母亲是谁,刘彻的母亲王皇后
- 一个被误解的乱世枭雄,一个被误解的星座