https

什么是HTTPS

HTTPS就是在安全的传输层发送HTTP,HTTP + TLS/SSL。

HTTPS,客户端首先打开一条到web服务器端口443的连接,建立了TCP连接,客户端和服务器就会初始化SSL层,对加密参数进行沟通,交换密钥,握手完成后,SSL初始化完成,客户端将请求报文发送给安全层。

用途:

  • 防止窃取,内容加密,浏览器到服务器的内容都是以加密形式传输,中间者无法直接查看原始内容;

  • 防止冒充,配备身份证书,保证用户访问的真实的站点,即使被 DNS 劫持到了第三方站点,也会提醒用户没有访问真实站点,有可能被劫持;

  • 防止篡改,具有校验机制,防止内容被第三方冒充或者篡改。

TLS/SSL

TLS(Transport Layer Security)传输层安全协议。它的前身是SSL(Secure Sockets Layer)安全套接层。基本思路是采用公钥加密法,用于在两个通信应用程序之间提供保密性和数据完整性。该协议由两层组成: TLS 记录协议(TLS Record)和 TLS 握手协议(TLS Handshake)。

常用TLS版本:TLS1.2和TLS1.1(TLS1.0、SSL3.0和SSL2.0已经被证实不安全)。

TLS协议组成

tls_protocol.png

TLS 协议主要有五部分:应用数据层协议,握手协议,报警协议,加密消息确认协议,心跳协议。由 record 协议传输。

TLS握手

tls.png

0 ms:TLS运行在TCP基础之上,这意味着我们必须首先完成TCP 三次握手,这需要一个完整的来回交互(RTT)。

56 ms:TCP连接建立后,先向服务器发出加密通信的请求(Client Hello请求)

发送内容:

支持的协议版本;
支持的加密列表(比如Rsa);
加密随机数;
其他TLS选项。

84 ms:服务器回应(Server Hello),服务器回应TLS协议版本

回应内容:

一个服务器生成的随机数(用于加密密钥);
确认使用的加密方法;
服务器证书;
其他TLS选项。

112 ms:客户端回应(Client Key Exchange),验证服务器证书通过(否则给予警告)。假设双方协商好一个共同的TLS版本和加密算法,客户端使用服务器提供的证书,生成新的对称密钥,并用服务器的公钥进行加密,并告诉服务器切换到加密通信流程。到现在为止,所有被交换的数据都是以明文方式传输,除了对称密钥外,它采用的是服务器端的公钥加密。

回应内容:

一个随机数。该随机数用服务器公钥加密,防止被窃听;
编码改变通知,表示随后的信息都将用双方商定的加密方法和密钥发送;
客户端握手结束通知,表示客户端的握手阶段已经结束。这一项同时也是前面发送的所有内容的hash值,用来供服务器校验。

140 ms:服务器的最后回应(Server Finish),服务器用自己的私钥解密客户端发过来的对称密钥,并通过验证MAC检查消息的完整性,并返回给客户端一个加密的“Finished”的消息。

回应内容:

编码改变通知,表示随后的信息都将用双方商定的加密方法和密钥发送;
服务器握手结束通知,表示服务器的握手阶段已经结束。这一项同时也是前面发送的所有内容的hash值,用来供客户端校验。

168 ms:客户端采用对称密钥解密消息,并验证MAC,加密隧道建立。

Client                                       Server

ClientHello                -------->
                                              ServerHello
                                             Certificate*
                                       ServerKeyExchange*
                                      CertificateRequest*
                           <--------      ServerHelloDone
Certificate*
ClientKeyExchange
CertificateVerify*
[ChangeCipherSpec]
Finished                   -------->
                                       [ChangeCipherSpec]
                           <--------             Finished
Application Data           <------->     Application Data

TLS加密 Secret Keys

PreMaster secret

PreMaster secret是在客户端使用RSA或者Diffie-Hellman等加密算法生成的。它将用来跟服务端和客户端在Hello阶段产生的随机数结合在一起生成Master secret。

Master secret

Session Secret

RSA 发挥的关键作用就是对 PreMaster secret 进行了加密和解密

tls_encrypt.gif

TLS/SSL的功能实现主要依赖于三类基本算法:散列函数 Hash、对称加密和非对称加密。

TLS延迟

HTTP耗时 = TCP握手

HTTPs耗时 = TCP握手 + TLS/SSL握手

命令行工具curl有一个w参数,可以用来测量TCP握手和SSL握手的具体耗时

curl -w "TCP handshake: %{time_connect}, SSL handshake: %{time_appconnect}\n" -so /dev/null https://www.baidu.com

TCP handshake: 0.021, SSL handshake: 0.076

w参数表示指定输出格式,time_connect变量表示TCP握手的耗时,time_appconnect变量表示SSL握手的耗时

HTTPS对速度的影响:

  1. 协议交互所增加的网络 RTT(round trip time)

  2. 加解密相关的计算耗时

网络耗时

HTTP 首个请求的网络耗时

http_connection.png

HTTPS 首个请求的网络耗时

https_connection.png

计算耗时

1、浏览器计算耗时

  • RSA 证书签名校验,浏览器需要解密签名,计算证书哈希值。如果有多个证书链,浏览器需要校验多个证书。

  • RSA 密钥交换时,需要使用证书公钥加密 premaster。耗时比较小,但如果手机性能比较差,可能也需要 1ms 的时间。

  • ECC 密钥交换时,需要计算椭圆曲线的公私钥。

  • ECC 密钥交换时,需要使用证书公钥解密获取服务端发过来的 ECC 公钥。

  • ECC 密钥交换时,需要根据服务端公钥计算 master key。

  • 应用层数据对称加解密。

  • 应用层数据一致性校验。

