Deep Understanding of iOS Crash Log

531 阅读3分钟

什么是崩溃

  • 崩溃是指当程序执行一些不被允许的行为时,发生的异常退出现象

崩溃怎么产生的

  • 程序会在执行无意义计算时发生崩溃,比如除以 0
  • 应用在启动阶段耗时超过 20s 时会发生崩溃,因为在 Apple 的 看门狗 机制下,启动阶段耗时过长,应用会被系统强制关闭,并在崩溃日志中标记本次崩溃原因:0x8badf00d
    Exception Type:  EXC_CRASH (SIGKILL)
    Exception Codes: 0x0000000000000000, 0x0000000000000000
    Exception Note:  EXC_CORPSE_NOTIFY
    Termination Reason: Namespace SPRINGBOARD, Code 0x8badf00d
    
  • 应用使用的内存超过了系统限制时,就会发生 OOM(Out-Of-Memory 超出内存限制),触发 Jetsam 机制强制关闭应用。Jetsam 机制是 iOS 操作系统中,为了防止内存资源滥用而衍生出的一套机制,当应用过度占用内存空间时,会被系统强制关闭,并生成一份格式为 JSON,前缀为 JetsamEvent 的文件保存在手机本地。由于内存不足而引起的系统强杀,大多数情况无法记录堆栈信息,大多数第三方也只能简单的采集次数。实际想要调试的话,还是得靠真机导出报告进行分析。
  • 当程序访问数组越界,以及错误操作野指针等等,都会产生崩溃

Analyzing crash logs

  • 基本环境信息 - 崩溃发生时间、应用进程号、版本号以及运行设备的硬件信息等等
  • 崩溃原因信息 - 崩溃类型、错误码、异常标记、终止原因与描述

16468812780293.jpg 16468813986773.jpg

  • 堆栈信息 - 保留了程序终止时,每个线程的堆栈信息

16468814834878.jpg

  • 终止时应用二进制信息:应用程序的可执行文件和用到的库 16468815465035.jpg

16469816554814.jpg

Exception Type

Mach异常描述
EXC_BAD_ACCESS错误内存访问访问“错误”内存地址。“错误”可能指“地址不存在”或者“应用没有权限访问”。因此通常与 SIGBUS 及 SIGSEGV 相关联
EXC_CRASH异常跳出通常与 SIGABRT 相关联,意思是由于检测到代码抛出的未捕获异常而使应用程序异常退出
EXC_BREAKPOINT跟踪/断点捕获通用与 SIGTRAP 相关联。可以由你自己的代码或者 NSExceptions 抛出时触发
EXC_GUARD违反了受保护资源的防护(Violated Guarded Resource Protection)由违背受保护资源防护触发,例如‘某些文件描述符’
EXC_BAD_INSTRUCTION非法指令通常与特定非法或未定义指令/操作数相关
EXC_RESOURCE资源限制应用由于达到资源消耗限制而退出
00000020十六进制异常类型非 'OS Kernel' 异常
  • EXC_BAD_INSTRUCTION (SIGILL)

    • That means the CPU was trying to execute an instruction that does not exist or is invalid for some reason and that’s why the process died
    • 这意味着CPU试图执行一条不存在或因某种原因无效的指令,这就是进程死亡的原因
  • Exception Type: EXC_CRASH (SIGKILL)

    • Watchdog events :Watchdog 定时器超时
    • Device overheated :设备过热
    • Memory exhaustion : 内存超出
    • Invalid code signature :无效签名
  • Memory errors: EXC_BAD_ACCESS (SIGSEGV)

    • Writing to memory that is read-only:写入只读存储器

    • Reading from memory that does not exist at all: 从根本不存在的内存中读取(读取释放后的对象)

如何进行crash日志符号化

  • crash日志符号化通常是通过 atos 和 symbolicatecrash 这两个工具来完成

atos

  • atos 是苹果提供的符号化工具,在Mac OS系统下默认安装,他的缺点是只能一个地址一个地址逐个翻译
  • 使用方法
atos -arch <Binary Architecture> -o <Path to dSYM file>/Contents/Resources/DWARF/<binary image name> -l <load address> <address to symbolicate>  

需要传入这几个信息:arch 架构、dSYM路径、binary image 载入内存的初始地址、崩溃的地址

16469123059160.jpg

symbolicatecrash

  • symbolicatecrash 是 Xcode 自带的一个程序,他是对 atos 的封装,可以翻译整个crash文件
symbolicatecrash AwesomeDemo.crash -d AwesomeDemo.App.dSYM > result.log

参考

programmer.ink/think/deep-…

medium.com/@jjuou2/und…

www.xuyanlan.com/2020/04/12/…

tech.youzan.com/you-zan-cra…