1.tombstone日志

带有符号表的so库放在:

out/target/product/msmnile_gvmq/obj/SHARED_LIBRARIES/_intermediates/LINKED

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
#00 pc 00000000003bce1c  /system/lib64/libbluetooth.so (bluetooth::Uuid::ToString() const+12)
#01 pc 0000000000180388 /system/lib64/libbluetooth.so (checkIOSDevice(unsigned int, bluetooth::Uuid*) [clone .cfi]+136)
#02 pc 000000000018442c /system/lib64/libbluetooth.so (btif_dm_search_services_evt(unsigned short, char*) [clone .cfi]+1388)
#03 pc 000000000017cfbc /system/lib64/libbluetooth.so (bt_jni_msg_ready(void*) [clone .cfi]+136)
#04 pc 0000000000096908 /system/lib64/libchrome.so (base::debug::TaskAnnotator::RunTask(char const*, base::PendingTask*)+248)
#05 pc 00000000000afd14 /system/lib64/libchrome.so (base::MessageLoop::RunTask(base::PendingTask*)+416)
#06 pc 00000000000affbc /system/lib64/libchrome.so (base::MessageLoop::DeferOrRunPendingTask(base::PendingTask)+52)
#07 pc 00000000000b03f8 /system/lib64/libchrome.so (base::MessageLoop::DoWork()+380)
#08 pc 00000000000b1790 /system/lib64/libchrome.so (base::MessagePumpDefault::Run(base::MessagePump::Delegate*)+180)
#09 pc 00000000000afa08 /system/lib64/libchrome.so (base::MessageLoop::RunHandler()+112)
#10 pc 00000000000cc60c /system/lib64/libchrome.so (base::RunLoop::Run()+136)
#11 pc 000000000017d54c /system/lib64/libbluetooth.so (run_message_loop(void*) [clone .cfi]+348)
#12 pc 00000000002b6164 /system/lib64/libbluetooth.so (work_queue_read_cb(void*) [clone .cfi]+120)
#13 pc 00000000002b460c /system/lib64/libbluetooth.so (run_reactor(reactor_t*, int) [clone .cfi]+416)
#14 pc 00000000002b4440 /system/lib64/libbluetooth.so (reactor_start(reactor_t*) [clone .cfi]+84)
#15 pc 00000000002b5f14 /system/lib64/libbluetooth.so (run_thread(void*) [clone .cfi]+188)
#16 pc 00000000000819b4 /system/lib64/libc.so (__pthread_start(void*)+36)
#17 pc 0000000000023478 /system/lib64/libc.so (__start_thread+68)

2.分析工具概要介绍

  • addr2line:用来分析单个pc地址对应的源码行数,比如示例log中的第13行中的#00 pc 00000000003bce1c,00000000003bce1c就是crash时pc调用的堆栈地址,用这个地址就可以分析出对应在源码中的行数;
  • objdump:用来把相应的so变成汇编语言的asm文件,然后根据地址信息(比如00000000003bce1c)就可以找到更加详细的相关函数信息;
  • ndk-stack:用来把log信息全部翻译成更加详细的带源码行数信息的log,相当于是在整个crash堆栈信息都执行addr2line命令。

3.使用方法

3.1 addr2line
1
2
3
jieou@gxatek-fw-no:/work/jieou/gxa_code/lagvm_p/LINUX/android$ ./prebuilts/gcc/linux-x86/aarch64/aarch64-linux-android-4.9/bin/aarch64-linux-android-addr2line -C -f -e libbluetooth.so 3bce1c
bluetooth::Uuid::ToString() const
system/bt/types/bluetooth/uuid.cc:169
3.2 objdump
1
2
3
./prebuilts/gcc/linux-x86/aarch64/aarch64-linux-android-4.9/bin/aarch64-linux-androidkernel-objdump -S libbluetooth.so > libbluetooth.asm
# 或者
./prebuilts/gcc/linux-x86/aarch64/aarch64-linux-android-4.9/bin/aarch64-linux-androidkernel-objdump -d libbluetooth.so > libbluetooth.txt
3.3 ndk-stack
1
2
# 在Android根目录
jieou@gxatek-fw-no:/work/jieou/gxa_code/lagvm_p/LINUX/android$ ndk-stack -sym out/target/product/msmnile_gvmq/obj/SHARED_LIBRARIES -dump out/target/product/msmnile_gvmq/obj/SHARED_LIBRARIES/libbluetooth_intermediates/LINKED/tombstone_00.txt > 1.txt

4.分析过程

  • 拿着tombstone文件首先找到带有符号表so库
  • 使用addr2line对一个或者多个地址进行输出调用栈行数和文件名字
  • 对着代码查看错误逻辑或者是否附近有错误log打出
  • 如果没有log日志,使用objdump反编译so库,然后查看对应地址的寄存器操作情况

5.其他工具

5.1 debuggrep

触发debuggerd进行相应的dump操作,其中参数-b表示在控制台中输出backtrace,参数tid表示的是需要dump的进程或者线程id。

通过debuggerd -b [pid],可输出Native进程的调用栈,这些信息是通过解析/proc/[pid]/maps而来的。

1
debuggrep -b pid/tid
5.2 调用栈

查看调用栈

1
cat /proc/pid/stack
5.3 打印trace文件
1
2
3
4
adb shell
echo 1 > /d/tracing/tracing_on
echo 1 > /d/tracing/events/binder/enable
cat /d/tracing/trace_pipe

参考文档

  1. 《ndk_stack_log.txt》
  2. 《libbluetooth.asm》
  3. 《debuggerd守护进程》