Skip to content

深入理解 SSL、TLS 与 HTTPS

1. 核心概念与关系

1.1 课程引言

  • 定位: 选修内容,主要应对面试中可能出现的网络安全原理问题,尤其针对校招。
  • 关联性:
    • 与日常编码(如 Ajax)无直接关系
    • 属于原理层面,与运维和计算机基础知识(网络协议)关系更紧密。
  • 直观区别:
    • HTTP: 浏览器地址栏显示 "不安全"。
    • HTTPS: 浏览器地址栏显示 "一把锁",代表安全。

1.2 协议定义

  • SSL (Secure Sockets Layer): 安全套接字层协议。
  • TLS (Transport Layer Security): 传输层安全性协议。
  • 关系: TLS 是 SSL 的升级版。在讨论中,两者常被视为同一概念。

1.3 HTTPS 的构成

HTTPS 并非一个全新的协议,它的本质是在 HTTP 和 TCP 之间增加了一个安全层。

  • 标准 HTTP 通信模型:
      应用层: HTTP
          |
      传输层: TCP
          |
      网络层: IP
  • HTTPS 通信模型:
      应用层: HTTP
          |
      安全层: SSL/TLS  <-- 新增的安全层
          |
      传输层: TCP
          |
      网络层: IP

核心结论: 理解了 SSL/TLS 的工作原理,就等于理解了 HTTPS 的核心。

2. 为什么需要安全传输?

2.1 问题的根源:明文传输

  • 传输安全: 保护数据在客户端和服务器之间传输的过程中,不被第三方窃取或篡改。
  • 网络路径: 客户端与服务器的通信需经过多个网络节点(如路由器)。
  • 风险: 任何一个中间节点都可能被攻击者(中间人)控制,从而监听或修改传输的明文数据。

2.2 中间人攻击 (Man-in-the-Middle Attack) 示例

  • 场景:
    • 客户端 (邓哥) -> 想发送 "我爱你" -> 服务器 (莫妮卡)
    • 攻击者 (陈哥) 潜伏在中间节点。
  • 攻击过程:
    1. 邓哥发送明文消息 "我爱你"。
    2. 陈哥在中间节点截获该消息。
    3. 陈哥将消息篡改为 "我恨你"。
    4. 陈哥将篡改后的消息转发给莫妮卡。
    5. 莫妮卡收到 "我恨你",并认为是邓哥的真实意图,造成严重后果。

HTTP 协议就是这种无保护的明文传输,请求和响应都可能被中间人截获和篡改(例如,在正常网页中注入弹窗广告)。

3. 安全方案的演进

3.1 方案一:对称加密

  • 原理: 使用同一个密钥进行加密和解密。
  • 优点: 加解密速度快,效率高,适合海量数据通信。
  • 流程设想:
    1. 客户端请求密钥。
    2. 服务器将对称密钥 key1 发送给客户端。
    3. 客户端使用 key1 加密数据后发送。
  • 漏洞:
    1. 在第 2 步中,服务器发送密钥 key1 的过程是明文的。
    2. 中间人陈哥可以直接截获这个密钥 key1
    3. 后续客户端使用 key1 加密的数据,陈哥因为拥有 key1,可以轻松解密、篡改、再加密后发给服务器。
    4. 结论: 对称加密方案失败,因为密钥分发过程不安全。

3.2 方案二:非对称加密

  • 原理: 一对密钥,公钥 (PublicKey) 和私钥 (PrivateKey)。
    • 公钥加密的数据,只有对应的私钥能解密。
    • 私钥加密/签名的数据,对应的公钥能解密/验证。
  • 流程设想 (问题):
    1. 服务器将公钥发给客户端。
    2. 客户端用公钥加密 "我爱你" 并发送。
    3. 服务器用私钥解密,成功收到消息。
    4. 问题出现: 服务器回复 "你是个好人",用什么加密?如果用公钥加密,客户端没有私钥,无法解密

3.3 方案三:非对称加密 + 对称加密 (混合方案)

