Files
knowledge-kit/Chapter1 - iOS/1.76.md
2020-04-06 22:35:27 +08:00

61 lines
3.6 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# iOS Crash分析
> 目前在重构 APM,在做测试的时候有这样一个需求,分析线上环境的 top10 Crash, APM SDK 的提测 Demo 工程中需要有模拟能力并全链路分析是否可以在 Demo 工程中生成 Crash -> 上报组件上报 -> 服务端符号化. 在查询目前 App 的 top 10 Crash 的时候发现系统层面的 Crash 还是无法符号化成功. 虽然这不重要,但是还是想探讨下如何可以解析这种系统层面的 Crash 信息.
## 背景
APM 监控到 Crash,然后线程回溯拿到堆栈信息,再调用上报组件的能力,上报组件按照一定的策略去上报数据,服务端符号化解析堆栈信息.为了方便查看拿 stack_trace_id 去查询堆栈信息.接口信息如下图
![接口堆栈信息](https://raw.githubusercontent.com/FantasticLBP/knowledge-kit/master/assets/2019-10-10-APM_Stack_trace_api.png)
拿到堆栈信息里面的 json 本地保存成拓展名为 ***.crash** 文件,Mac 可以打开拓展名为 crash 的文件. 然后根据 **Crashed Thread** 后面的数字去查找对应的 Thread 里面的信息
![Crash 信息](https://raw.githubusercontent.com/FantasticLBP/knowledge-kit/master/assets/2019-10-10-APM_Crash.png)
结果发现是系统层级的信息,看不懂
```Shell
Thread 12 Crashed:
0 libsystem_platform.dylib 0x00000001c34a87e8 0x1c34a2000 + 26600 (<redacted> + 16)
1 Foundation 0x00000001c42fe698 0x1c41ea000 + 1132184 (<redacted> + 52)
2 Foundation 0x00000001c42091fc 0x1c41ea000 + 127484 (<redacted> + 1744)
3 Foundation 0x00000001c4208af4 0x1c41ea000 + 125684 (<redacted> + 1232)
4 Foundation 0x00000001c42fecec 0x1c41ea000 + 1133804 (<redacted> + 272)
5 libdispatch.dylib 0x00000001c32d8a38 0x1c3279000 + 391736 (<redacted> + 24)
6 libdispatch.dylib 0x00000001c32d97d4 0x1c3279000 + 395220 (<redacted> + 16)
7 libdispatch.dylib 0x00000001c32b0c34 0x1c3279000 + 228404 (<redacted> + 404)
8 libdispatch.dylib 0x00000001c32b0314 0x1c3279000 + 226068 (<redacted> + 592)
9 libdispatch.dylib 0x00000001c32bc9d4 0x1c3279000 + 276948 (<redacted> + 340)
10 libdispatch.dylib 0x00000001c32bd248 0x1c3279000 + 279112 (<redacted> + 116)
11 libsystem_pthread.dylib 0x00000001c34b91b4 0x1c34ad000 + 49588 (_pthread_wqthread + 464)
```
为了搞懂这种 Crash,这篇文章就诞生了.
## crash 后的 backtrace 符号化
iOS 的奔溃日志结合 dsym 文件可以找到奔溃时的 backtrace这是解决奔溃的关键线索。如果是同一台 Mac 进行打包,导入 crash log 会自动将 backtrace 进行符号化,这样我们就可以看到类名、文件名、方法名和行号。
如果打包不是在同一台 Macxcode 找不到对应的符号表backtrace 是不会被解析成功的。
```
Last Exception Backtrace:
0 CoreFoundation 0x2cb535f2 __exceptionPreprocess + 122
1 libobjc.A.dylib 0x3a3c5c72 objc_exception_throw + 34
2 CoreFoundation 0x2ca67152 -[__NSArrayM objectAtIndex:] + 226
3 myapp 0x004fe736 0x9b000 + 4601654
4 myapp 0x00507ed4 0x9b000 + 4640468
5 myapp 0x004fd112 0x9b000 + 4595986
6 myapp 0x003275c6 0x9b000 + 2672070
```
方法:将 crash 对应的包比如 Test.app 文件和 crash 文件放在一个文件夹下。执行下面命令
```shell
atos -arch arm64 Test.app/Test -l 0x9b000 0x004fe736
```
其中:
arch 后代表指令架构集第一个数字取backtrace的要解析的行的第4列第二个数字取第3列, 就会得到对应的方法名,文件名,行号.