ios 打印 详细错误日志_【专家专栏】林相宇 | IOS错误日志抓取和分析

本文介绍了如何使用Xcode和命令行工具获取iOS设备的错误日志,包括第三方App的错误日志,以及如何在无dsym文件的情况下进行日志符号化,便于错误分析。同时,文章解析了错误日志的格式和关键组成部分,为iOS应用的调试和故障排查提供了指导。
摘要由CSDN通过智能技术生成

原标题:【专家专栏】林相宇 | IOS错误日志抓取和分析

在调试自己和别人的IOS App时,发生Crash是非常正常的情况,分析这些Crash的主要手段之一就是分析Crash发生时产生的错误日志。对于未越狱的IOS设备,获取错误日志主要通过Xcode自带的日志获取功能,但是这种方式有以下两点限制:

1.只能获取开发者自己开发的App的日志,无法获取第三方App的日志。

2.自动化工作难度较高(错误日志收集,错误日志整理等)。

文中,笔者首先简单介绍了一下使用Xcode抓取和分析错误日志的方法,然后为了克服上面的两个缺陷,笔者调研了一套可自动化的第三方App在本地测试的错误日志抓取方法。最后,笔者简单介绍了一下IOS错误日志的基本构成,供读者进行日志分析和分类收集参考。

错误日志的获取

使用Xcode获取错误日志

对于自己研发并在测试机上测试的应用,我们可以通过Xcode来分析测试过程中的错误日志。但是App一但发布到AppStore,那么我们如何获取用户在使用过程中产生的错误日志呢?为了解决这一问题,苹果官方提供了一套供App开发者使用的基于Xcode工具的解决方案。

对于App在测试机上运行的情况,Xcode支持获取Apple机器的Log的情况。打开Xcode并打开自己开发的AppProject,在Window->Devices中,找到对应的设备

点击View Device Logs

在此处可以查看设备的日志信息,确认测试机连接到Mac,即可看到已经符号化完成的错误日志

对于在AppStore已经发布的App产生的错误日志,在Window->Organizer中,找到对应的App,在Crashes目录中找到AppStore下载的其他使用者使用过程中产生的错误日志。

使用命令行获取错误日志

苹果官方提供的方案虽然能够成功的获取错误日志,但是有一个前提,那就是用户必须是App的开发者,如果我们需要获取第三方开发者开发的App的错误日志,那么上述方法就不能正确的工作了。适用于这一场景的可行方案之一,是使用libimobiledevice库中的idevicecrashreport命令来获取。

libimobiledevice库:libimobiledevice 是Github上的一个开源库,主要提供和未越狱的苹果IOS设备通信的服务。包括App安装,系统日志获取,设备信息获取和错误日志获取等能力(其他具体的服务能力可以参考libimobiledevice的官网:http://www.libimobiledevice.org/)。

本文具体主要使用idevicecrashreport和ideviceinstaller命令。

假设你获取的第三方App的Ipa已经发布到App Store,那么你可以直接从App Store上下载并测试。如果未发布到App Store,则需要使用ideviceinstaller命令安装该App到指定的手机。具体的command如下:

出现如下日志后安装成功(IOS > 9的设备使用ideviceinstaller会出现Segmentation fault,但是不影响App本身的安装)

然后就可以愉快地测试App了:)

App出现Crash后,ios设备本身保留了CrashReport。为了将设备上的CrashReport拷贝到本机,就需要使用idevicecrashreport命令了。具体的command如下:

如果需要在设备上保留错误日志,使用-k选项;如果需要将crashreport单独存放,使用-e选项。

导出后的文件结构如下所示:

其中wifi为IOS的wifi信息,此处我们并不关心。我们关注其中CrashDemo开头的两个后缀为ips的文件(CrashDemo是我用来测试的App名)。使用Xcode打开一个ips文件。如下所示:

这样我们就成功得到了App的错误日志。

该方法的优点:

可以获取第三方App的错误日志。

方法全部通过命令行方式进行获取,方便编写shell进行自动化获取

该方法的缺点:

无法获得AppStore上使用者相关的错误日志。

错误日志的符号化