这是现代 HTTPS 采用的核心思想。

  • 核心思路:

    • 使用非对称加密安全地协商出一个对称加密的密钥。
    • 使用协商好的对称加密密钥来加密后续的所有通信内容。
  • 流程设想:

    1. 服务器将自己的公钥 PublicKey_S 发送给客户端。
    2. 客户端随机生成一个对称加密的密钥 key_symmetric
    3. 客户端使用服务器的公钥 PublicKey_S 来加密这个对称密钥 key_symmetric
    4. 客户端将加密后的对称密钥发送给服务器。
    5. 服务器使用自己的私钥 PrivateKey_S 解密,得到对称密钥 key_symmetric
    6. 至此,双方都拥有了同一个对称密钥 key_symmetric,且该密钥的传输过程是安全的。
    7. 后续所有通信都使用 key_symmetric 进行对称加密。
  • 新的漏洞 (终极问题):

    • 中间人陈哥依然可以在第 1 步动手脚。
    1. 服务器发送公钥 PublicKey_S 时,陈哥截获。
    2. 陈哥自己生成一对新的公私钥PublicKey_CPrivateKey_C
    3. 陈哥将服务器的公钥 PublicKey_S 存起来,然后把自己的公钥 PublicKey_C 发送给客户端。
    4. 客户端毫不知情,以为收到的是服务器的公钥,于是用 PublicKey_C 加密了对称密钥 key_symmetric 并发送。
    5. 陈哥截获后,用自己的私钥 PrivateKey_C 解密,成功获取了对称密钥 key_symmetric
    6. 为了让通信继续,陈哥再用之前保存的服务器公钥 PublicKey_S 加密 key_symmetric,然后发给服务器。
    7. 最终,客户端、服务器都能正常通信,但他们协商出的对称密钥已被陈哥掌握,所有通信内容对他而言都是透明的。

根本原因: 客户端无法验证收到的公钥到底是不是目标服务器的。这就是信任问题

4. 终极解决方案:CA 与数字证书

为了解决信任问题,必须引入一个权威的、所有人都信任的第三方机构。

  • CA (Certificate Authority): 证书颁发机构。一个全球公认的可信实体。

4.1 数字证书 (Digital Certificate)

服务器不再直接发送公钥,而是向 CA 机构申请一个数字证书,然后将证书发给客户端。

  • 申请流程: 服务器生成一对公私钥,然后将公钥和自己的域名、身份信息等提交给 CA。
  • 证书内容:
    • 颁发机构 (Issuer): 是哪个 CA 机构颁发的。
    • 网站域名 (Subject): 该证书是颁发给哪个网站的。
    • 服务器公钥 (Public Key): 服务器的公钥。
    • 有效期 (Validity): 证书的有效时间。
    • 数字签名 (Digital Signature): 证书的防伪关键

4.2 数字签名 (Digital Signature)

  • 生成过程:

    1. CA 使用一种哈希算法,计算出证书主要内容(域名、服务器公钥等)的信息摘要
    2. CA 使用自己的私钥对这个信息摘要进行加密。
    3. 这个加密后的摘要就是数字签名
  • 验证过程 (由浏览器/客户端自动完成):

    1. 浏览器获取到服务器发来的证书。
    2. 浏览器使用同样的哈希算法,计算出证书主要内容的信息摘要 A
    3. 浏览器使用内置在操作系统或浏览器中的 CA 公钥,对证书里的数字签名进行解密,得到信息摘要 B
    4. 对比 AB 是否相等
      • 如果相等: 证明:
        1. 证书内容没有被篡改过(否则摘要 A 会不同)。
        2. 这个证书确实是由该 CA 颁发的(否则无法用 CA 公钥解密签名)。
      • 如果不相等: 证明证书是伪造的或被篡改了,连接不安全。

4.3 最终的安全握手流程 (TLS Handshake)

  1. Client Hello: 客户端向服务器发起请求,并告知自己支持的 TLS 版本、加密算法套件、一个随机数 random_C 等信息。
  2. Server Hello: 服务器选择一套加密算法,返回自己的数字证书和一个随机数 random_S
  3. Client Verification & Key Exchange: a. 验证证书: 客户端验证证书的合法性(见面试题部分)。 b. 获取公钥: 验证通过后,从证书中取出服务器的公钥 PublicKey_S。 c. 生成预主密钥: 客户端生成第三个随机数 pre_master_secret。 d. 加密并发送: 使用服务器的公钥 PublicKey_S 加密 pre_master_secret 后发送给服务器。
  4. Server Decryption: 服务器使用自己的私钥 PrivateKey_S 解密,得到 pre_master_secret
  5. 生成会话密钥: 客户端和服务器同时使用 random_Crandom_Spre_master_secret 这三个随机数,通过约定的算法各自独立计算出最终的会话密钥 (Session Key)
  6. Handshake Finished: 双方互相发送一个 "握手结束" 的消息,该消息会用刚刚生成的会话密钥加密。如果对方能成功解密,说明握手成功。
  7. Secure Communication: 后续所有应用层数据(HTTP 请求/响应)都使用这个会话密钥进行对称加密传输。

