Skip to content

HTTPS 握手到底在握什么

提示本文发布于 4 个月前,其中信息可能已经时过境迁...

以前面试被问到 HTTPS 握手过程,我都是背那几步:Client Hello、Server Hello、证书验证、密钥交换……背是背得下来,但总觉得差点意思。直到最近认真把笔记重新整理了一遍,才真正把"为什么这么麻烦"这件事想通了。

核心就一句话

非对称加密协商,对称加密通信。

用最复杂、最安全的手段(非对称),去商量出一个最简单、最快的密钥(对称),然后剩下的海量数据都用这个快密钥传输。

握手过程,像一场精心策划的接头

第一步:打招呼 + 索要证件

浏览器对服务器说:"你好,我想建立 HTTPS 连接。这是我支持的加密算法列表,还有一个随机数 A。"

第二步:亮出证件

服务器回应:"好的,这是我选定的加密算法,这是我的数字证书(里面有公钥),还有一个随机数 B。"

第三步:验明正身

浏览器拿到证书后做三件事:

  1. 查户口——是不是正规 CA 机构签发的
  2. 看日期——证书有没有过期
  3. 核对域名——这张证书是不是给这个网站发的

验证通过,浏览器就确信:这个公钥确实属于这个服务器。

第四步:生成预备密钥

浏览器再生成一个随机数 C,用服务器的公钥加密后发过去。

第五步:生成会话密钥

浏览器有 A、B、C,服务器也有 A、B、C(用私钥解密拿到 C),双方用同样的算法算出同一个"会话密钥"。

第六步:确认

双方用会话密钥加密一条消息告诉对方:"我准备好了。"

一个常见的疑问

我以前一直想不通:黑客截获了 A、B、公钥,甚至截获了加密后的 C,为什么还算不出会话密钥?

后来才明白,关键点在于:黑客没有私钥。

浏览器用公钥加密 C,就像把 C 装进一个透明的防弹玻璃盒子里,挂了一把只有服务器才有钥匙的锁。黑客能看到盒子,知道里面是 C,甚至知道是哪把锁,但打不开。

没有 C,就凑不齐三个随机数,就算不出会话密钥。

两种密钥交换方式

面试常说的是 RSA 方式——浏览器直接用公钥加密 C 发过去。但现代更常用的是 ECDHE,它多了一个"完美前向安全"的特性:即使私钥泄露,之前的通信记录也无法被解密。

ECDHE 的原理有点像颜色混合——双方各拿一种秘密颜色,混合公共颜色后交换,再各自混合对方的颜色,最终得到相同的第三种颜色。整个过程没有直接传输那个秘密数字,但双方能在本地算出完全一样的结果。

总结

HTTPS 握手的本质就是:用非对称加密安全地传递一个秘密,然后双方用这个秘密生成对称密钥,之后的所有通信都用这个对称密钥加密。

想通了这个逻辑,再去记那几步流程,就顺多了。