遇到iOS Crash,该如何分析?

一、背景说明

众所周知,Android App在机型兼容覆盖上面临非常大的挑战,一个根本原因就是由于Android生态的开放性,市场上充斥着数量巨大的各类Android设备,无法在浩如烟海的机型上做适配。

反观iOS生态,尽管整体上iOS App质量明显优于Android应用,但是从阿里云测移动质量中心的统计数据来看,依然有30%左右的iOS App存在崩溃、运行卡顿等严峻问题。iOS开发者依然需要花大力气通过各种测试手段发现这些隐藏问题,并逐一进行修复。

本文从解决iOS App崩溃的角度出发,分析了一份标准的iOS应用程序的Crash报告,iOS开发者可以通过这边文章掌握基本的崩溃分析方法。

二、如何分析iOS
Crash

      一份标准的iOS应用程序的Crash报告,通常由以下6个部分组成:

      1. 报告头(Header)

报告头包含了应用程序以其运行环境的一些基本信息,下面是报告头的一个例子。

Incident Identifier: E6EBC860-0222-4B82-BF7A-2B1C26BE1E85
CrashReporter Key: 6196484647b3431a9bc2833c19422539549f3dbe
Hardware Model: iPhone6,1
Process: TheElements [4637]
Path: /private/var/mobile/Containers/Bundle/Application/5A9E4FC2-D03B-4E19-9A91-104A0D0C1D44/TheElements.app/TheElements
Identifier: com.example.apple-samplecode.TheElements
Version: 1.12
Code Type: ARM (Native)
Parent Process: launchd [1]
 
Date/Time: 2015-04-06 09:14:08.775 -0700
Launch Time: 2015-04-06 09:14:08.597 -0700
OS Version: iOS 8.1.3 (12B466)
Report Version: 105

 

       2. 异常代码(Exception
Codes)

异常代码可能包含异常类型(Exception Type)、异常子类型(Exception Subtype)、处理器的详细异常代码(processor-specific
Exception Codes)和其它能提供更多Crash信息的字段,最后一个字段列出了触发Crash的线程索引。下面是异常代码的示例。

Exception Type: EXC_CRASH (SIGABRT)
Exception Codes: 0x0000000000000000, 0x0000000000000000
Triggered by Thread: 0

