HeapSnap

1、HeapSnap 是什么

HeapSnap 是一个定位内存泄露的工具,适用于Android平台。

主要特性如下:

对系统负载低

不需要修改目标进程的源代码

支持Andoroid上的大多数native进程

对函数调用栈自动进行解析,大多情况下不需要找带符号表的程序/库反查地址

支持Android多数较新的版本(Android4.0及以上)

需要root权限支持

2、HeapSnap 工具使用

先让目标进程加载libehapsnap.so,然后再使用kill命令发信号给目标进程去保存heap。下面介绍三种加载libehapsnap.so动态库的方法

2.1 使用heapsnap工具加载动态库

该方法通过进程注入的方式把代码加载到目标进程内。

把heapsnap和libheapsnap.so推送到机器(程序也可以推送到其它目录下)

adb shell chmod 0777 /data/local/tmp

adb push libheapsnap/libheapsnap.so /data/local/tmp/libheapsnap.so

adb shell chmod 0644 /data/local/tmp/libheapsnap.so

adb push heapsnap /data/local/tmp/heapsnap

adb shell chmod 0755 /data/local/tmp/heapsnap

通过adb或者串口登陆目标机器,开启malloc调试,并重启目标进程

setprop libc.debug.malloc 1

setprop libc.debug.malloc.options backtrace

stop;start

[执行你的应用]

加载动态库

/data/local/tmp/heapsnap -p -l /data/local/tmp/libheapsnap.so

通过signal 21获取目标进程的heap信息,并自动保存在/data/local/tmp/heap_snap目录下

kill -21 [pid]

多次在不同时间点获取目标进程的heap信息,并对这些heap信息进行比对,从而找出异常的内存分配

也可以选择在加载动态库时直接执行动态库中的函数保存heap信息,然后马上关闭动态库.以后每次获取heap信息都需要调用相同的命令:

/data/local/tmp/heapsnap -p -l /data/local/tmp/libheapsnap.so -o -f heapsnap_save

获取到的heap信息保存在: /data/local/tmp/heap_snap 目录下

对于已经加载库的进程,也可以这么调用获取heap信息.

2.2 LD_PRELOAD加载动态库

把libheapsnap.so推送到机器

adb shell chmod 0777 /data/local/tmp

adb push libheapsnap/libheapsnap.so /data/local/tmp/libheapsnap.so

adb shell chmod 0644 /data/local/tmp/libheapsnap.so

通过adb或者串口登陆目标机器,开启malloc调试,并重启目标进程(以mediaserver为例)

setprop libc.debug.malloc 1

stop media

LD_PRELOAD=/data/local/tmp/libheapsnap.so mediaserver &

也可以配置当前shell的环境变量,避免每次都要在目标进程前加"LD_PRELOAD"前缀

export LD_PRELOAD=/data/local/tmp/libheapsnap.so

mediaserver &

通过signal 21获取目标进程的heap信息,并自动保存文件到/data/local/tmp/heap_snap/目录下

kill -21 [pid]

多次在不同时间点获取目标进程的heap信息,并对这些heap信息进行比对,从而找出异常的内存分配

2.3 目标程序编译时候链接动态库

在目标程序的编译脚本中加入下面这行,然后在你的程序中调用heapsnap_save(),重新编译好的程序在启动时候会自动链接libheapsnap.so库。

缺点就是需要目标程序的源代码及编译环境。

LOCAL_SHARED_LIBRARIES := libheapsnap

可以参考src/leak_builtin.c代码

3、解析backtrace

使用heapsnap获得的heap信息,已经自动对地址做了解析,如下所示:

Heap Snapshot v1.0

Total memory: 33800

Allocation records: 3

Backtrace size: 32

z 0 sz 4096 num 8 bt 0000007f9a2b0e14 0000007f9a37f534 00000055828338bc 000000558283379c 0000007f9a37f6b0 0000005582833810

#00 pc 0000000000008e14 /system/lib64/libc_malloc_debug_leak.so (leak_malloc+408)

#01 pc 0000000000019534 /system/lib64/libc.so (malloc+24)