此时,中间人陈哥因为没有服务器的私钥,无法解密 pre_master_secret,因此无法计算出会话密钥,只能看到一堆无法破解的加密数据。

5. 面试核心问题

Q1: 什么是中间人攻击?有了 HTTPS 后还能攻击吗?

回答: 中间人攻击 (MITM) 指的是攻击者在通信双方之间插入自己,窃听或篡改信息。HTTPS 的设计目标就是为了防御此类攻击。但理论上,在特定条件下,仍可能存在攻击方式:

  1. SSL 劫持攻击 (SSL Hijacking): 攻击者伪造一个服务器的证书(自签名证书)发给客户端。此时客户端的浏览器会弹出严重的安全警告(“您的连接不是私密连接”),提示证书的颁发机构不受信任。如果用户忽略警告并选择继续访问,那么攻击就可能成功。
  2. SSL 剥离攻击 (SSL Stripping): 用户请求 https://example.com,攻击者截获请求后,自己与 https://example.com 建立安全的 HTTPS 连接,但与用户之间建立的是不安全的 HTTP 连接。它将所有 HTTPS 链接替换为 HTTP 链接返回给用户。用户看到的是 HTTP 网站,地址栏没有锁,但可能不会注意到。为了防范此攻击,现代浏览器对 HTTP 网站会明确标记 "不安全"。

Q2: 简述一下 HTTPS (TLS) 的握手过程。

回答: HTTPS 握手过程主要目的是安全地协商出一个用于后续通信的对称密钥。

  1. 客户端问候 (Client Hello): 客户端发送支持的 TLS 版本、加密套件和客户端随机数。
  2. 服务器响应 (Server Hello): 服务器确定加密套件,发送其数字证书和服务器随机数。
  3. 客户端验证与密钥交换:
    • 客户端验证服务器证书的合法性。
    • 验证通过后,生成一个"预主密钥"(Pre-master secret)。
    • 使用证书中的服务器公钥加密这个"预主密钥"并发送给服务器。
  4. 服务器解密与密钥生成:
    • 服务器用自己的私钥解密,得到"预主密钥"。
    • 双方根据三个随机数(客户端随机数、服务器随机数、预主密钥)独立计算出相同的会话密钥。
  5. 握手完成: 双方交换使用会话密钥加密的"握手完成"消息,验证密钥协商成功。之后所有通信都使用该会话密钥进行对称加密。

Q3: 客户端如何验证证书的合法性?

回答: 客户端(浏览器)会执行以下一系列检查:

  1. 信任链验证: 检查证书的颁发机构 (CA) 是否是操作系统或浏览器信任的根 CA。它会沿着证书链一直向上追溯,直到找到一个可信的根证书。
  2. 有效期验证: 检查当前系统时间是否在证书的有效期之内。
  3. 吊销状态验证: 通过在线证书状态协议 (OCSP) 或证书吊销列表 (CRL) 查询该证书是否已被颁发机构吊销。
  4. 域名验证: 检查证书上记录的域名是否与当前正在访问的网站域名一致。
  5. 签名验证: 使用 CA 的公钥解密证书的数字签名,并与自己计算的证书信息摘要进行对比,确保证书未被篡改。

Q4: 为什么需要 CA 机构对证书进行签名?

回答: 核心是为了解决信任问题。如果没有权威的 CA 签名:

  • 任何人都可以自己生成证书,这使得客户端无法分辨一个证书的真伪。
  • 中间人可以轻易地用自己的假证书替换掉服务器的真证书,客户端无法察觉,导致 HTTPS 失去意义。 CA 作为一个受信任的第三方,它的签名就相当于一个权威的担保,向客户端保证:“这个证书里的公钥确实属于这个域名,你们可以放心使用它进行加密通信。”