利用中间人解密HTTPS数据

一、HTTPS协议

HTTPS协议网上有很多介绍的文章,这里引用http://www.cnblogs.com/zhuqil/archive/2012/07/23/2604572.html(作者:朱祁林 出处:http://zhuqil.cnblogs.com 本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。)的内容。

HTTPS其实是有两部分组成:HTTP + SSL / TLS,也就是在HTTP上又加了一层处理加密信息的模块。服务端和客户端的信息传输都会通过TLS进行加密,所以传输的数据都是加密后的数据。具体是如何进行加密,解密,验证的,且看下图。

wKioL1Y5VFrCjuPkAAH76JlcMpU211.jpg

图一 HTTPS协议会话过程

1. 客户端发起HTTPS请求

这个没什么好说的,就是用户在浏览器里输入一个https网址,然后连接到server的443端口。

2. 服务端的配置

采用HTTPS协议的服务器必须要有一套数字证书,可以自己制作,也可以向组织申请。区别就是自己颁发的证书需要客户端验证通过,才可以继续访问,而使用受信任的公司申请的证书则不会弹出提示页面(startssl就是个不错的选择,有1年的免费服务)。这套证书其实就是一对公钥和私钥。如果对公钥和私钥不太理解,可以想象成一把钥匙和一个锁头,只是全世界只有你一个人有这把钥匙,你可以把锁头给别人,别人可以用这个锁把重要的东西锁起来,然后发给你,因为只有你一个人有这把钥匙,所以只有你才能看到被这把锁锁起来的东西。

3. 传送证书

这个证书其实就是公钥,只是包含了很多信息,如证书的颁发机构,过期时间等等。

4. 客户端解析证书

这部分工作是有客户端的TLS来完成的,首先会验证公钥是否有效,比如颁发机构,过期时间等等,如果发现异常,则会弹出一个警告框,提示证书存在问题。如果证书没有问题,那么就生成一个随即值。然后用证书对该随机值进行加密。就好像上面说的,把随机值用锁头锁起来,这样除非有钥匙,不然看不到被锁住的内容。

5. 传送加密信息

这部分传送的是用证书加密后的随机值,目的就是让服务端得到这个随机值,以后客户端和服务端的通信就可以通过这个随机值来进行加密解密了。

6. 服务段解密信息

服务端用私钥解密后,得到了客户端传过来的随机值(私钥),然后把内容通过该值进行对称加密。所谓对称加密就是,将信息和私钥通过某种算法混合在一起,这样除非知道私钥,不然无法获取内容,而正好客户端和服务端都知道这个私钥,所以只要加密算法够彪悍,私钥够复杂,数据就够安全。

7. 传输加密后的信息

这部分信息是服务段用私钥加密后的信息,可以在客户端被还原

8. 客户端解密信息

客户端用之前生成的私钥解密服务段传过来的信息,于是获取了解密后的内容。整个过程第三方即使监听到了数据,也束手无策。

二、HTTPS中间人思路

wKioL1Y5VM6CeCy2AAKzte4z14o841.jpg

图二  HTTPS的中间人模型


将Attacker插入到客户端和服务器的通信链路上,对客户端扮演服务器角色,对服务器扮演客户端角色。如上图所示,前面5个步骤和正常的HTTPS通信一致,后面的过程解释如下:

1、图一中第6步的crypt content with key,在图二的第6步中并没有,因为Attacker并没有真正的内容提供给Client,它需要扮演客户端角色从Server获取内容后再发送给Client;

2、7-12是一个正常的HTTPS请求过程(可参考图一),其会话密钥是key1;

3、第13步用key1 Decrypt之后得到明文的Response内容,并用key0对其加密后发送给Client;

4、第14步Client用key0解密Response内容,得到请求返回的内容。

三、解密SSL数据

由图二可知,对于Attacker来说,它有会话密钥key0和key1,可以利用key0解密得到Client与Attacker之间的HTTPS数据,也利用key1解密得到Attacker与Server之间的HTTPS数据,两者效果一样。

四、实现

假设Client为Windows操作系统,Server为www.server.com(IP:xxx.xxx.xxx.xxx),Attacker运行Linux操作系统。

1、DNS欺骗

本文不介绍DNS欺骗技术,而是利用hosts文件进行域名重定向来达到测试的目的。在C:\WINDOWS\system32\drivers\etc\hosts文件中添加

xxx.xxx.xxx.xxx    www.server.com

通过修改hosts文件,Client访问www.server.com就会被重定向到Attacker,Attacker再负责访问真正的www.server.com。

2、伪造证书

cert.sh www.server.com

cat sslcerts/www.server.com-cert.pem sslcerts/private/www.server.com.pem > ps.pem

第一个命令是根据www.server.com的证书伪造一个证书,当然,伪造的证书并没有经过任何CA机构的签名。第二个命令则把伪证书的公钥和私钥合并到一个文件中,以备后用。

3、构造通通

stunnel -p ps.pem -d 443 -r 8080

stunnel -c -d 8080 -r www.server.com:443

Stunnel是一个自由的跨平台软件,用于提供全局的TLS/SSL服务,具体用法请自行查阅文档。第一条命令在本地监听443端口,提供TLS/SSL服务,并将数据转发到本地的8080端口;第二条命令在本地监听8080端口,接收上一个stunnel进程发送过来的数据,然后把数据转发到www.server.com的443端口,从www.server.com:443回来的数据也可以转发到8080端口,并转交给第一个stunnel进程。

4、解密数据

第三小节提到,stunnel有会话密钥key0、key1,可解密数据,因此对于stunnel,可以看到明文的HTTPS数据。但是现在我们不想修改stunnel,我们不在stunnel的进程空间中,因此访问不到key0、key1以及明文数据。不过Attacker有伪证书对应的私钥,可以利用该私钥解密Client发送过来的密钥密文,得到密钥key0,进而解密HTTPS数据。具体做法如下:

①在Attacker机器上运行wireshark,点击Edit→Preferences→Protocols→SSL,然后点击RSA keys list右边的Edit,然后输入Attacker的ip地址,443端口,http协议以及ps.pem的文件路径。

②wireshark开始嗅探数据,如果有Client访问Server,wireshark就会嗅到数据,并利用刚才输入的私钥信息解密会话密钥,进而解密会话数据。


说明:正如前文提到的那样,伪造的证书并没有经过CA机构签名,因此客户端浏览器认为证书并不可信,会进行警告。只有用户忽略浏览器警告,后续的解密流程才得以继续。


参考:

[1] http://www.webos-internals.org/wiki/Decrypt_SSL_%28trusted_man-in-the-middle_technique%29