#02 pc 00000000000008bc /system/bin/leak_test

#03 pc 000000000000079c /system/bin/leak_test (main+28)

#04 pc 00000000000196b0 /system/lib64/libc.so (__libc_init+104)

#05 pc 0000000000000810 /system/bin/leak_test

通常,heapsnap所解析出来的backtrace信息已经能够大致判断出泄露点了。

但是有时候你需要更精确的解析,如果你手上有设备所对应的android环境,那么可以使用android提供的工具进行backtrace地址解析

android 6及早期版本

$ development/scripts/stack heap.txt > heap_info.txt

android7以后的版本

$ development/scripts/native_heapdump_viewer.py heap.txt > heap_info.txt

解析后的信息如下:

BYTES %TOTAL %PARENT COUNT ADDR LIBRARY FUNCTION LOCATION

0 0.00% 0.00% 0 APP

107808 100.00% 100.00% 198 ZYGOTE

107800 99.99% 99.99% 197 5d1b2c0678 /system/bin/leak_test do_arm64_start external/heapsnap.git/leak_test.c:?

107800 99.99% 100.00% 197 77cd006594 /system/lib64/libc.so __libc_init /proc/self/cwd/bionic/libc/bionic/libc_init_dynamic.cpp:109

98304 91.18% 91.19% 24 5d1b2c073c /system/bin/leak_test foo /proc/self/cwd/external/heapsnap.git/leak_test.c:9 (discriminator 1)

8472 7.86% 7.86% 172 5d1b2c0764 /system/bin/leak_test main /proc/self/cwd/external/heapsnap.git/leak_test.c:22

8472 7.86% 100.00% 172 77cd02a084 /system/lib64/libc.so sleep /proc/self/cwd/bionic/libc/upstream-freebsd/lib/libc/gen/sleep.c:58

8472 7.86% 100.00% 172 77cd05756c /system/lib64/libc.so nanosleep /proc/self/cwd/bionic/libc/arch-arm64/syscalls/nanosleep.S:7

8472 7.86% 100.00% 172 77cd2206bc [vdso] ??? ???

...

注意: 对于android7/8/9版本,需要打下面这个补丁,才能正常解析heapsnap保存下来的heap信息

$ cd android/development

$ patch -p1 < android_7_8_9_development_script.patch

4、注意点

注意arm/arm64版本的区别,如果调试的目标程序是32bit,请使用arm版本的heapsnap程序和libheapsnap.so库;如果调试的目标程序是64bit,就要使用arm64版本的heapsnap程序和libheapsnap.so库。

对于android 9/10及以后的版本,若你调试的对象是**/vendor目录下的程序,那么你必须把libheapsnap.so**文件也放到/vendor目录下,否则加载libheapsnap.so文件会失败。

对于android 7/8/9版本,在这几个版本中把获得的heap信息,以及解析脚本"native_heapdump_viewer.py"存在问题,heapsnap对heap信息有做了修正;也提供了补丁"android_7_8_9_development_script.patch"修正"native_heapdump_viewer.py"脚本的问题。

LD_PRELOAD环境变量只对当前的shell有效,如果进程是做为service由init启动,需要先stop该进程,然后在shell下启动进程.

一些具有AT_SECURE属性的进程或者环境,它们在link处理过程中会忽略掉LD_PRELOAD参数,即LD_PRELOAD对该类进程或环境不起作用.

使用heapsnap需要root权限.

