iOS逆向 -- 应用重签名学习 (实战总结)
<h2 id="一前言"><strong>一、前言</strong></h2><p>在日常正向开发打包提交时,我们都会对应用进行签名,然后上传到App Store。其中签名的这个过程 XCode 已经帮我们做过了,我们只需要配置好证书和描述文件就可以。但是如果我们希望学习其他的应用,进行一些逆向开发,就需要调试其他的应用,而我们首先就需要对这些应用进行重签名。</p>
<h2 id="二ios双层签名机制"><strong>二、iOS双层签名机制</strong></h2>
<h3 id="21加密方式了解"><strong>2.1、加密方式了解</strong></h3>
<p>首先,我们先了解下iOS签名中用到的加密方式,RSA & Hash。</p>
<blockquote>
<p><strong>RSA加密:</strong>一种非对称加密方式,也叫现代加密(区别与传统的对称加密)。这种方式的加密会生成一对公私钥,如果公钥加密,则用私钥解密,反之亦然。一般情况下,我们自己会保存私钥。</p>
</blockquote>
<blockquote>
<p><strong>对称加密:</strong>通信的两端事先约定好一个密钥,使用密钥对明文进行加密,生成密文的加密方式。这种加密方式的特点是,加密效率高(相对于非对称加密),但一旦密钥泄漏,则安全隐患较大。</p>
</blockquote>
<blockquote>
<p><strong>Hash:</strong>把任意长度的输入通过哈希算法变换成固定长度的输出,得到的结果是128位二进制,即32位16进制字符。Hash的特点是对于相同的数据会得到相同的结果,不同的数据一般会有不同结果(hash冲突除外)。因此,可以作为一种信息摘要,或者信息“指纹”,用来做数据识别。</p>
</blockquote>
<blockquote>
<p><strong>作为一个开发者,有一个学习的氛围跟一个交流圈子特别重要,这是一个我的iOS交流群:834688868,不管你是大牛还是小白都欢迎入驻 ,分享BAT,阿里面试题、面试经验,讨论技术, 大家一起交流学习成长!</strong></p>
</blockquote>
<p>如果你正在面试,或者正准备跳槽,不妨看看我精心总结的面试资料: BAT 大厂最新面试题+答案合集(持续更新中) 来获取一份详细的大厂面试资料为你的跳槽加薪多一份保障</p>
<h3 id="22app-store应用签名验证"><strong>2.2、App Store应用签名验证</strong></h3>
<p>苹果为了保证安全性,除了对iOS系统做了很多安全的设计外,对于应用的验证及安装渠道的控制也做了很多事情。例如,一个应用如何从App Store下载到安装到手机上,会经历下面几个步骤:</p>
<ul>
<li>
<p>1、苹果会生成一对公私钥,私钥苹果自己保存,公钥内置在iOS设备中</p>
</li>
<li>
<p>2、苹果对应用进行对称加密和签名,并用私钥对签名信息进行加密</p>
</li>
</ul>
<p>上诉两个步骤在App上架完成前就会完成,以下步骤是下载到手机后发生的</p>
<ul>
<li>
<p>3、应用下载到手机后,iOS系统使用公钥对签名信息验证,如果通过则安装到手机</p>
</li>
<li>
<p>4、在每次应用运行时,对应用进行解密操作</p>
</li>
</ul>
<h3 id="23调试安装的签名验证"><strong>2.3、调试安装的签名验证</strong></h3>
<p>以上是从App Store下载应用的验证过程,但我们平时开发过程中的应用安装并非从App Store下载,也没有私钥进行加密,苹果会如何进行验证的呢?首先我们可以看下苹果的需求:</p>
<ul>
<li>
<p>1、不需要从AppStore下载也可以安装</p>
</li>
<li>
<p>2、为了保证系统的安全性,App的安装不能脱离苹果的控制,需要经过苹果允许才可以安装,且不能导致非开发的App被安装</p>
</li>
</ul>
<p>为了实现这一目的,苹果引入了一个双层签名的机制,大致流程如下图:<img src="https://upload-images.jianshu.io/upload_images/17161430-fabc38d69206a6a4?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<p>双层签名流程<strong>整理下来步骤如下</strong></p>
<ul>
<li>
<p>1、在 Mac 上生成一对公私钥,记为 公钥M 和 私钥M;将包含 公钥M 的CSR文件上传到苹果服务器</p>
</li>
<li>
<p>2、苹果对 公钥M 做一次Hash签名,使用 公钥A 对签名信息进行一次加密,生成一个包含 公钥M 和 签名信息的证书</p>
</li>
<li>
<p>3、为了实现控制安装设备数量等需求,苹果生成一个包含证书、App ID、设备信息的描述文件,并返回给Mac电脑</p>
</li>
<li>
<p>4、在使用XCode打包过程中,使用先对应用包进行一次签名,再使用 私钥M 对签名信息进行一次加密</p>
</li>
<li>
<p>5、将应用包、加密签名及描述文件打包成安装包,发送到iOS设备,进行图中的第4步操作</p>
</li>
</ul>
<h2 id="三ios应用重签名"><strong>三、iOS应用重签名</strong></h2>
<h3 id="31-应用重签原理"><strong>3.1 应用重签原理</strong></h3>
<blockquote>
<p>iOS应用重签名:是指对一个应用重新进行签名,使其运行在我们的工程中。</p>
</blockquote>
<p>通过上一节关于应用签名原理的介绍,我们发现如果将待签名应用的描述文件替换成我们的描述文件,并使用我们的证书对其再进行一次签名,就可以使得iOS系统认为这是我们自己的工程安装的应用,从而可以对其他应用进行分析与调试。</p>
<h3 id="32-应用重签名步骤"><strong>3.2 应用重签名步骤</strong></h3>
<p>我们以微信 7.0.8 的安装包为例进行重签。</p>
<h4 id="321-前提"><strong>3.2.1 前提</strong></h4>
<p>进行应用重签时,需要注意必须使用已经脱壳的应用进行,否则会签名失败。我们可以使用otool命令查看应用是否加壳</p>
<blockquote>
<p>otool -l 应用可执行文件名称</p>
</blockquote>
<p><img src="https://upload-images.jianshu.io/upload_images/17161430-523b435b2fb12fac?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<p>如图所示,cryptid 值为0,表示应用已经脱壳,如果值为1,则表示应用未脱壳。</p>
<blockquote>
<p>壳:如2.2节所诉,苹果会对应用可执行文件及资源文件等进行加密,俗称加壳。如果想要重签调试应用,则先要解密,这个过程称为脱壳。</p>
</blockquote>
<h4 id="322-应用重签">3.2.2 应用重签</h4>
<ul>
<li>1、我们需要先创建一个自己的工程,并运行到手机上,运行的目的是将我们的描述文件安装到手机上;同时在Product的应用包中找到我们的描述文件</li>
</ul>
<p><img src="https://upload-images.jianshu.io/upload_images/17161430-7768514bf5b70073?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<ul>
<li>2、将脱壳的 WeChat 安装包中的plugin、Watch删除,因为普通的证书无法签名plugin和Watch,删除对重签微信应用也不影响。</li>
</ul>
<p><img src="https://upload-images.jianshu.io/upload_images/17161430-8623a319a3942983?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<p><img src="https://upload-images.jianshu.io/upload_images/17161430-47a3a3e4f9cd18a0?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<ul>
<li>3、对Frameworks进行重签,微信中包含6个Framework,需要一一进行签名,下图是 WeChat 7.0.8的Framework结构</li>
</ul>
<p><img src="https://upload-images.jianshu.io/upload_images/17161430-3ed7d12402850a05?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<p>如果使用的WeChat 8.0.2版本,其Framework结构如下图,其中的库文件也均需要重签名<img src="https://upload-images.jianshu.io/upload_images/17161430-76caca73dedd594e?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<p>首先使用 security 命令查看电脑上的证书,找到我们自己的证书</p>
<blockquote>
<p>security find-identity -v -p codesigning</p>
</blockquote>
<p><img src="https://upload-images.jianshu.io/upload_images/17161430-f12a114635d89692?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<p>使用codesign命令进行farmework的重签名(如果是微信8.0.2版本,会有很多dylib的swift库,这些也需要重签,命令与下文一致)</p>
<blockquote>
<p>codesign -fs "证书名" 待签文件</p>
</blockquote>
<p><img src="https://upload-images.jianshu.io/upload_images/17161430-620316cd068a619f?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<ul>
<li>4、接下来需要进行描述文件的替换,找到第一步保存的描述文件,放在 WeChat 的app包内。(如果待签的app包中包含描述文件,直接替换;微信中没有该文件,将我们的描述文件放入即可)。</li>
</ul>
<p><img src="https://upload-images.jianshu.io/upload_images/17161430-0e5b1f51794b00a2?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<ul>
<li>
<p>5、找到微信的 info.plist 文件,修改bundleId 为我们新建的工程的bundleId</p>
</li>
<li>
<p>6、查看描述文件,找到授权信息</p>
</li>
</ul>
<p>使用如下命令查看描述文件信息</p>
<blockquote>
<p>security cms -Di embedded.mobileprovision (embedded.mobileprovision为描述文件名称)</p>
</blockquote>
<p><img src="https://upload-images.jianshu.io/upload_images/17161430-5b0f929105652ad4?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<p>拷贝 Entitlements 标签下的 dict标签对信息(保存了应用的授权信息),并保存到一个plist文件中<img src="https://upload-images.jianshu.io/upload_images/17161430-0765d3183860fc25?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<p>此处为了方便在工程中新建了一个plist文件,也可以在其它地方新建。坑点:注意图中红色标记处可能为 R45LY736NP.*,需要手动将 * 替换成自己的 bundleId(这里替换为 ResignDemo),否则会后续在替换包时会失败,导致无法安装</p>
<ul>
<li>7、将微信app包与上一步对plist文件放在一个文件夹下,使用如下命令对应用包进行重签</li>
</ul>
<blockquote>
<p>codesign -fs "证书" --no-strict --entitlement=plist文件名 xxx.app</p>
</blockquote>
<p><img src="https://upload-images.jianshu.io/upload_images/17161430-ce8d7cf5531e0684?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<p>出现上图的 replacing existing signature 表示重签成功。</p>
<ul>
<li>8、运行工程,将重签的微信安装包替换我们自己的工程的app包</li>
</ul>
<p><img src="https://upload-images.jianshu.io/upload_images/17161430-85519afcd13de2a7?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<p>如图点击 加号,选择刚刚重签的微信app包,将ResignDemo工程的app包替换成如图所示即可。</p>
<ul>
<li>9、此时手机的ResignDemo会被替换成微信,包括图标和名称都后替换,在XCode -- Debug -- Attach to process中找到最新WeChat进程,选中后将微信进程附加到 ResignDemo工程上,附加成功后即可进行View Debug,如图所示</li>
</ul>
<p><img src="https://upload-images.jianshu.io/upload_images/17161430-375e3b0b2b8e6c18?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<p><img src="https://upload-images.jianshu.io/upload_images/17161430-69e3bbce4b467a36?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240"></p>
<h2 id="四总结"><strong>四、总结</strong></h2>
<p>本次以微信为例进行了一次重签名实践,总结下主要步骤如下:</p>
<blockquote>
<p>1.删除插件和带有插件的.app包(比如Watch)</p>
</blockquote>
<blockquote>
<p>2.对Frameworks里面的库进行重签名</p>
</blockquote>
<blockquote>
<p>3.给可执行文件 +x(可执行)权限(一般不需要,如果没有执行权限时,使用 chmod +x 文件名称 添加权限)</p>
</blockquote>
<blockquote>
<p>4.添加描述文件(新建工程,真机编译得到)</p>
</blockquote>
<blockquote>
<p>5.替换BundleID</p>
</blockquote>
<blockquote>
<p>6.通过授权文件(Entilements)重签.app包</p>
</blockquote>
<p>以上就是总结的关于应用重签名的实践知识,如果有不正确的或者理解不到位的地方,欢迎大家指正🙏</p>
<p>作者 | 奔跑的不将就</p><br><br>
来源:https://www.cnblogs.com/iOSer1122/p/14952299.html
頁:
[1]