常见的异常类型有以下几种。

 

        a. Bad Memory Access [EXC_BAD_ACCESS // SIGSEGV // SIGBUS]

    此类型的Excpetion是最常见的Crash,通常由访问了无效的内存导致。

    SIGSEGV:访问了无效地址,没有物理内存对应该地址,通常由于重复释放对象导致。

    SIGBUS:总线错误,与 SIGSEGV 不同的是,SIGBUS
访问的是有效地址,但总线访问异常,通常是访问了未对齐的数据。

    SEGV:代表无效内存地址,比如空指针、未初始化指针、栈溢出等。

 

        b. Abnormal Exit [EXC_CRASH // SIGABRT]

     进程异常退出,造成Crash通常是因为未捕获到Objective-C/C++的异常。

     SIGABRT:收到Abort信号退出,通常Foundation库中的容器为了保护状态正常会做一些检测,例如插入nil到数组中等会遇到此类错误。

 

         c. 其它异常类型

     有些异常类型没有被命名,以16进制数字表示。

     0xbaaaaaad:意味着该Crash log并非一个真正的Crash,它仅仅只是包含了整个系统某一时刻的运行状态,由用户同时按Home键和音量键触发。

     0xbad22222:当VoIP程序在后台太过频繁的激活时,系统可能会终止此类程序。

     0x8badf00d:程序启动或者恢复时间过长被watch dog终止。

     0xc00010ff:程序执行大量耗费CPU和GPU的运算,导致设备过热,触发系统过热保护被系统终止。

     0xdead10cc:程序退到后台时还占用系统资源(如通讯录)被系统终止。

     0xdeadfa11:程序无响应用户强制退出。当用户长按电源键,直到屏幕出现关机确认画面后再长按Home键,将强制退出应用。我们可以合理认为用户这么做的原因是应用程序没有响应。

 

       3. 应用详情(Application
Specific Information)

有些Crash出现时,会产生额外的信息,这些信息能帮助用户更好地了解应用程序终止时的运行环境。示例如下。

Application Specific Information:
MyApp[134] was suspended with locked system files:
/private/var/mobile/Library/AddressBook/AddressBook.sqlitedb

 

       4. 回溯(Backtrace)

这部分列出了发生Crash时线程的调用栈。示例如下。

Thread 0 name: Dispatch queue: com.apple.main-thread
Thread 0 Crashed:
0   TheElements               0x0000000100063fdc -[AtomicElementViewController myTransitionDidStop:finished:context:] (AtomicElementViewController.m:201)
1   UIKit                     0x000000018ca5c2ec -[UIViewAnimationState sendDelegateAnimationDidStop:finished:] + 184
2   UIKit                     0x000000018ca5c1f4 -[UIViewAnimationState animationDidStop:finished:] + 100
3   QuartzCore                0x000000018c380f60 CA::Layer::run_animation_callbacks(void*) + 292
4   libdispatch.dylib         0x0000000198fb9368 _dispatch_client_callout + 12
5   libdispatch.dylib         0x0000000198fbd97c _dispatch_main_queue_callback_4CF + 928
6   CoreFoundation            0x000000018822dfa0 __CFRUNLOOP_IS_SERVICING_THE_MAIN_DISPATCH_QUEUE__ + 8
7   CoreFoundation            0x000000018822c048 __CFRunLoopRun + 1488
8   CoreFoundation            0x00000001881590a0 CFRunLoopRunSpecific + 392
9   GraphicsServices          0x00000001912fb5a0 GSEventRunModal + 164
10  UIKit                     0x000000018ca8aaa0 UIApplicationMain + 1484
11  TheElements               0x000000010005d800 main (main.m:55)
12  libdyld.dylib             0x0000000198fe2a04 start + 0
 
Thread 1 name: Dispatch queue: com.apple.libdispatch-manager
Thread 1:
0   libsystem_kernel.dylib    0x00000001990e0c94 kevent64 + 8
1   libdispatch.dylib         0x0000000198fc897c _dispatch_mgr_invoke + 272
2   libdispatch.dylib         0x0000000198fbb3b0 _dispatch_mgr_thread + 48
 
...

 

       5. 线程状态(Thread
State)

这部分列出了发生Crash的线程的状态,即寄存器和寄存器的值。示例如下。

Thread 0 crashed with ARM Thread State (64-bit):
    x0: 0x0000000000000000   x1: 0x0000000000000000   x2: 0x0000000000000000   x3: 0x00000001995f8020
    x4: 0x0000000000000000   x5: 0x0000000000000001   x6: 0x0000000000000000   x7: 0x0000000000000000
    x8: 0x0000000000000000   x9: 0x0000000000000015  x10: 0x0000000199601df0  x11: 0x0000000b0000000f
   x12: 0x00000001741e8700  x13: 0x000001a5995f5779  x14: 0x0000000000000000  x15: 0x0000000044000000
   x16: 0x00000001989724d8  x17: 0x0000000188176370  x18: 0x0000000000000000  x19: 0x00000001701dda60
   x20: 0x0000000000000001  x21: 0x0000000136606e20  x22: 0x00000001000f6238  x23: 0x0000000000000000
   x24: 0x000000019cc640a8  x25: 0x0000000000000020  x26: 0x0000000000000000  x27: 0x0000000000000000
   x28: 0x000000019cc577c0  fp: 0x000000016fd1a8d0   lr: 0x00000001000effcc
    sp: 0x000000016fd1a860   pc: 0x00000001000effdc cpsr: 0x60000000

 

       6. 二进制映像(Binary Images)

这部分列出了当Crash发生时被装载进进程内存空间的依赖库或者模块。示例如下。

Binary Images:
0x100058000 - 0x10006bfff TheElements arm64 <77b672e2b9f53b0f95adbc4f68cb80d6> /var/mobile/Containers/Bundle/Application/CB86658C-

 

三、结合云上测试报告

       阿里云iOS自动化测试提供的检测报告里提供了详细的Crash日志,iOS开发者可以通过上面的Crash 分析方法快速定位到崩溃原因并加以解决。

       

 

       此外,检测报告里也包含了整个测试过程中的屏幕录像视频,对于崩溃发生的位置、时间都有记录。通过这个回溯视频,对于疑难bug的解决可以提供有效的定位依据,提高bug分析效率。

         

       除iOS自动化测试外,阿里云移动服务还提供针对移动端的全面测试服务,包括Android 自动化测试、H5自动化测试。移动开发者可以点击前往体验试用。

时间: 2024-09-19 09:19:54

遇到iOS Crash,该如何分析?的相关文章

分析iOS Crash文件:符号化iOS Crash文件的3种方法

当你的应用提交到AppStore或者各个渠道之后,请问你多久会拿到crash文件?你如何分析crash文件的呢? 上传crash文件 你的应用应当有模块能够在应用程序crash的时候上传crash信息. 要么通过用户反馈拿到crash文件,要么借助自己或第3方的crash上传模块拿到crash文件. 今天要分析的场景是你拿到用户的.crash文件之后,如何符合化crash文件(Symbolicating crash logs)的3种方法.帮助尽快找到crash原因. crash文件例子 cras

iOS通过dSYM文件分析crash

http://blog.csdn.net/hjy_x/article/details/20929095 重点是dwarfdump --uuid命令 我们在ios开发中会碰到的很多crash问题,如果Debug调试模式的话,我们可以往往很容易的根据log的输出定位到导致crash的原因,但对于已经上线的应用,或者是release环境包导致的crash,我们就需要一些特殊的手段来通过crash log进行分析定位了. 通过参考网上的一些资料,总结了一下,下面介绍一下通过dSYM文件以及crash l

iOS应用的crash日志的分析基础

Outline如何获得crash日志如何解析crash日志如何分析crash日志     1. iOS策略相关     2. 常见错误标识     3. 代码bug 一.如何获得crash日志 当一个iOS应用程序崩溃时,系统会创建一份crash日志保存在设备上.这份crash日志记录着应用程序崩溃时的信息,通常包含着每个执行线程的栈调用信息(低内存闪退日志例外),对于开发人员定位问题很有帮助. 如果设备就在身边,可以连接设备,打开Xcode - Window - Organizer,在左侧面板

代码不方便放-iOS crash的问题解决方向

问题描述 iOS crash的问题解决方向 解决方案 无效的访问,看看是不是指针的问题 解决方案二: 有你对应函数了 在那个函数增加一些信息输出来进一步分析

浅谈iOS Crash(一)

本文讲的是浅谈iOS Crash(一),一.捕获iOS Crash 1.设置异常断点并运行 设置异常断点.png 说明:设置Xcode异常断点后运行程序,发生Crash时,断点会定位到出错的代码行,但仅适用于开发阶段.线上APP的Crash还需要通过收集Crash机制来捕获Crash并记录在日志中. 2.Mach异常 和 Unix信号 iOS Crash发生时,先产生Mach异常(最底层的内核级异常),然后Mach异常在host层被ux_exception转换为相应的Unix信号,并通过thre

Crash日志,分析专用

iOS Crash日志 Understanding Crash Reports on iPhone OS https://developer.apple.com/videos/wwdc/2010/?id=317 http://www.cnblogs.com/smileEvday/p/Crash1.html http://www.cocoachina.com/industry/20130725/6677.html    http://www.cnblogs.com/tiechui/p/382004

浅谈iOS Crash(二)

浅谈iOS Crash(一) 一.僵尸对象(Zombie Objects) 1.概述 僵尸对象:已经被释放掉的对象.一般来说,访问已经释放的对象或向它发消息会引起错误.因为指针指向的内存块认为你无权访问或它无法执行该消息,这时候内核会抛出一个异常( EXC ),表明你不能访问该存储区域(BAD ACCESS).(EXC_BAD_ACCESS类型错误) 调试解决该类问题一般采用NSZombieEnabled(开启僵尸模式). 2.使用NSZombieEnabled Xcode提供的NSZombie

iOS Crash常规跟踪方法及Bugly集成运用详细介绍_IOS

iOS Crash常规跟踪方法及Bugly集成运用 当app出现崩溃, 研发阶段一般可以通过以下方式来跟踪crash信息 #1.模拟器运行, 查看xcode错误日志 #2.真机调试, 查看xcode错误日志 #3.真机运行, 查看device系统日志  下面举例说明, 先写一段会Crash的代码crashdemo: - (void)viewDidLoad { [super viewDidLoad]; // Do any additional setup after loading the vie

[Mac OS/iOS]反汇编工具Hopper分析Crash Log

   在Mac OS下分析Crash Log有很多种方法,这里不是要说明如何分析的Crash Log, 主要是展示下Hopper的使用. 强大的IDA大家可能已经知道,但它的Mac OS版本又让人回到了DOS时代.幸运的是Mac OS有了一个小巧的替代品:Hopper, 基本上满足了工作上的反汇编的需要,包括伪代码以及控制流图(Control Flow Graph),支持ARM指令集并对Objective-C的做了优化.   先给张界面总览(左侧是符号列表,打开程序后,用工具栏最右侧的Read