github snap android,GitHub - albuer/heapsnap: HeapSnap 是一个定位内存泄露的工具,适用于Android平台。...相关推荐

  1. Android C++ Native 内存泄露检查工具Raphael使用介绍

    Android C++ Native 内存泄露检查工具使用介绍 实现原理 使用方法 Raphael添加到测试apk 添加项目依赖 同步gradle 启动泄露检测功能 直接使用boardcast功能控制 ...

  2. Android Studio 选项菜单和动画结合_Android性能测试③-发现和定位内存泄露amp;卡顿...

    Android性能测试③-发现和定位内存泄露&卡顿 Android用户也许会经常碰到以下的问题: 1)应用后台开着,手机很快没电了--应用耗电大: 2)首次/非首次启动应用,进入应用特别慢-- ...

  3. android的内存泄露有几种,Android中几种有可能会导致内存泄露的情况

    8种机械键盘轴体对比 本人程序员,要买一个写代码的键盘,请问红轴和茶轴怎么选? 1.Static静态成员导致的内存泄露 将占用大量内存空间的变量声明为static静态类型.当Activity被销毁的时 ...

  4. android异步加载图片并缓存到内存和sd卡上,Android批量图片加载经典系列——采用二级缓存、异步加载网络图片...

    http://www.cnblogs.com/jerehedu/p/4560119.html 2015-06-08 09:20 by 杰瑞教育, 232 阅读, 1 评论, 收藏, 编辑一.问题描述 ...

  5. Android studio内存泄露分析工具

    使用 Android Studio 检测内存泄漏与解决内存泄漏问题 本文在腾讯技术推文上 修改 发布. http://wetest.qq.com/lab/view/63.html?from=ads_t ...

  6. android内存问题查看工具,哪些Android工具和方法最适合查找内存/资源泄漏?

    如果您只是使用位图背景,那么@hp.android的答案很好,但是,在我的例子中,我有一个BaseAdapter提供一套ImageViewS代表aGridView..我修改了unbindDrawabl ...

  7. DialogInterface内存泄露 anonymous class implements android.content.DialogInterfaces$OnClickListener...

    用Leak Canary工具检测到anonymous class implements android.content.DialogInterfaces$OnClickListener 谷歌之,找到一 ...

  8. 从Handler.post(Runnable r)再一次梳理Android的消息机制(以及handler的内存泄露)

    http://blog.csdn.net/ly502541243/article/details/52062179/

  9. android堆内存解析,heapsnap HeapSnap 是一款针对 Android 进程堆内存进行追踪、定位,以便查出泄露位置的工具 @codeKK c开源站...

    1.HeapSnap 是什么 HeapSnap 是一个定位内存泄露的工具,适用于 Android 平台. 主要特性如下: 对系统负载低 不需要修改目标进程的源代码 支持 Andoroid 上的大多数 ...

最新文章

  1. 数学工具WZgrapher
  2. 串口流控--软件流控与硬件流控
  3. Protocol Buffer基本语法
  4. centos 7 Chrony 集群同步时间
  5. Linux SendMail服务启动慢总结
  6. 安防监控应用成LED企业新盈利点
  7. excel单元格斜线_Excel技巧 | 如何绘制斜线表头
  8. LeetCode 245. 最短单词距离 III
  9. Redis系列-主从复制配置
  10. python 面试题2
  11. 一起谈.NET技术,ASP.NET MVC 3 Beta初体验之超酷的Chart
  12. Vue样式绑定~非常详细哦
  13. LINUX SHELL中for用数组循环
  14. 数字信号处理技术(二)变分模态分解(VMD)-Python代码
  15. Kindle4rss中文rss资源推荐~
  16. 王者荣耀服务器维护多久结束,王者荣耀健康系统重置时间 时间限制规则详解...
  17. 部分mp4视频在ios手机端上无法播放问题
  18. Python爬取网上车市[http://www.cheshi.com/]的数据
  19. 应用概率统计-第一章 随机事件及其概率
  20. 【课后习题】高等数学第七版上第一章 函数与极限 第六节 极限存在准则 两个重要极限

热门文章

  1. 疫情之下的网站优化该怎样进行?
  2. oracle 不查加锁的记录,oracle 锁查询 select加锁方法
  3. qt5编程入门 第2版_2小时入门SparkSQL编程
  4. python爬取图片教程-推荐|Python 爬虫系列教程一爬取批量百度图片
  5. gradle学习(1)hello world
  6. Vim 删除不包含指定字符串的行及统计匹配个数
  7. springboot 应用中静态资源下载
  8. poj1564 Sum It Up dfs水题
  9. H5与Native交互之JSBridge技术
  10. C#字符ASCII码学习经验