针对苹果证书申请签名记一下自己的看法,有错误或遗漏的地方请指出。
一.目的
苹果为什么要采取如此复杂的证书签名机制
对盗版软件做到一定的控制,大部分主流操作系统(Windows/Mac/Linux)对运行在自己平台上的软件都得不到很好的管理,随便哪里下载都能用。苹果希望对自己的平台有一定的控制权,在ios系统上运行的软件都需要得到自己的允许。苹果最近对使用热更新的部分软件给予了警告,说明苹果在控制权方面是丝毫不想让步的。(同意你的软件安装在ios系统,而且你的每次更新或者改变,人家也要知道,也要人家同意。)
二.概念了解
对称加密:
对原始的可逆变换。如 abcd变成defg,字母表顺移三位,密钥就是3(当然这是简单举例,实际应用中进行了相当复杂的位运算),通讯两端知道密钥3就可以进行加解密。优点加解密速度快,对服务器压力小。缺点在于其中一端制定了加密密钥,怎么传送到另一端。只要经过网络就有可能被拦截,攻击者知道了密钥,你的加密就毫无意义。是不是要对密钥再一次加密,那生成密钥还是存在上述问题,除非你骑马送过去。怎么解决,往下看。
非对称加密(基于公钥的加密):
生成两份密钥,分别是公钥和私钥,公钥加密私钥解密,私钥加密公钥揭秘(实际应用中公钥用来加密,私钥多用来签名认证),私钥自己保存,公钥散发出去,解决了对称加密中密钥的安全传输问题。
数字签名:
在要传送的数据后面加上一段信息(给数据签名),证明信息没有被修改过。简要描述:对数据做hash计算,得到一个hash值,这个过程不可逆(不能通过hash值得到原数据,代表算法MD5)。将签名和数据一起加密发送出去,对方接到数据后用自己的的密钥解开,拿出数据和签名(上文中提到的hash值),将数据用同样的hash算法处理,若得到同样的签名。则证明数据没有被修改过,反正则被修改,主要用非对称加密的方式来实现。这里有个前提,hash算法要保证不同的内容一定会得到不同的hash值。
三.签名机制(图文流程)
有了上面的概念我们来一步步学习苹果是如何用签名加密来实现对ios控制的
问题一.苹果要让发布在appStore的App都得到自己官方的认证许可
简单解决思路:苹果官方生成一对公私钥,私钥由苹果后台保存,公钥内置在每台ios系统内。在上传app到appstore时,苹果对每个app都用私钥数字签名。iOS系统装入app的时候会用公钥解密验证,这样就能保证app是苹果同意安装的(假设私钥是不会外泄的,只有苹果才知道,不然这事没发往下说了。当然也不可能外泄)。其实上面的思路已能够解决让苹果很大程度上控制app和ios系统。
问题二.如何让开发者使用真机调试
以上的解决思路确实能保证从appstore下载装入iOS系统的app是苹果官方允许的,但对于开发者来说要用真机调试啊,不能用模拟器开发完直接上appstore吧。这时候怎么把app装入真机ios系统,如何对调试过程进行控制。
解决思路:在app每次真机编译完成之后传送到苹果后台,后台私钥对其进行签名,然后装机调试。这确实是一个办法,但频繁的调试每次都要后台交互签名。单就网络问题苹果和开发者都不会接受的。
所以苹果给出了现行的方法,证书签名(双层签名方法)。以上比较好理解,以下会分条说明并带着截图。
1.从本地申请一对密钥,见图1图2。你可以看到本地钥匙串已经生成一对密钥(下文简称公钥P,私钥P,图3),本地也生成了一个certSigningRequest(证书签名请求)文件,暂且理解为本地生成的公钥P文件。
2.证书请求文件已准备好了,还是通过最基本流程截图展示证书请求过程,当然后面也会解释原理。
进入苹果开发者网站,注册了付费的开发者账号才能看到如下页面
选择申请一个证书,下以开发证书为例
选择继续,这里需要上传我们本地生成的公钥P文件
选择downlaod,下载证书文件到本地。也可以回到图5处下载生成的证书文件。
如下图证书文件
至此我们已经把证书请求下来了。解释一下此过程苹果做了什么,为什么说控制了开发者的安装行为
接上 3. 见图7图8 我们把我们本地生成的公钥P传到了苹果后台,苹果后台有一对固定密钥,这同上面appstore提到的签名密钥一样(下文简称公钥Q,私钥Q),苹果用私钥Q对我们上传的公钥P进行了加密数字签名。生成了如图9所示的证书文件。简单理解这个文件包含了公钥P及私钥Q对其的数字签名。
4.我们把下载的证书双击安装然后配置到xcdoe里边如图10,在我们开发时,编译完一个app时本地的私钥P会对此app进行数字签名,同时会把上面配置的证书文件一起打包进app里,过程见图。便可装到手机上(其实大部分还是不可以的,因为描述文件问题,后面解释)。通过以下的原理解释你先明白苹果怎么通过证书控制调试安装行为。
原理解释:a.在安装的时候,iOS系统取出app 内的证书,通过ios系统内置的公钥Q(上文提到过的内置公钥)去验证证书的数字签名是否正确,在这一步验证什么呢,验证了证书是没有被修改过的,也就保证了内含的公钥P是苹果认证过的。b. 然后再用公钥P对app(私钥P签名过的)进行验证,这个过程就间接验证了此安装行为是否经过苹果的允许。这里可能有点绕,对不太理解的小伙伴在补充一下。我们通过内置私钥Q验证了公钥的P的可靠性(这跟appstrore验证原理相同),如此一来只要可以被公钥P认证通过的app也就是安全的。这样的app就只能是私钥P签名过的了(因为它们是一对么,我是安全的,你加密签名过的也就是安全的了)。
问题二.如何控制开发者权限的滥用
至此苹果解决了开发者的问题,给予了开发者通过证书真机安装App的权限。但是问题貌似又回到了原点,你开发者把这样的app丢出去,大家又可以肆无忌惮下载了,还绕过了appstrore。又可能被滥用了,瞎搞了一通,是不是。人苹果爸爸手段多得很,来两个限制。
1·.让签名只能针对某个(有人说通配符,应该是某些,这些细节先忽略)具体的app,意思就是你要在后台注册你的AppID。
2,对可以安装设备数量也进行限制100个(企业证书?细节先不要在意,后面解释),要把这100个设备的设备号也要后台注册。
有了上面两条,开发者也逃不出苹果的手心了。怎么解决,照常理,在生成证书文件的时候把这两个限制条件一块加进去,把本地公钥P,注册的appID和设备号一块签名加密,生成一个证书下载供开发者使用,可能变得有点复杂。如果只有这两项限制是完全行可行的。但是ApplePay/push/iCould这些苹果都想控制,你也需要申请,人家还要把信息加在里证书里边。着实不好扩展,于是苹果将它们分开,搞了另一个东西叫Provisioning Profile(描述文件),就是把你的证书,注册的appId和设备ID搞一块在用私钥Q进行签名。,搞完之后出现了一个mobileprovision这样的文件,我们下载到本地。以下图文展示
注册appid,下边有选项里有可以使用通配符
注册设备号,可以添加100个,每年可更新
给描述文件添加信息 此处添加appID
选择证书
选择设备
以上我们已经准备好描述文件,苹果正是用它来控制开发者对app的滥用。
如此一来又会多出两条步骤,希望你没有晕,解释一下它是怎么工作的。首先配好证书,把你下载的描述文件也双击安装,在xcode里也把它配好见图19。其他过程不变,在编译本地签完名之后会把这个描述文件也一块打包进app。安装的时候通过系统内置的公钥Q,去验证mobileprovision数字签名,当然证书也会在验一遍。确保mobileprovision注册的信息都是苹果授权的。然后取出mobileprovision的数据列表做各种匹配验证,包括用上面提到的用公钥P验证app签名,验证当前设备的设备ID是否在此ID列表上,appid是否对应的上,各种权限开关等等。
其他问题解释:
企业证书:此类证书是不需要配置设备号ID的,数量不限。但是不能发不到appstore
p12文件:上文我们提到了本地的公私钥,它就是用我这台mac生成的,那如果其他Mac也要调试,对app签名的话,我们就导出私钥(p12)文件给别台mac,把证书和描述文件一块拷贝过去,搞定