2、服务端计算耗时

  • RSA 密钥交换时需要使用证书私钥解密 premaster。这个过程非常消耗性能。

  • ECC 密钥交换时,需要计算椭圆曲线的公私钥。

  • ECC 密钥交换时,需要使用证书私钥加密 ECC 的公钥。

  • ECC 密钥交换时,需要根据浏览器公钥计算共享的 master key。

  • 应用层数据对称加解密。

  • 应用层数据一致性校验。

身份认证

身份认证主要涉及到 PKI 和数字证书。通常来讲 PKI(公钥基础设施)包含如下部分:

  • End entity:终端实体,可以是一个终端硬件或者网站。

  • CA:证书签发机构。

  • RA:证书注册及审核机构。比如审查申请网站或者公司的真实性。

  • CRL issuer:负责证书撤销列表的发布和维护。

  • Repository:负责数字证书及 CRL 内容存储和分发.

CA,Catificate Authority,它的作用就是提供证书(即服务器证书,由域名、公司信息、序列号和签名信息组成)加强服务端和客户端之间信息交互的安全性,以及证书运维相关服务。

HTTPS优化

访问速度优化

(1)Tcp fast open

TCP Fast Open (TFO) is an experimental update to TCP that enables data to be exchanged safely during TCP’s connection handshake。

详细参考:rfc7413

(2)HSTS

将用户 HTTP 请求 302 跳转到 HTTPS

  1. 不安全,302 跳转不仅暴露了用户的访问站点,也很容易被中间者支持。

  2. 降低访问速度,302 跳转不仅需要一个 RTT,浏览器执行跳转也需要执行时间。

HSTS(HTTP Strict Transport Security),Declare that a website is only accessible over a secure connection (HTTPS)。

服务端返回一个 HSTS 的 http header,浏览器获取到 HSTS 头部之后,在一段时间内,不管用户输入www.baidu.com还是http://www.baidu.com,都会默认将请求内部跳转成https://www.baidu.com。

浏览器支持Strict Transport Security

(3)Session resume

复用 session,实现简化握手

Session cache

Session cache 的原理是使用 client hello 中的 session id 查询服务端的 session cache, 如果服务端有对应的缓存,则直接使用已有的 session 信息提前完成握手,称为简化握手。

缺点:

  1. 需要消耗服务端内存来存储 session 内容

  2. nginx,apache 只支持单机多进程间共享缓存,不支持多机间分布式缓存

Session ticket

The ticket is created by a TLS server and sent to a TLS client. The TLS client presents the ticket to the TLS server to resume a session.

Client                                     Server

ClientHello
(SessionTicket extension)   -------->
                                               ServerHello
                           (empty SessionTicket extension)
                                          NewSessionTicket
                                        [ChangeCipherSpec]
                            <--------             Finished
[ChangeCipherSpec]
Finished                    -------->
Application Data            <------->     Application Data

rfc4507

rfc5077

缺点:

  1. 只是 TLS 协议的一个扩展特性,目前的支持率不是很广泛

  2. 需要维护一个全局的 key 来加解密,需要考虑 KEY 的安全性和部署效率

(4)Ocsp stapling

Ocsp 全称在线证书状态检查协议 (rfc6960),用来向 CA 站点查询证书状态,比如是否撤销。通常情况下,浏览器使用 OCSP 协议发起查询请求,CA 返回证书状态内容,然后浏览器接受证书是否可信的状态。

rfc6960

这个过程非常消耗时间,因为 CA 站点有可能在国外,网络不稳定,RTT 也比较大。那有没有办法不直接向 CA 站点请求 OCSP 内容呢?ocsp stapling 就能实现这个功能。

详细介绍参考 RFC6066 第 8 节。简述原理就是浏览器发起 client hello 时会携带一个 certificate status request 的扩展,服务端看到这个扩展后将 OCSP 内容直接返回给浏览器,完成证书状态检查。

由于浏览器不需要直接向 CA 站点查询证书状态,这个功能对访问速度的提升非常明显。

Nginx 目前已经支持这个 ocsp stapling file,只需要配置 ocsp stapling file 的指令就能开启这个功能:

ssl_stapling on;ssl_stapling_file ocsp.staple;

(5)False start

False start 的原理就是在 client_key_exchange 发出时将应用层数据一起发出来,能够节省一个 RTT。

False start 依赖于 PFS(perfect forward secrecy 完美前向加密),而 PFS 又依赖于 DHE 密钥交换系列算法(DHE_RSA, ECDHE_RSA, DHE_DSS, ECDHE_ECDSA),所以尽量优先支持 ECDHE 密钥交换算法实现 false start。

falsestart

(6)使用 SPDY 或者 HTTP2

支持多路复用,能将多个 HTTP 请求在同一个连接上一起发出去

HTTP2协议

HTTPS 计算性能优化

  1. 优先使用 ECC

  2. 使用最新版的 openssl

  3. 硬件加速方案

  4. TLS 远程代理计算

Tools

wiresharp

wiresharp_https.png

chrome devtools security

chrome_devtools_security.png

问题记录

  • 使用TLS1.2版本,需要升级openssl到1.0.1版本

  • curl库需要升级到7.34以上版本

  • PHP编译需要指定curl目录

参考

web64 计算机网络4