概念性的东西:代码签名是对可执行文件或脚本进行数字签名.用 来确认软件在签名后未被修改或损坏的措施。和 数字签名原理同样,只不过签名的数据是代码而已。算法
在iOS出来以前,之前的主流操做系统(Mac/Windows)软件随便从哪里下载都能运行,系统安全存在隐患,盗版软件,病 毒入侵,静默安装等等.那么苹果但愿解决这样的问题,要保证每个安装到 iOS 上的 APP 都是通过苹果官方容许的,怎样 保证呢?就是经过代码签名。shell
若是要实现验证.其实最简单的方式就是经过苹果官方生成非对称加密的一对公私钥.在iOS的系统中内置一个公钥,私钥 由苹果后台保存,咱们传APP到AppStore时,苹果后台用私钥对APP数据进行签名,iOS系统下载这个APP后,用公钥验证这个签名, 若签名正确,这个APP确定是由苹果后台认证的,而且没有被修改过,也就达到了苹果的需求:保证安装的每个APP都是通过苹 果官方容许的.安全
若是咱们iOS设备安装APP只从App Store这一个入口这件事就简单解决了,没有任何复杂的东西,一个数字签名搞定. 可是实际上iOS安装APP还有其余渠道.好比对于咱们开发者iOSER而言,咱们是须要在开发APP时直接真机调试的.并且苹 果还开放了企业内部分发的渠道,企业证书签名的APP也是须要顺利安装的. 苹果须要开放这些方式安装APP,这些需求就没法经过简单的代码签名来办到了。
bash
• 通过苹果容许才能够安装服务器
• 不能被滥用致使非开发APP也能被安装微信
因此为了实现这些需求,iOS签名的复杂度也就开始增长,苹果给出的方案,就是双层签名。app
iOS的双层代码签名流程简单梳理,这也不是最终的iOS签名原理.iOS的最终签名在这个基础上还要稍微加 点东西.ide
首先这里有两个角色.一个是iOS系统 还有一个就是咱们的Mac系统.由于iOS的APP开发环境在Mac系统下.因此这 个依赖关系成为了苹果双层签名的基础.工具
一、在Mac系统中生成一对非对称加密算法的公钥和私钥,这里简称公钥M和私钥M。网站
二、苹果本身也有一对固定的公钥A和私钥A,公钥A在每一个手机iOS系统中,而私钥A在苹果后台。
三、在项目打包过程当中,咱们第一件事,就是生成CSR文件,生成文件的时候,电脑会让咱们填入相关开发者信息,这些就是所谓的信息摘要。把CSR文件(包含公钥M以及开发者信息)发送给苹果后台,苹果后台用私钥A去签名公钥M,获得了一份数据包含了公钥M以及其签名,这份数据称为证书,以及会给咱们一份描述文件(经过填写设备ID、AppID、证书等信息获得的(Provisioning profile)。
四、在开发时,编译完一个APP后,用本地的私钥M(其本质就是P12文件)对这个APP进行签名,同时把第三部获得的描述文件及证书一块儿打包进APP里,安装到手机上。
五、在安装时,iOS系统取得证书,经过系统内置的公钥A,去验证证书的数字签名是否正确。
六、验证证书后确保了公钥M是苹果认证过的,再用公钥 M 去验证 APP 的签名,这里就间接验证了这个 APP 安装 行为是否通过苹果官方容许。(这里只验证安装行为,不验证APP 是否被改动,由于开发阶段 APP 内容老是 不断变化的,苹果不须要管。)
若是你仍是不太明白,就仔细看一下下面的流程图。
有了上面的过程,已经能够保证开发者的认证,和程序的安全性了。
描述文件(Provisioning profile)通常包括三样东 西:证书、App ID、设备。当咱们在真机运行或 者打包一个项目的时候,证书用来证实咱们程序 的安全性和合法性。
苹果为了解决应用滥用的问题,因此苹果又加了两个限制. 第一限制在苹果后台注册过的设备才能够安装. 第二限制签名只能针对某一个具体的APP. 而且苹果还想控制App里面的iCloud/PUSH/后台运行/调试器附加这些权限,因此苹果把这些权限开关统一称为 Entitlements(受权文件).并将这个文件放在了一个叫作Provisioning Profile(描述文件)文件中. 描述文件是在AppleDevelop网站建立的(在Xcode中填上AppleID它会代办建立),Xcode运行时会打包进入APP内. 因此咱们使用CSR申请证书时,咱们还要申请一个东西!! 就是描述文件! 在开发时,编译完一个 APP 后,用本地的私钥M对这个APP进行签名,同时把从苹果服务器获得的 Provisioning Profile 文件 打包进APP里,文件名为embedded.mobileprovision,把 APP 安装到手机上.最后系统进行验证。
Xcode提供了签名工具,codesign,咱们经过几个命令就能够完成重签名。平常咱们开发中,签名的过程都是Xcode代替咱们手工完成。
$security find-identity -v -p codesigning //列出钥匙串里可签名的证书
复制代码
$Codesign –fs “证书串” //文件名 强制替换签名
复制代码
$Chmod +x 可执行文件 //给文件添加权限
复制代码
$security cms -D -i ../embedded.mobileprovision //查看描述文件
复制代码
$codesign -fs “证书串” --no-strict --entitlements=权限文件.plist APP包
复制代码
$Zip –ry 输出文件 输入文件 将输入文件压缩为输出文件
复制代码
说在前面的一些注意事项,由于刚开始接触逆向,因此如今pp助手下载越狱的ipa包。越狱的ipa包是非加密包,能够经过几项操做查询到该ipa包是否加密
如下咱们用微信举例:
一、下载越狱版WeChat ipa包,解压后,获得WeChat.app,右键显示包内容,打开iterm2,cd到该目录下。
二、
$ otool -l WeChat | grep cry //otool查询WeChat文件信息,而后管道输出以cry开头的信息.复制代码
cryptid 0 // 1表明加密算法, 0表明未加密复制代码
ps:若是cryptid 1 ,证实app是通过appStore加密处理过的。此加密是对称加密,由于数据量过大,以前咱们说过非对称加密适合小型数据加密。那么何时解密呢?是手机安装的时候对app解密,仍是在运行的时候解密呢?答案是运行的时候解密,因此在appStore上下载的app,咱们每次运行的时候,都会进行解密。
三、在该文件夹下删除插件和带有插件的.app包(Watch\Plugins若是有就删除)
四、在显示包内容文件夹对Frameworks文件夹下的库进行重签名
$ codesign -fs "iPhone Developer:XXX(123A456B)" abc.framework //强制替换签名,这里强调一下,若是存在多个.framework都要依次强制替换签名。复制代码
五、包内容下,有个叫WeChat的可执行文件,该文件图标为白色则是无执行权限,黑色则是有可执行权限。
$ chomd +x 可执行文件 //给文件添加权限复制代码
六、本地新建工程,(必定要是同名工程,避免在包内容文件夹下的可执行文件冲突,同时也是为了方便),这里新建工程是为了获得描述文件,描述文件不可生成,只能去请求,把新建项目在真机跑一遍,保证真机已信任该描述文件。
七、打开该新建工程,打开包内容,复制描述文件,而后粘贴到微信的包内容下
七、替换BundleID,在微信(WeChat.app)的包内容文件夹下找到info.plist文件,替换成新建工程的BundleID。
八、打开新建工程的描述文件、查看描述文件信息
$ cd /复制代码
$ security cms -Di +描述文件复制代码
<key>Entitlements</key>
<dict>
<key>xxxxx</key>
<array>xxxxx</array>
<true/>xxxx
<string>xxxx</string>
</dict>复制代码
复制<dict>下全部内容,而后新建abx.plist文件,粘贴其内容,保证格式正确。
九、经过受权文件(Entilements)重签.app包,注意,上面生成的abx.plist的很重要,描述文件包含其权限文件。
$codesign -fs "iPhone Developer:XXX(123A456B)" --no-strict --entitlements=abx.plist WeChat.app
复制代码
十、回到Xcode新建项目中,command + shift + R,点击+,安装WeChat.app。这时候会提示,是否要替换掉你刚才新建的项目(由于为了让手机信任描述文件,因此咱们以前用真机跑过一次新建项目)。选择替换replace。
十一、至此安装成功。回到Xcode中,点击debug,选择attach to process,找到WeChat。点击。直到Xcode进程栏中显示, Running WeChat on XXiPhone。成功附加,就能够lldb调试了。
说在最后面的话。以上知识点仅是从新签名的原理,往后还会更新利用Xcode快速重签名以及shell脚本重签名。
若是我哪里写的不对,还但愿你能校订出来,咱们共同进步,若是你喜欢此文章,就动一动小手点个赞吧。