我们可以注意到,上述第二种错误日志的获取方法所获取到的日志,日志中的堆栈信息并不像Android等错误日志中的堆栈信息那样打印出了调用的堆栈,而是使用段基址 + 偏移地址的格式显示。除此之外,对于错误信息,也进行了相关的处理。为了能够正确的分析错误,我们需要对这些地址进行符号化,从而将日志翻译成能够处理的信息。一般来说,符号化日志需要开发者提供编译App后生成的dsym文件,该文件包含了App编译后的所有类和函数的地址信息。但是如果我们需要分析第三方开发者的App,那么我们是无法获得该App的dsym文件的。下面给出了无dsym文件场景下符号化日志信息的方法。

不带dsym文件的日志符号化

使用symbolicate符号化错误日志文件

symbolicate:symbolicate是github开源的三方脚本,该脚本使用xcode自带的符号化工具symbolicatecrash进行符号化。symbolicate支持两种符号化的方法。使用App的dsym文件和使用App的ipa解压后的App文件夹。

那么为什么不直接使用xcode的symbolicatecrash命令进行符号化呢?这一点我们可以通过分析symbolicate.sh的源码来了解。

通过分析源码,我们可以看出xcode自带的symbolicatecrash工具的主要缺陷有两点:

1. 工具随着Xcode版本有着比较大的变更。

2. 缺少对错误日志UUID和App有效性的校验。

在我们的场景中,我们没有App的dsym文件,所以我们主要依赖App的ipa解压后的文件夹来进行调试,解压ipa可以使用mac自带的unzip命令

解压后的app目录在appdirpath/Payload目录下,在Finder中显示如下:

symbolicate脚本的使用方法如下:

符号化后的错误日志文件如下:

可以看见,堆栈信息的部分的已经完成了符号化,现在我们可以开始错误日志的分析了。

错误日志的分析

在完成了错误日志的符号化之后,接下来就是对错误日志的分析了,苹果官方提供的错误日志格式还是非常详细的。下面简单介绍错误日志(CrashReport)的基本格式。

CrashReport基本格式

IOS在以下两种情况下会产生错误日志:

1.应用违反操作系统规则。

2.应用中有Bug。

1中“违反操作系统规则“主要包括watchdog终止,用户强制结束和低内存终止三种情况。

2则是应用本身导致的问题。

1和2的日志格式不同,本文主要介绍2的情况下产生的错误日志的基本格式。

下图是一个错误日志的例子

整个错误日志分为进程信息、Crash信息、Crash异常、线程回溯、线程状态和二进制映像6个部分。

进程信息:包括Crash的ID(Incident Identifier),设备的Model和标识符(CrashReporter Key和Hardware Model),App信息(Path、Identifier、Version和CodeType),以及启动的进程信息(Process、ParentProcess)。

Crash信息:包括Crash发生的时间和系统号

Crash异常:包括异常类型(Exception Type)和异常码(Exception Codes)。此处对经常出现的异常码汇总如下(苹果的异常码还是很生动的)

0x8badf00d:(ate bad food)这个异常码表示该异常是由watchdog终止引发的。

0xbad22222:这个异常码表示该异常是由VoIP被过于频繁重启引发的。

0xdeadl0cc:(dead lock)这个异常码表示该异常是由于App长期占用系统资源而被系统强行终止引发的异常。

0xdeadfa11:(dead fail)这个异常码表示该异常是由用户强制终止引发的。

线程回溯信息:

回溯信息包括四列:

帧编号

二进制库的名称

调用方法的地址

第四列分为两个子列,一个基本地址和一个偏移量。

对于未符号化的日志,这一列的内容比较难以理解

对于符号化后的日志,该列内容如下:

分别为该进程调用的函数名称和对应的代码行号

线程状态:Crash中寄存器中的值(不常用,堆栈信息足以完成大部分的Crash分析)

二进制映像:Crash发生时已经载入的二进制文件

以上就是本文的全部内容了,文中涉及到的开源库的Github地址如下:

libimobiledevice: https://github.com/libimobiledevice/libimobiledevice

symbolicate: https://github.com/JohnWong/symbolicate

作者介绍

林相宇

南京邮电大学计算机科学与技术硕士,现在百度平台测试部,主要负责百度MTC产品的IOS移动测试。返回搜狐,查看更多

责任编辑:

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值