Android-NDK编译APK中native死机调试
来源:互联网 发布:叮当猫网络什么意思 编辑:程序博客网 时间:2024/05/14 14:12
Android java程序在异常之前还打印出代码调用栈,让程序员有迹可寻,结合单步调试,定位问题相对容易些。
请看一断死机的logcat 打印,你能否找到死机哪个函数呢?而这就是我们需要解决的问题
I/DEBUG ( 669): *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** ***
I/DEBUG ( 669): Build fingerprint: 'generic/generic/generic:2.3.1/GRH78/eng.root.20120613.153206:eng/test-keys'
I/DEBUG ( 669): pid: 1140, tid: 1150 >>> com.ipanel.portal <<<
I/DEBUG ( 669): signal 11 (SIGSEGV), code 1 (SEGV_MAPERR), fault addr 00241000
I/DEBUG ( 669): r0 00241000 r1 00000000 r2 000da324 r3 00000000
I/DEBUG ( 669): r4 00000000 r5 00000000 r6 00000000 r7 00000000
I/DEBUG ( 669): r8 00000280 r9 8484e2d8 10 000001e0 fp 0012d184
I/DEBUG ( 669): ip 00000000 sp 48af05e8 lr 00000000 pc afd1195c cpsr 20000010
I/DEBUG ( 669): #00 pc 0001195c /system/lib/libc.so
I/DEBUG ( 669): #01 pc 00301874 /data/data/com.ipanel.portal/lib/libportal_jni.so
I/DEBUG ( 669): #02 pc 00301874 /data/data/com.ipanel.portal/lib/libportal_jni.so
I/DEBUG ( 669): #03 pc 00301874 /data/data/com.ipanel.portal/lib/libportal_jni.so
I/DEBUG ( 669): #04 pc 00301874 /data/data/com.ipanel.portal/lib/libportal_jni.so
I/DEBUG ( 669): #05 pc 00301874 /data/data/com.ipanel.portal/lib/libportal_jni.so
从NDK r5b开始,增加了调试的支持,引入了ndk-gdb脚本,可以单步调试程序。
而NDK r6给我们带来了一个惊喜,那就是ndk-stack工具,其作用就是将上面的栈打印翻译成我们能懂的描述。
下面就看看ndk-stack是如何使用的吧。
首先,要求动态链接库带调试信息,如果是用的ndk-build编译native代码,在$PROJECT_PATH/obj/local/<ab>下就有,<ab>代表设备的ABI(比如,缺省就是armeabi)。如果是用的cmake编译native代码,需要将CMAKE_BUILD_TYPE定义成Debug,判断是否编译了带调试信息的版本,可以检查最后的编译命令有没有带-g参数。
编译出的so通常位于$PROJECT_PATH/libs/<ab>下。
接下来输入如下命令,指定带调式符号的so所在的路径(用$SYMBOL_SO_PATH指代):
adb logcat | ndk-stack –sym $SYMBOL_SO_PATH
ARM平台调式命令:
a、将C:\NDK\android-ndk-r6b添加到windows的path环境变量中
b、adb connect ip(xx.xx.xx.xx)
c、adb logcat > 1.log
d、cat 1.log | ndk-stack -sym $(project_loc)\obj\local\armeabi
输出:
D:\hisi-tools\sdk-tools>cat 1.log | ndk-stack -sym E:\svnhome\apptv\r23-jilin\p
ackages\iPanel30Portal\obj\local\armeabi
********** Crash dump: **********
Build fingerprint: 'generic/generic/generic:2.3.1/GRH78/eng.root.20120613.153206
:eng/test-keys'
pid: 1140, tid: 1150 >>> com.ipanel.portal <<<
signal 11 (SIGSEGV), code 1 (SEGV_MAPERR), fault addr 00241000
Stack frame #00 pc 0001195c /system/lib/libc.so
Stack frame #01 pc 00301874 /data/data/com.ipanel.portal/lib/libportal_jni.so:
Routine ipanel_nvram_task_burn in ../../src/sdk/jilin_2011/proj-sdk/include/../
lib_ffs/ffs_task.c:416
Stack frame #02 pc 00301874 /data/data/com.ipanel.portal/lib/libportal_jni.so:
Routine ipanel_nvram_task_burn in ../../src/sdk/jilin_2011/proj-sdk/include/../
lib_ffs/ffs_task.c:416
ok,即可定位程序崩溃的位置
对于mips平台来说,使用的命令稍微有些不同,只能使用mipsxx-address2linx工具
ARM平台路径:
C:\NDK\android-ndk-r6b\toolchains\arm-linux-androideabi-4.4.3\prebuilt\windows\bin
调试命令:
$:cat 1.log | C:\NDK\android-ndk-r6b\toolchains\arm-linux-androideabi-4.4.3\prebuilt\windows\bin\arm-linux-androideabi-addr2line.exe -e E:\svnhome\apptv\r23-jilin\packages\iPanel30Portal\obj\local\armeabi\libportal_jni.so 00301874
输出结果:
/usr/local/ipanel_rcc2/build/sdk/../../src/sdk/jilin_2011/proj-sdk/include/../li
b_mem/memx_custom.c:83
与利用ndk-stack有所不同,不过都能定位于具体的文件及行数
MIPS平台:
C:\NDK\android-ndk-r8-windows\toolchains\mipsel-linux-android-4.4.3\prebuilt\windows\bin
调试命令:
$:cat 1.log | C:\NDK\android-ndk-r8-windows\toolchains\mipsel-linux-android-4.4.3\prebuilt\windows\bin\mipsel-linux-android-addr2line.exe [address]
基本上与ARM同样的方式调试
利用address2line的注意点:
I'm using NDK r5, so the executable I'm using is located at $NDK/toolchains/arm-linux-androideabi-4.4.3/prebuilt/linux-x86/bin
; make sure that is in your $PATH
. The command to use looks like
arm-linux-androideabi-addr2line -C -f -e obj/local/armeabi/libXXX.so <address>
Or, for the case above:
arm-linux-androideabi-addr2line -C -f -e obj/local/armeabi/libnativemaprender.so 0003deb4
Note:
- The -C flag is to demangle C++ code
- Use the .so file under obj/local/armeabi, since this is the non-stripped version
如果大家还有更好的调试方法,请也提供下给给受苦调试android死机的同学们一个“脱难”的方法。
- Android- NDK编译APK中native死机调试
- Android-NDK编译APK中native死机调试
- 使用ndk-gdb调试android native程序
- Android Studio 调试 Native 、NDK,C
- 使用GDB调试Android NDK native程序
- Android+NDK+CDT+eclipse+OPenGL ES的编译与native调试
- NDK编程:Android.mk编译APK范例
- Android studio 中调用ndk-build 进行编译native 层直接编译
- android 死机调试
- android如何使用ndk-gdb调试native程序
- Android NDK入门(三)-- native代码的调试方法
- 使用GDB调试Android NDK native(C/C++)程序
- 使用GDB调试Android NDK native(C/C++)程序
- 使用GDB调试Android NDK native(C/C++)程序
- 使用GDB调试Android NDK native(C/C++)程序
- Android NDK学习--编译和调试(Ubuntu+Eclipse+NDK)
- react native编译需要android ndk版本问题
- 用ndk-gdb调试Native
- WEBGL 2D游戏引擎研发系列 第五章 <操作显示对象>
- Extjs框架的封装
- JQuery拖拽元素改变大小尺寸实现代码
- jmeter 脚本增强(检查点、集合点)
- 修改tomcat项目的图标
- Android-NDK编译APK中native死机调试
- 杉树资本面试
- 【Cocos2d-x游戏引擎开发笔记(23)】多线程以及线程同步
- 刘恺威熬夜筹备婚礼 心情比杨幂还紧张
- C指针
- 有关WebSphere MQ消息通道管理的几点技巧
- 在VC中使用WebBrowser控件的两方法
- EIAC.SSO接入接口文档
- 【Java】Hashmap不能用基本的数据类型 Dimensions expected after this token