Android处理native crash(ndk-stack和addr2line)

1.在线调试crash

1.1查看当前手机的cpu,即abi:

在命令行中执行查看cpu的命令

adb shell
cat /proc/cpuinfo

在这里插入图片描述

当前手机cpu是aarch64 , 即通常是加载arm64-v8a下so库。

1.2通过adb logcat+ndk-stack 解析so库,输出报错的堆栈

格式:

# SYMBOL_SO_PATH为带调试信息的so所在的根目录
adb logcat | ndk-stack -sym SYMBOL_SO_PATH

在命令行中执行:

adb logcat| D:\miniwan\AndroidStudio\sdk\ndk\22.1.7171670\prebuilt\windows-x86_64\bin\ndk-stack -sym C:\Users\hexingen\Desktop\nativeCrash\so

当运行apk,执行到crash时,打印报错堆栈,如下所示:

在这里插入图片描述

根据堆栈,可知crash 发生FUIRichText.cpp的392行。

2.处理crash的日志问题

很多情况下,发生native crash的场景是测试或者线上捕捉,这时就需要根据未strip的so库进行还原堆栈。

2.1通过ndk-stack 解析crash报错文件

格式:ndk-stack -sym 未strip的so库目录 -dump crash文件

# SYMBOL_SO_PATH为带调试信息的so所在的根目录  crash_file_path是发生crash文件的路径
ndk-stack -sym SYMBOL_SO_PATH -dump crash_file_path

特别注意:crash的内容,必须*号开头

*** *** *** *** *** *** *** *** *** *** *** *** *** *** *** ***
2023-02-02 10:17:15.891 26938-26938/? A/DEBUG: Build fingerprint: 'OPPO/PCLM50/OP4AB5:12/RKQ1.211103.002/Q.202211171711:user/release-keys'
//...
2023-02-02 10:17:15.891 26938-26938/? A/DEBUG: signal 6 (SIGABRT), code 0 (SI_USER), fault addr --------
2023-02-02 10:17:15.891 26938-26938/? A/DEBUG: Abort message: 'terminating with uncaught exception of type std::out_of_range: basic_string'
2023-02-02 10:17:15.891 26938-26938/? A/DEBUG:     x0  0000000000000000  x1  0000000000005fb7  x2  0000000000000006  x3  00000073dbaeead0
//....
2023-02-02 10:17:15.892 26938-26938/? A/DEBUG: backtrace:
2023-02-02 10:17:15.892 26938-26938/? A/DEBUG:       #00 pc 00000000000799c8  /apex/com.android.runtime/lib64/bionic/libc.so (abort+168) (BuildId: bbbdeb7c87c74f1491f92c6e605095b0)

当通过命令行执行D:\miniwan\AndroidStudio\sdk\ndk\22.1.7171670\prebuilt\windows-x86_64\bin\ndk-stack -sym C:\Users\hexingen\Desktop\nativeCrash\so -dump C:\Users\hexingen\Desktop\nativeCrash\so\crash.txt后,会解析出如下内容:
在这里插入图片描述

根据堆栈,可知crash 发生FUIRichText.cpp的392行。

2.2通过addr2line解析报错文件

格式:

#addrx 是报错地址 so-file 是报错地址对应的且未strip的so库
addr2line  -f -C -e so-file <addr1> <addr2> ...
  • -e --exe=:指定需要转换地址的可执行文件名
  • -f --functions:在显示文件名、行号输出信息的同时显示函数名信息。
  • -C --demangle[=style]:将低级别的符号名解码为用户级别的名字。

这里需要注意点,addr2line和so库的版本要匹配上。

执行以下命令行:

D:\miniwan\AndroidStudio\sdk\ndk\22.1.7171670\toolchains\aarch64-linux-android-4.9\prebuilt\windows-x86_64\bin\aarch64-linux-android-addr2line.exe -f -C -e C:\Users\hexingen\Desktop\nativeCrash\so\libAppPlayJNI.so  0000000003bdf2f8 0000000003bdf45c 0000000003bdc704 0000000003bdbde8 0000000003bdbd68  000000000123823c 00000000019db7bc 00000000019da848 00000000019da000

解析结果如下所示:

在这里插入图片描述

更多详情阅读介绍addr2line调试命令

猜你喜欢

转载自blog.csdn.net/hexingen/article/details/128899180