大家好,又见面了,我是全栈君。
延迟
定义和标准延迟
延迟简单地说,它是一种转移或信息包从起点到终点,所花费的时间。
延迟=发送延迟 传播延迟 处理延迟 排队延迟:
Propagation delay 传播时延
传播时延这个概念。是指电磁信号或者光信号在传输介质中传输的时延。而在光纤或者铜线中。光信号和电磁信号的传播速度都在20万公里/秒以上,在传输介质中传输的是电磁信号或者光信号,而不是数据!
Transmission delay 传送时延 发送时延是指结点在发送数据时使数据块从结点进入到传输媒体所需的时间,也就是从数据块的第一个比特開始发送算起,到最后一个比特发送完成所需的时间。
发送时延又称为传输时延
Processing delay 处理时延 处理数据包的头部。校对位错误, 并确定数据包要传输的方向
Queuing delay 排队时延 数据包等待处理的时间
总的时延是从client到server全部时延的总各。Propagation 时间是由两者之间的距离和传播的介质(光纤或铜线)决定。
还有一方面。Transmission delay 是由两者建立起来传输链接的传输速率决定的,跟两者之者的距离没有关系。 举例来说, 如果我们分别在1Mb的链接和100Mb的链接,传递一个10Mb的文件。 前者的时间为10秒,而100Mbps时,仅仅需花费0.1秒。
下一步。 当数据包到达一个路由器。 路由器必需检測数据包的头,从而决定下一个路由。 同一时候还须要对数据进行校验, 全部的这些逻辑都是在路由器硬件上完毕。所以Processing delay是很小的, 但它也确时存在。 最后来讲讲Queuing delay. 当数据包从较快的传速速率(光钎)到一个100MB的路由器。这就常过了路由器的处理速度, 那么这个数据包就须要进入到缓存区提排队。 这个排队时间。就是Queuing Delay.
光速与Propagation delay
光速是299, 792, 458米每秒, 但光速在介质中传播会有能量损耗, 这仅仅是一个理论的值。通过下面图表,能够清楚的了解光纤实际的速度和造成的Propagation 延时
路径 | 距离 | 真空光速延时 | 光纤延时 | 光纤信号往返时间 |
---|---|---|---|---|
New York to San Francisco | 4,148 km | 14 ms | 21 ms | 42 ms |
New York to London | 5,585 km | 19 ms | 28 ms | 56 ms |
New York to Sydney(悉尼) | 15,993 km | 53 ms | 80 ms | 160 ms |
绕赤道一周 | 40,075 km | 133.7 ms | 200 ms | 200 ms |
光纤上的传输速度是挺快的, 但从纽约到悉尼还是花费了160毫秒. 这也不过理论上的值(两个城市是直接通过光纤相连), 实际上数据包会经过不同的路径(悉尼到旧金山, 在到纽约等等)。经理的路径越多,就会引入很多其它的处理延时。等待延时, 传输延时。终于RTT(Round-trip time)将达到 200 – 300ms.
通常100-200ms是正常的值, 假设超过了300ms, 那么整个交互就变慢了. 能够使用Content delivery network(CDN), 将server的资料缓存在离client近期的server。 降低两者之者的距离.
构建TCP
互联网由两个重要的协议组成,IP 和 TCP. IP(Internet Protocol) 提供了通信两方之间的路由以及寻址,它仅仅管发送数据。而不保证数据是否完速的传送到了接收端。TCP(Transmission Control Protocal), 提供了在不可靠的通道上。建立一个抽像的可靠网络。
TCP 提供了一个可靠的抽像网络。
它向应用程序隐藏了复杂的网络通信细节: 重发丢失的数据。 按序发送。拥塞控制。 数据的完整性等。 当你使用TCP时。你能够保证发送和接受到的数据是一样的,并且顺序也是一样的。 所以TCP是保证准确传输最佳化的协议。
TCP 并非 HTTP唯一的传送协议。 HTTP也能够建立在用户数据报协议(User Datagram Protocal) 或者 UDP, 也能够选择其他传送协议。 但在实际中, HTTP在互联网的通信都是通过 TCP。
所以理解TCP的核心执行原理,是我们优化web性能的基础知识。
三次握手
全部的TCP都是从三次握手開始。 在client或者server交换随意应用数据之前,它们必须先建立连接,确认数据包的序列号, 以及其他用于连接的特殊变量。 因为安全原因,序列号是从两方中随机挑选。
SYN
client会挑选出一个数字序列号 X, 而且发送一个SYN 数据包(包括额外的TCP 标记和选项)
SYN ACK
server接受到 syn 包, 在序列号X上加1. 而且挑选一个序列号Y, 并附上它自己的标记和选项。 并响应这个数据包
ACK
client对x, y 加1 , 并发回ACK包, 完毕握手。
图1-1
当三次握手完毕, 应用层数据就能够在client和server之间传送。 client能够在ACK 包发送完后马上传送数据包。 但server必须在接受到ACK包之后,才干够。
整个的启动过程(三次握手) 。 每个TCP连接都须要进行, 所以对于使用TCP的应用程序。 这个过程会很重要: 每个新的连接在传输数据之前都会有一个响应延时。
举一个样例, 假设我们的client在New York, 但server是在London, TCP连接是建立在光纤上的, 三次握手将至少花费56 毫秒(client能够在第三次ACK后,马上数据传输): 28ms 是一个方向的Propogation delay.
三次握手产生的延时,使得建立新的TCP连接是昂贵的, 这也是为什么在使用TCP时。须要对已有连接进行重要最大的原因之中的一个.
Slow-Start 慢启动
你能够通过 http://www.cnblogs.com/fll/archive/2008/06/02/1212479.html 了解TCP 对端到端数的可靠性, 以及流量控制, 网络拥塞。 在来看这一段文章。
TCP的提出攻克了流量控制的问题(通过rwind, 告知client,我能处理的数据量). 可是网络拥塞的问题出如今了。 流量控制防止了发送端(sender) 发送数据的速度超过接收者(receiver)的处理速度。 但TCP还没有考虑到不论什么一端的网络带宽是否被所有占用(发生拥塞)。 所以须要有一种机制来保证两端之者的有一个合理的传输速度.
我们看一个样例, 如果你在家里看一个很大的视频(在线) 。 为了保证你有最好的体验,整个带宽都会被视频占用。
这时你的朋友用你家的网络下载一个软件。 但这里你家的网络带宽已经很少了,所以 video server必须调速它的数据传送率。 否则,如果它还是以同样的速度传送的话,数据仅仅会仅仅简单的堆积在某个中间网关,而且数据包将会被丢弃。导致网络的低效利用。
1988年, Van Jacobson 和 Michael J.Karels 提出了几个算法,来解决这些问题: slow-start(慢起动), congestion avoidance(拥塞避免), Fast retransimit(高速重传), Fast recovery(高速恢复)。
非常快这四个算法成为了TCP规范中的强制部分。
为了理解slow-start 在实际应用中造成的影响,我们回到之前的样例, 我们的客户位于New York. 尝试从London的server获取一个文件。
首先经历三次握手, 在此其间。双方都通过ACK包,向对方告知自己的 receive window(rwnd)的大小。 一旦后一个ACK包进入网线。我们就能够交换应用数据。
client和server之间交换的数据大小是多少才合适呢? 这恰恰就是slow-start 被设计出来的原因了。
一開始, server初始化每个TCP连接 初始化一个 congestion window(cwnd 拥塞窗体), 而且保守的设置一个初始值 (由Linux系统指定大小).
Congestion window size(cwnd)
在接收到还有一端返回 的acknowlledgment(ACK)之前, 发送端能够发送最大的数据。 最初。 cwnd的開始值为 1个MSS(最大报文段, 能够通过 http://blog.csdn.net/wilsonpeng3/article/details/12869233了解TCP报文头 ), 在1999年, R2581添加一以了4个MSS. 到2013年已经添加到10MSS。
cwnd 变量不会在发送端和接收端之间告知对方和交换。 所以在这样的情况下,它将是一个私有变量。在两个发送端维护。
client和server都是在三次握手后,发送第一个数据包时。 初始化1MSS.
比方浏览器(图1-1的第二步。 y 1, x 1 后就能够发送数据了, 那么此时浏览器的cwnd 为 1MSS, 在一个RTT时间内,收到带ACKed的数据包后,会添加1个MSS. 能够发送两个数据包了。)
而server要在接到收到浏览器的ACK包后,才干够发送数据, 它的cwnd 为1MSS, 在下一次接收到client的ACKed包后,会添加1MSS.
那我们slow-start对我们的浏览器应用程序有什么影响呢? HTTP 和非常多其他应用程序都是执行在 TCP协议之上。 无论带完是多少。 每个TCP边接必须经历 slow-start。
我们不能直接将合适的流量应用到每个连接。
我们都是以最小的 cwnd 開始, 在每次 RTT之后, 指数添加cwnd的大小.
方程式 2-1 表式的是, 达到指定的传输速度所须要的时间:
让我们如果下面情下:
- client和server的速度达到 65,535 (64KB)
- 初始cwnd: 4 MSS (RFC2581)
- RTT(一个响应用的时间): 56ms (London to New York)
每个新建的TCP连接的吞吐量都被限制为 cwnd的大小。 实际上, 要达到64 KB的限制, 我们将添加cwnd的大小为45 MSS, 这须要花费244毫秒:
如图2-4所看到的。 这里4次请求与响应, 要经历好几百的延迟。才干够达到client与server的吞吐量, 64KB. 而在实际。server与client之前的速度以Mbps为单位, 在慢启动之前,这些都是速度都是无效的。
图 2-4
为了减小在添加拥塞空口大小,所花的时间,我们能够减小 server与client RTT的时间。
比如, 将server布置到离client更进的位置。 或者。我们能够添加初始的 cwnd的大小 到 10 MSS (RFC 6928).
对于视频以及大型文件来说, Slow-start不是特别大的问题。 但对于非常多短的和突发的http来说。 由于它限制了带宽吞吐量的能力(高带宽,但使用不上). 这就会对性能造成影响。
注: slow-start restart 对于空暇的连接(比方http keepalive connections, 不传送数据时), 进行重置到安全 cwnd 值。 这个机制对于 http 长连接造成性能影响。能够通过下面命念关闭
- $> sysctl net.ipv4.tcp_slow_start_after_idle
- $> sysctl -w net.ipv4.tcp_slow_start_after_idle=0
为了了解三次握手和慢启动对http请求造成的影响,我们如果 New York的客户 从 London的server请求一个20 KB的文件。新的TCP连接。如图 2-5所看到的。
- RTT 的时间为 56ms
- Client 和 Sever 之间的带宽 5 Mbps;
- Client 和 server 的 receive window(rwnd): 65,535 bytes (64KB)
- 初始 cwnd : 4 MSS (4 × 1460 bytes ≈ 5.7 KB)
- 服务器处理响应的时间: 40 ms
- GET请求大小,小于单个 segement( 1460)
图2-5
0 ms Client 通过SYN包,进行TCP第一次握手
28ms server返回一个SYN-ACK, 而且有指定 rwnd 大小
56ms Client 发送一个对SYN-ACK所的确认包。 并指定 自已的 rwnd大小, 并马上发送一个 HTTP GET 请求
84ms server接受 HTTP request, 并花 40 ms处理
124ms server完毕,并产生一个20kb的响应, 而且发送4 TCP segments的数据(5480 bytes), 并暂停,等待client返回一个 ACK包
152ms client接收到 4 个片段的数据。 并确认每一段数据, 并返回一个ACKed 包。
180ms server添加cwnd的值, 并发送8 个数据段
208ms client接收到 8个数据段。并确认每一段数据
236ms server添加每一个ACK 包的 cwnd, 并发送剩余的数据段
264ms client接收剩余数据段,并返回每个段的ACKs包
在一个新的TCP传递一个20KB的数据, 花费了264ms . 让我们对照一下,重用同样的TCP连接, 并请求同样的内容
图2-6
0 ms client发送请求
28ms server接收到请求
68ms server处理完请求。并生成20KB的响应。可是当前的cwnd为15 segments, 因此能够一次性发送完20KB的数据
96ms client接收到15个数据段。并ACKs 它们
同样同样的请求在同样的连接上(除了三次握手)。 性能上提升了275%;
在这两个样例中, 5 Mbps的带宽没有对性能产生不论什么影响,基本的影响因素是拥塞窗体大小。
拥塞避免
要认识到一点, TCP是通过数据包丢失返馈机制来调节 网络性能。
从慢启动能够看到,cwnd能够非常快的增长上来(2的N次方)。从而最大程度利用网络带宽资源,可是cwnd不能一直这样无限增长下去,一定须要某个限制。TCP使用了一个叫慢启动门限(ssthresh)的变量。当cwnd超过该值后,慢启动过程结束,进入拥塞避免阶段, 或者发生了丢包现像。也会进入到拥塞避免阶段. (http://www.cnblogs.com/fll/archive/2008/06/10/1217013.html)
假设发现丢包现像。 拥塞避免算法。觉得网络发生了拥塞: 在网络中的某处。我们遇到了拥塞的线路或者路由器。 它们强制性的丢弃了数据包。 在此时, 我们须要调速 拥塞窗体的大小, 以免丢失很多其它的包, 同一时候避免挤占网络。
一旦拥塞窗体被重置, 拥塞避免会採用它自己的算法添加窗体的大小。 保证包的最小丢失。 假设你以前观察过TCP连接的,就知道图表的线为什么是锯齿形的。
TCP 通过拥塞控制和拥塞避免,调整拥塞窗体的大小, 以免在网络中发生丢包。
Bandwidth-Delay Product (带宽拖延乘积)
TCP 内制的拥塞控制和拥塞避免带来了还有一个重要的性能优化: 发生者和接收者最佳值,这取决于RTT 和 两者之前的带宽( data rate)
我们回顾一下之前内容。 在发送者和接收者之间传送中的数据大小(unacknowledged),取决于 rwnd 和 cwnd 中最小的一个。
rwnd 的大小每次都会出如今ACK包中(固定), 而 cwnd 根据发送者的拥塞控制和拥塞避免。动态调整的。
假设发生者 或 接收者 超过了最大的unacknowledged data(未确认数据), 它必须停下来,等待其他之前发送过的包的确认信息(ACK). 那么它须要等待多久呢? 这取决于两者之者的响应时间RTT.
Bandwidth-Delay Product
数据链路上带宽与 end-to-end 之间的延时乘积。 它所表示的是。 任一时间点, 能够发送的最大 未确认(unacknowledged)的数据.
sender 或 receiver 在停下来等待之前发送的包确认信息, 就会有一段时间空隙(data gap), 在这段空隙内。发送端是不能在发送数据的。
为了解决问题, 窗体的大小就须要调整到足够大。 这样服sender在接受到receiver 返回的ACK包之前,也能够继续发送数据。 这样就没有gaps。
因此最优的窗体大小依赖于 Round-trip time (RTT). 当窗体比較小的时候, 你将会限制连接的吞吐量。
图2-7 Figure 2-7. Transmission gaps due to low congestion window size
那么流量控制窗体(rwnd) 和 拥塞控窗体(cwnd) 须要多在布吕尼 ? 计算这个值很easy, 首先, 让我们如果cwnd 和 rwnd中。最小的值为 16KB. RTT时间为 100ms:
无论在sender 和 receiver的有效带宽是多大, 这个TCP 连接不会超过 1.31 Mbps; 为了达到更大的输出, 我们须要添加 最小窗体值 或者降低两者之间的RTT.
相同。我们也能够通过 RTT 和 两者之者的有效带宽, 计算出最佳的 window 大小, 让我们如果RTT 相同为 100 ms. 但发送者有10 Mbps的有效带宽。 而且接收者的带宽高于100Mbps. 如果两者之者没有网络拥塞, 那我们发送到client的速度为 10Mbps;
窗体大小最少须要122.1 KB 才干适应 10 Mbps 的数据链路。 但rwnd最大的值为64KB, 除非通过其他方法调整 – 查看 “Window Scaling (RFC 1323″ on Page 18”
Head-of-Line Blocking 线头堵塞
TCP 是在不可靠的信道上提供了一条抽像的可靠网络。
这包含基础包的错误检察和改动, 按序发送, 重发丢失的包, 以及流量控制, 拥塞控制 和拥塞避免(保证网络资源的最有效利用). 所以非常多应用都是使用TCP.
但TCP不是唯一能够选择的, 有时TCP不是最好的选择。 特别是TCP有一些特性会引入不必要的延迟和性能问题。 比方有序 和 可靠的数据包传递(有些应用并不总是须要这些特性).
为了更好的理解这个问题。 我们回忆一下。每一个TCP 包 会携带一个唯一的序列号(Number)。 而且数据必须有序的传递到接收者那。 如图2-8所看到的. 假设一个包在路由中丢失了, 则全部的后序的包(2,3)都必须在接收者的 TCP 缓存里等待 丢失包(1)的重传。因为这个工作是在TCP层。 我们的应用程序不能看到TCP重传或者缓存中的包队列。 应用程序在能够訪问到这些数据之前,必须等待完整的包序列。 能够简单点说。 应用程序尝试从socket读取数据会有迟时发生。
这就是 TCP head-of-line(HOL) blocking(线头堵塞)
线头堵塞使我们的应用程序避免了对数据包进行又一次排序。 使得应用程序代码easy编写。
但是。 这会引入不确定的延时,以等待丢失的数据包重发。
这样的延时能够称为 (jjitter, http://blog.csdn.net/junllee/article/details/6110912) 。这影响到程序的性能。
图2-8
更进一步的说。 有的应用程序甚至不须要可靠的递送。或者有弃的递送: 比方数据包是一个独立的消息, 则有序递送就全然没有必要。 又比方,每一条消息都会覆盖之前的传送的消息。 那么可靠传送也没有必要。丢失了能够在之后中获得。 但不幸的是TCP 不提供这些配置 – 全部的数据包都是以可靠而有序的方式传递数据.
应用程序执行以无序或者忽略丢包的的方式执行,但必须使用其他的传输协议, 这就是UDP.
Packet Loss is OK (丢包的发生也是有优点的) 实际上, 数据包的丢失会使TCP获得更好的性能。 丢失的包作为一种反馈机制,TCP知道网络拥塞。 就会调整接收者和发送者之间的发送速率。 避免造成整个网络瘫痪。
并且, 有的应用程序能够忍受数据包丢失: audio, video , 游戏状态更新。
它们都不须要可靠和有序的数据传递。 顺便说一样, 这也是什么WebRTC(网页实时通信()是基于UDP作为传输协议的原因. 假设一个包丢失。 视频解码器会简单的在视频中插入一小段空白, 并继续处理之后的处据包。 假设这个空隙很小。视频解码都不会通知使用者,这样就不用在视频输出的时候。 以暂停的方式等待丢失的包。 相同的。假设我们正在传递的数据是 3D游戏中一个角色的状态更新, 这时我们等待的数据是用来描写叙述 T-1 时间点的状态。 而T时间点的数据包已经接收。那么T-1 秒的数据包就是不须要的了。 理想的是,我们能够接收到每个状态更新。 可是为了保证游戏的不发生延迟。 我们能够接爱间歇性的丢包。 以保证较低的延迟.
TCP 优化
TCP 协议是一种自适应的协议,以保证公平的对待网络的各节点,并最有效的利用各种网络。(公平, 有效利用)。 因此, 优化TCP最好的方法是让TCP知道当前的网络条件, 而且根据上次和下层的协议类型和要求,调整TCP的行为。 比方, 无线网络,它须要不同的拥塞算法; 有的应用程序为了达到最好的体验,会自己定义QoS语义。
不同的应用程序有不同的要求, 而每个TCP算法,也有非常多影响因子。这些都导致TCP的优化。成为了学术和商业研究中永恒的课题。 在眼下为前。我们仅仅是简单的介绍了影响到TCP 性能的一些因素。 当然另一些其他的因素,比方 selctive acknowledgments(SACK 选择性确认), delayed acknowledgments (拖延性确认), 高速重发等等。 这使得每个TCP会话都变得复杂, 难以理解, 分析, 调整。
尽管每个TCP算法都有自已特定的细节,并继续发展出不同的反馈(feedback)机制,但核心的原理依旧同样, 这些原理导致的性能问题也没有改变:
- TCP 三次握手 引入的延迟 2 RTT
- TCP slow-start 都会发生在每一个新的TCP连接
- TCP 流量 和 拥塞控制。 影响到全部TCP连接的吞吐量(带宽)
- TCP 吞吐量会受到cwnd(拥塞窗体)大小的影响
因此, 每一个tcp 连接在现代化的快速网络下,传送数据的速率也是受限于 发送者和接受者之间的 roundtrip 时间的影响(能够看看带宽拖延积)。或者这么解释, 尽管能够无限制的添加带宽, 採用光速传送数据,从New York 到 London的拖延还是有28ms. 在非常多情况下,TCP的瓶颈不是带宽的大小。而是延迟的大小。 能够查看图2-5.
调优server配置
首先须要调优TCP 会使用到的每个 buffer(rwnd, cwnd)的值 和超时变量。这里的影响TCP的因素许多。 所以最简单有效的方法是 升级server到最新的系统。 TCP 最佳的实践和算法都存在于最新的系统内核中。
有了最新的系统内核, 就能保存你的server配置使用下面最佳实践:
- 提升TCP’s 的初始化拥塞窗体的大小 原书 26页: cwnd 在一開始假设有一个非常大的值, 它同意TCP 在第一次RTT内传递很多其它的数据。 同一时候意味着它能够加速window的增长。 特别是 在优化突发性。短连接中起来决定性的作用。
- Slow-Start Restart 原书23页 : 禁用在TCP闲置时。进行慢启动。 这将明显的做优化长连接TCP的性能。
- Window Scaling 添加 接收窗体的大小 原书18 : 添加 rwnd 大小,达到网络最好的吞吐量
- TCP 高速打开 原书 16: 在某些情况下, 同意应用程序数据能够在初始的SYN包。一起发送。 TFO是一种新的优化方式, 要求在client和server都支持。
除了这些, 依据你的应用程序。 你也能够调整server其他的TCP设置。以优化快速连接。 内存使用 或者其他。 但这些配置会依赖于系统平台,应用程序, 以及硬件 — 在此之前,你必须查阅系统文档。
调优应用程序行为
- 尽量减小要发送数据的大小
- 我们不能改变数据发送大小的速度, 可是能够将数据放到离client更近的地方。
- TCP 连接的重用,对性能的改善非常明显
减小不必要的数据量传输。是最佳的一个优化。 e.g : 减小不必要的资源 或者 通过压缩算法将数据压缩后传输。 之后。 将数据放到离客户近期的地方。 比方使用CDN, 它会减小网络RTT 带来的延迟, 改善TCP性能。 最后 , 在可能的情况下,重用TCP连接
性能检測清单
下面是一个简短的优化清单。能够用在寻常的工作中:
- 升级你的系统内核到最新的版本号
- 确保cwnd 的大小设置为了 10 MSS
- 禁用 slow-start after idle
- 同意窗体可伸缩
- 消除多余数据的传输
- 压缩传送的数据
- 将server部署在离客户近期的地方。减小RTT
- 在可能的情况下, 重用TCP
UDP
udp 对前端没有什么影响,它是一种不可靠的协议, 能够通过google 了解udp的特性。以及NAT. 最新的採用的技术是Google 在浏览器提供的WebRTC.
TLS
SSL 协议最初是由Netscape公司开发的, 保证web中的电子商务的安全性。 它通过加密技术保护客户的私有数据。 以及安全的传输认证信息和信息的完整性。 为了达到这几个目标, SSL协议是在应用层实现, TCP的上一层就是SSL层, 之后同意其他的协议执行在它上面,比方HTTP, email, 即时通信等等。
当使用了SSL 时, 第三方的仅仅能判断出连接的两方是谁。 加密协议是什么, 以及数据传送的频率和大概的数据量。 但不能查看和改动不论什么实际的数据。
图 4-1
SSL 2.0 是第一个公布的版本号。 但非常快被SSL3.0代替, 由于2.0被发生有安全漏洞。 SSL一開始是属于网景公司, 经过IETF的努力,成为了RFC2246 中的一个标准协议。
这就是TLS1.0, 它实际上是SSL 3.0的一个升级。
加密、 认证、 完整性
TLS 会为全部执行在它上面的应用程序提供三方面的基础服务: 加密, 认识。 以及数据的完整性。 从技术上来说。你能够依据自己的须要,使用一种或者两种。比方你能够使用未被验证的安全证书, 但你知道这会导致安全问题, 在实践中。 一个安全web应用将会使用到三种服务。
加密 Encryption
提供一种机制,使数据以密文的形式发送
Authentication
提供一种机制,数据发送者的身份。 而不是第三方发送的数据
完整性
提供一种机制。保证数据不会被篡改和伪造
为了建立一个安全的password数据通道, 连接的两端必须协商好,使用哪种password套件来加密数据。 TLS 协议规范中定义了握手协议。用来处理处据交换, 我们将在 “TLS Handshake” 原书 50页 有具体讲解。 握手协议使用对方的公共密钥加密数据(非对称加密)。 数据接收方自己的私钥进行解密, 这样就能够在非安全信道上共享公共密钥。
握手协议也同意连接的两方,认证对方的身份。 当使用者在浏览器端。 认证机制充许客户校验自称的server是谁(比方你的银行), 而不是简单冒充的目的名称和IP 地址。 这样的认证是基于建立的信任链(能够通过 信任链和认证中心。即有一个权威的颁证机构,帮你确认,这个证书所相应的银行)。 另外, server也能够校验客户的身份, 比方, 一个公司代理server能够识别全部的员工。 每个员工都有它们自己的一个唯一证书(不是CA发的。而是公司自己通过软件生成).
如今TLS 有了加密和身份认证, TLS协议也提供了它,自己拥有的消息分帧机制, 并通过 message authentication code(MAC) 对每一条消息进行签名。
MAC算法是一种单向加密散列函数, 它的key 是通信两方协商 的一个结果(session key) , 能够查看http://www.ruanyifeng.com/blog/2014/02/ssl_tls.html 。 每当TLS record 要发送, 就会产生一个MAC值, 并附加在消息的后面。这样接收者,就能够计算和校验发送过的值, 以确保消息的完整性和身份认证。 (简单点说,密文通过MAC算法,基于session key 生成密文的校验值。 并把这个校验值一起发送到接收端,接收端使用MAC算法和同样的session key 对接到的信息生成校验值。并对照是否一样。就能保证消息的一致性)
综述, 加密,认证,数据的完整性保证了Web的安全性。 全部的现代浏览器都支持多种password套件, 能够用来认证client和server身份,而且透明的完毕信息的完整性校验和每个record的校验。
TLS 握手
在client和server開始效换应用数据之前, 两者必须协调一个加密通道: client和server协商好两方使用的TLS协议版本号, 加密的方法(比方RSA公钥加密),假设有须要。还要校对证书。 但每一步都会有新的数据包往返于client和server。 全部的TLS连接在启动的时候都有这种延迟发生。
图 4-2 TLS握手协议
0 ms TLS 执行在TCP连接上, 所以我们必须先完毕TCP的三次握手, 将花费一次往返的时间 56 ms
56ms 此处TCP能够使用了, client以文本的形式,发送多个參数。 比方client须要执行的TLS协议版本号, 它支持的加密算法, 和其他TLS 会用到的选项
84ms server选择TLS 版本号(根据client要求)。 并根据client支持的加密算法,确定加密套件。
并附上自己的证书, 发回一个响应给client。 在这里,另一些可选项。 server也能够要求客户商提供证书, 以及扩展TLS的參数
112ms 如果两端能够使用协商的TLS 版本号和password套件, 而且client对server提供的证书是信任的, 客户商这时候会生成一个新的对称密钥, 并使用server的公共密钥进行加密, 并告诉server。未来的通信以加密的方式进行。
到眼下为此。全部交换过的数据都是以明文的方式进行, 除了新的对称密钥。 是使用server的公共密钥进行了加密。
140ms server使用自己的私钥对client发过来的 对称密钥进行解密, 并通过MAC确认消息的完毕性, 并使用(用解密后的对称密钥), 加密 “Finished” 信息,并返回给client.
168ms client之前的生成的对称密解, 解密server返馈的信息, 并核实MAC是否一致。 假设都是正确的。 则建立起了安全加密链路, 应用数据如今就能够发送。
你能够通过 http://www.ruanyifeng.com/blog/2014/02/ssl_tls.html 了解更具体的握手过程
新的TLS连接须要两次的往返(上图中的绿色线)。才干完毕整个握手过程。
另外,你能够选择一种简单的握手, 它仅仅需一次往返。 能够查看 55页的 ”TLS Session Resumption”
协商建立一条安全的TLS 遂道是一个复杂的过程。 很多的子过程都可能会导致错误的发生。 但好的消息是,全部的工作都是通过浏览器和server完毕, 我们仅仅须要提供和配置自己的证书。
话虽如此, 我们的应用程序不用管TLS 遂道的建立, 可是它必须等待整个TCP, TLS 握手的完毕。 才干够发送数据。 假设不精心管理, 在TLS上传递数据, 会引入上百,上千毫秒的延时。
应用层协议协商(ALPN)
网络的两端希望使用自己定义的应用层协议,彼此进行通信。
能够直接通过port进行确定, e.g HTTP使用 80port。 TLS 使用 443port。 全部的client和server都是使用的这些公认的port。但在实际中。通过port来配匹配应用层协议是不可靠的,每个port都须要由系统开发。 并且防火墙和其他的中间机构仅仅同意 80 和 443port的信息通过。
所以, 为了能够简单的部署自己定义的协议, 我们必须重用80 或者 443port。 而且能够使用额外的机制协商应用程序协议。 80 port是为HTTP保留。 HTTP规范也指出,新的协议能够执行在HTTP协议层之上。但这会加入额外的RTT 和 延迟。 而且在实际中。也是不可靠的。 能够查看 “Proxies, Intermediaries, TLS, and New Protocols on the Web” 原书50页.
那么剩下的解决方式就是443port, TLS执行在这个端品。 它使用端到端加密遂道。对经过的数据进行模糊处理。 所以中间机构不须要知道传递的是什么类型的协议数据, 这样同意高速并且可靠的建立随意的应用层协议。
但是。 使用TLS 攻克了可靠性的问题, 我们依旧须要有一种方法。协商新的应用层协议。
我们能够将协商新的协议(HTTPS),作为TLS 握手的一部分:
- client向ClientHello消息中,加入一个, 新的ProtocolNameList 字段。 这个字段包括了它所支持的应用协议列表
- server检查ProtocolNameList 字段。 并在返回的SeverHello 消息中包括 ProtocolName字段,包括选中的协议
server可能会返回单个的协议名称。 假设它不支持client要求的协议。 则会选择终止连接。 因此,一旦TLS握手完毕。 两方之间的安全遂道已经建立。 同一时候client和server也协商好了要使用到的应用程序协议。 它们即能够马上用协商的进行通信。
ALPN 没有通过HTTP Upgrade exchange 的方式,减小了RTT导致的延时, 但须要注意, TLS握手自身也会产生一个响应延时, 因此 , ALPN 协商并不会比 HTTP Upgrade快,仅仅是它建立的是一个加密,哥靠的协议。
Server Name Indication (SNI)
在TCP两端建立好的TLS遂道, client仅仅须要知道server的IP地址就能够运行握手协议,但假设一台server有多个站点, 哪一个站点才是须要建立TLS连接呢?
为了解决问题。 Server Name Indication(SNI) 作为一个扩展,被引入到TLS协议, 它同意client在握手開始的时候,通过hostname字段,标识出它想要建立server的名称。 web server会检查SNI 中的 hostname. 并选择合适的证书, 并继续完毕握手。
但在很多老的client并不支持SNI, 比方执行在 Windows XP的浏览器, Android 2.2 等。
TLS Session Resumption
在全部使用安全通信的应用程序中, 握手阶段导致了额外的延迟和CPU计算, 严重的影响了应用程序的性能。为了减小同样的浪费, TLS 提供了在多个连接中。共用同样的安全密钥(生成的对称密钥)的能力。
Session Indentifiers
会话标识重用是在SSL 2.0版本号被引入, 它充许server创建并发送 32 字节的会话标识,作为 ”ServerHello” 消息的一部份。
在server内部,它须要为每个client缓存 session ID 以及TLS连接參数 (key, 加密算法)。 相同。 client也须要保存sessionID 信息, 而且在下次的TLS请求中, 在ClientHello 消息中带上sessionID. 当server收到sessionID时, 就知道client依旧保存了之前加密套件和 从上次握手所获得的 对称密钥。如图 4-3所看到的。 一个简短的握手过程。
假设两方没有从缓存在找到之前的信息,那么将会产生一个新的 session ID.
图4-3 简短的握手过程
利用会话标识。让我们减小了一个RTT时间。 以及计算开销。
在实际工作中, 很多web应用程序, 为了获取资源 会以并行的方式向同样的server建立连接, 就必须使用 会话重用,以减小延迟和计算开销。 现代化的浏览器会有意的等待第一个TLS连接完毕,在打开一条新的连接。
但是,在实际的工作中。使用server创建和保存session 标识符 具有局限性。 比方每天都会有成千上万的连接须要保存到缓存,这会导致缓存被使用完成, 有的站点是採用多个server,假设共享这些session也是一个问题。
(session 保存在server会带来哪些实际问题,能够查看 http://nil-zhang.iteye.com/blog/1279214)
Session Tickets
为了不在server缓存 TLS 的 sesion., 有了 “Session Ticket” (RFC5077) 机制, 它不须要server为每个已连接的client保存 session 状态。
取代的是, 假设client表明。它支持 Session Tickets, 在 TLS 握手的最后。 server会包括进一个新的 Session Ticket record. 这个记录包括了全部会话数据, 而且会以server才知道的安全密解加密。
会话船票会保存在client。 在之后的连接中,会以 SessionTick 扩展,包括进ClientHello 信息中。 这样全部的信息就仅保存在client。 并且 ticket 依旧是安全的, 由于它是使用server才知道的密钥加密的。
session indentifiers 和 session ticket 机制能够分别称为 会话缓存 和 无状态恢复。 无状态恢复的最大改进是不须要server端缓存。 client仅仅需在新的连接中提供 session ticket, 除非ticket 已经过期。
信息链 和 CA
我们如何才干知道,在建立加密遂道是我们信任的一方,而不是一个攻击者, 所以身份证认证在TLS 连接中是不可切割的一部分。为了知道如何验证两方的身份, 我们举了在 Alice 和 Bob 之间的一个样例:
- Alice 和 Bob 都有自己的公共密钥和私有密钥
- 两方都会隐藏自己的私有密钥
- Alice 向 Bob 分享自己的公共密钥, Bob 也向 Alice 分享了自己的公共密钥
- Alice 向 Bob 发了一条消息,这条信息是用她自己的私有密钥加密的
- Bob 使用 Alice’s 的公共密钥来校对信息提供者的签名, 这条消息是由Alice发送过来,而不是其他人
信任是交换数据之前的关键, 公钥加密算法,同意我们使用信息发送者的公共密钥, 确认被签名的信息是正确人发送过来的。
但这样的信任全然是基于 Alice 和 Bob 相互认识的基础上。才交换的公共密钥。
下一步, Alice 从Clarlie那里接收到一条信息, Alice 没有见过Clarlie, 但Clarlie 声称它是 Bob’s 的朋友。
实际上, Clarlie 为了证明自己是Bob的朋友。 Clarlie 要求Bob 对自己的公开密钥 使用 Bob 的私有密钥进行签时。 并以消息的附件,一起发送给Alice. 如图4-4. 在这样的情况下, Alice 首先确认 Clarlie的公共密钥中Bob的签名。 她已经有了Bob 的公开密钥, 所以知道Clarlie 的公开密钥的确是由 Bob签过的。Alice 接受了这条消息。 并使用消息中的Clarlie 公开密钥, 确证发送条消息的人确实是Clarlie.
图4-4
这样我们就建立了一条信息链: Alice 信任 Bob, Bob 信任 Charlie. 而且通过传递信任, Alice 确定信息 Charlie.
互联网和你的浏览器之间的认证也是採用同样的处理。 浏览器能够通过下面几种方式,加入信任
- 手动指定证书: 每个浏览器和操作系统都提供了一种机制,你能够手动的导入你信息的证书
- CA认证中心的证书
- 浏览器和操作系统自带的证书
在实际中,你不可能存放全部站点的证书。因此最通用的解决方法是使用CAs来帮我们进行校验. 如图 4-5. 站点会让认证中心对他的名字和公钥进行签名,并将这个签名发送到浏览器。假设浏览器的CAs的根文件夹下。有认证中心的公开密钥,就能确认这个站点是真实的。
图4-5
每个浏览器都同意你检查你安全连接中的信任链, 你能够当击URL 的中锁, 如图 4-6
图 4-6
Certificate Revocation
不重要。忽略
TLS Record Protocol
不同于IP 或者 TCP协议, 在TLS会话中的全部数据交换都是由TSL Record协议负责。 该协议须要负责识别不同类型的消息(握手信息,警告,数据), 并校对每个信息的完整性。
图 4-8 TLS record 结构
传递应用程序的数据的流程例如以下:
- Record 协议获得应用程序的数据
- 对接收到的数据进行分块: 最大为2的14次 bytes 或者16KB一个记录
- 应用数据能够选择压缩
- Message autentication code(MAC) 或 HMAC。 加入消息的校验码
- 使用协商好的加密算法,对数据进行加密
完毕以上步聚, 被加密的数据就会向下传入TCP层,进行传输。 在接收端, 则是相反的过程。
这个过程看起来非常easy。但须要注间几个地方:
- TLS record 最大为16KB
- 每个记录会包括 5-byte header, 一个MAC (SSLv3, TLS1.0, TLS1.1 为 20 bytes, TLS 1.2 须要32字节), 假设使用了块分组password, 还须要把password加上。
- 为了解密和校对record, 整个record 必须有效。
为你的应用程序挑选出最佳的record 的大小。对性能的优化非常重要,小的records 会导致非常大的开销, 然而大的records 会被TCP又一次进行组装
优化TLS
TLS的优化主要是配置你的server,比方TLS records 的大小。 内存缓冲区, 证书的大小, 是否支持简短的握手等等, 通过对这些參数的正确配置,会明显改善用户体验,减少操作开销。
计算开销
建立和维护一个加密的通道。在连接的两端都会引入额外的计算开销, 特别是在TLS握手时使用公共密钥加密对称密钥。 当连接建立之后,能够使用对称password加密全部的TLS records.
我们之前说过, 使用公钥加密 对照 对称密钥加密 会导致非常大的计算开销。 早先的站点通常须要额外的硬件来完毕 SSl计算。
但如今的硬件的性能有非常大的提升。都能直接完毕 但对于TLS Session 的恢复。 还是能够降低使用公钥加密。 除低计算的开销。
提前终止
无论是新建还是重用一个连接,都会有延迟的发生。 对于优化来说。 连接的建立是一个重要的区域。
我们看看一个TLS连接有哪些: TCP 三次握手, 之后是TLS握手, 添加两个RTT时间(新建)。
或者一个RTT(重用)。
在最坏的情况下,数据交换之前, TCP 和 TLS连接的设置过程就将花费三个 RTT. 以我们之前New York到London的样例, 一个RTT 时间为56ms, 那么新建一个TLS 将花费168ms, 而重用一个将花费112ms.
由于TLS是执行在TCP之上。所以对TCP的优化。也适用于这里。 通过CDN将server位置到离client近期的地方,减小RTT的值。
CDN不仅能够优化静态资源。你也能够应用动态内容上,提前终止TLS 会话。 如图 4-9所看到的,在本地代理server上,建立与client的连接(加速完毕握手),代理server与原始server之间建立一个长久(没有握手。仅仅负责数据传送),加密的连接。
这样全部的请求和响应都是从原server获取
图4-9 提前终止client连接
要做到这一点非常easy,非常多CDN都提供这种服务。 你也喜欢冒险。也能够以最小的花费搭建自己的基础设施: 在全球各地的数据中心部署云server,并配置代理server,将请求转发到你的原始server中。
并能够增加基于地理位置的DNS 负载均衡。
Session Caching and Stateless Resumption
了解概念就可以
TLS Record Size
通过TLS传输的应用数据,都是使用 record 协议。 查看图 4-8. 每个记录都将加入20-40不等字节大小的头部信息。 MAC 信息,以及其他的信息。
假设一个记录刚好能够装入一个 TCP数据包, 我们还须要加入IP 和 TCP的信息, 比方 IP会有20字节的头部信息, TCP也会有20字节的头部信息。
终于, 每个记录大概会加入60-100字节的头部信息。
电路中一个标准的最大传输单位(MTU) 大小是1500 字节。 数据包的结构就占领了 6% 的大小(overhead,在计算机网络的帧结构中,除了实用数据以外,还有非常多控制信息,这些控制信息用来保证通信的完毕。
这些控制信息被称作系统开销).
假设是一个非常好的记录,那么就不是 6%的系统开销。还是更高的比例。
但是,简单的添加记录的值,使它达到最大同意传递的16KB, 这也不是一个非常好的方法。 假设一个record 非常大,它会被分装进多个TCP 数据包。 则TLS的还有一端必须等待全部的TCP包到达之后才干够对数据进行解码(如图4-10)。
假设某些TCP数据包丢失, 还须要重传, 造成额外的延迟。
在实际中, 这样的延迟对于浏览器造成非常大的延迟, 还不如对数据一个字节一个字节的传递, 这样还可能会更快。
图 4-10. WireShark capture of 11,211-byte TLS record split over 8 TCP segments
假设records 太小,添加系统开销, 传到还有一头的实用数据就越少。
对应的,传送可用数据越少意味着传送的数据要很多其它的数据包。
这还意味着完毕传输数据须要额外的时间。
假设是大的records 又会引发延迟的发生。 这里非常难找到一个“正确” 的 record大小。 还好。浏览器会自己主动将web应用程序的值,设置为TCP MSS的大小,即records 值为 一个MSS(1460 bytes). 这种个TCP数据包传递一个record。 这样一个record就能够分配到多个TCP 数中包其中。
通过下面的方式。我们能计算出一个最佳的record:
- 电路中传输的数据包, 会包括IPv4 20bytes 地址, 假设是IPv6会是40 bytes
- TCP 会有20 bytes头部信息
- 40 个字节的TCP 可选信息, 比方 timestamps, SACKs
MTU通用的大小为1500 bytes, 那么在IPv4中 TLS record 大小就是1420 (1500- IP 20 – TCP 20 – TCP Option 40), 而对于IPv6,这个大小为1400. 为了兼容未来。 所以最佳的值为1400.
但我们在server的应用层上是不能配置 TLS record 的值。
而是须要通过server级别的配置,详细方法,须要查看server系统文档。
假设你的server须要处理大量的TLS 连接,则须要为每一个连接分配最小的内存使用。
OpenSSL 一般会为每一个连接分配50KB 的内存, 但正如调整record 大小一样,不妨查看OpenSSL 的文档。 Google的server能常将OpenSSL的值设置为5KB.
TLS 压缩
TLS 内部通过 record协议。 支持对传输的数据进行无损压缩: 压缩的算法是通过握手协议。两方协商好的。 压缩会发生在对每条record 加密之前。
但通常,你要禁止server的压TLS 压缩功能, 有下面几个原因:
- 在2012年。 黑客利用过TLS 压缩获得加密认证的cookie, 这就同意黑客运行会劫持, 这样的功能方法叫作”CRIME”
- 传输级别上的TLS 不知道要压缩的内容是什么,可能会压缩已经压缩过的数据,比方,图片,视频
两次的压缩,会浪费server和client的CPU, 并且导致非常严重的安全问题, 尽管非常多的浏览器禁用了TLS 压缩。但为了更好的保护你的客户。 你须要明白的禁止server压缩.
认证链长度
浏览器验证证书的过程是: 从站点的证书開始, 在遍历父证书。 直到信任的根文件夹( 证书是分级的,全球。 国家, 省份). 因此。第一条优化的原则是,在server上配置全部的中级证书。 假设忘记了, 那么很多浏览器依旧能够工作,可是它会暂停。 等待, 并向中间证书的server。 获取中间证书。 然后继续验证。直至根文件夹信任的证书。 这过程中会有新的DNS 查询, TCP连接。 和 HTTP GET请求。 会有数百毫秒的握手延迟。
但是浏览器怎么知道怎样获取中间证书的呢? 每个子证书通常都包括了父证书的URL
相反的, 你必须在你的信任链里不会包括不是必需的证书, 或者通俗点说, 你应该降低信任链的大小。
回顾一下。 server在TLS 握手期间。 会向client发送证书, 非常有可能证书的发送是在发生在新TCP连接的slow-start 阶段。
假设证书链的大小超过了TCP 初始 cwnd 的大小, 则仅仅能先发送一部份(TCP cwnd大小)。 等待client的 ACK后,在发送剩下的部分, 这就会导致多个RTT时间。
如图 4-11
图4-11 WireShack 软件截图 TLS 证书链的大小为 5, 323-byte
图4-11中, 证书链超过了5KB的大小,它超过了一些的老的server的拥塞窗体的大小。这就在握手阶段引入了其他RTT的大小。
有一个解决方式是添加初始的拥塞窗体的大小。 能够查看 “Increasing TCP’s Initial Congestion Window ” 原书 26页。
另外。 你也能够降低证书的大小:
- 减小认证的层级, 理想的是仅仅包括你自己的证书和中间人证书,第三个证书就是根文件夹证书(浏览器已经信任, 不须要在发送)
- 不要发送root 证书, 假设你的浏览器连root证书都没有,那么你发了,它也会不信任它
- 将证书链的大小减小到 2 KB 或 者3KB, 尽管为浏览器提供全部必要的证书,能够避免浏览器自己发起新的连接,获取中间代理人证书。从而引发不必要的RTT. 但这可能也就发生一次,而过大的证书会导致每一次新的TLS连接,有会有额外的RTT, 这样的性能损失更大
OCSP 装订
针对OCSP的优化, 每个新的TLS连接都须要浏览器检測认证链。但有一个步聚我们不能忘记, 那就是浏览器还须要检測证书是否被呆销,在这里,浏览器有两个方法,一个是下载CRL文件而且缓存。 另一个就是通过OCSP进行实时的检測, 从认证中心的server获取响应。 并使用认证中心的公开对响应进行加密。
以证实证书是否吊销。所以我们能够在server 发送一个请求到认证中心的响应,而且把它包括(装订)到认识链中(部分浏览器能够识别)。 这样我们自己的server就能够缓存被签名过的OCSP响应。能够节省多个client的额外请求。 但这里也须要注意一些问题:
- OCSP的大小从400到 4000不等。 装订到你的认证链中, 可能会超过你TCP拥塞窗体的大小
- 仅仅能装订一个OCSP响应。 那么对于中间(发证中心)的证书,浏览器还是会发送OCSP请求。
近期。你须要在配置server。同意有OCSP装订的功能。 好的消息是,主流的server。 比方Nginx, Apache, IIS是有这个功能的。 你能够查看这些server的文档说明。
HTTP Strict Transport Security (HSTS)
HTTP Strict Transport Security 是一个安全策略机制, 它同意server通过简单的HTTP 头, 比方 Strict-Transport-Security: max-age = 3153600. 向顺从的浏览器(知道这类http头的浏览器) 声明訪问规则。
这条规则表示,client必须强制运行下面规则:
- 全部到初始请求,都必须使用HTTPS
- 全部不安全的连接 和client请求,在请求发送之前。 应该自己主动转化为 HTTPS
- 假设发生认识错误, 显示错误信息, 而且不同意绕过吃警告
- max-age 表明 HSTS规则的有效期, 单位为秒
HSTS 不仅能够将原始连接转变为 HTTPS, 还能够保护应程序。 在性能上, 能够减小从 HTTP-to-HTTS的跳转(301 或者302)。
在2013年时。 支持HSTS的浏览器有 Firefox 4 , Chrome 4 , Opera 12 以及Android 版的Chrome 和 Firefox. 最新的了解能够查看 caniuse.com/stricttransportsecurity.
TLS 性能检測清单
- 优化TCP, 能够查看 “Optimizing for TCP” 在原书第32
- 升级TLS 库到最新的版本号
- 同意并配置 TLS session 的缓存 和 无状态重用
- 监測你的TLS session 缓存命中率, 并调整对应的配置
- 使用CDN。 在client近期的寺方, 提前终止 TLS sesion, 减少往返导致的延迟
- 配置TLS record 的大小。以适应单个TCP段的大小, 1400 bytes
- 确保你的认证不会超过初始化拥塞窗体的大小, 低于 2 or 3KB
- 从认证链中删除不是必需的证书, 减小认证链的深度
- 禁用server的TLS 压缩
- 配置你的server,以支持SNI, 域名识别
- 配置OCSP 装订功能
- 加入 HTTP Strict Transport Security header
測试和检验
最后, 检验和測试你的配置。 你能够使用在线的服务, 比方 Qualys SSL Server Test 扫描你公开的server的通用配置 和安全缺陷。 另外,你也能够使用 openssl 命令, 它将帮助你检验整个握手过程和本地的server配置
代码语言:javascript复制$> openssl s_client -state -CAfile startssl.ca.crt -connect igvita.com:443
CONNECTED(00000003)
SSL_connect:before/connect initialization
SSL_connect:SSLv2/v3 write client hello A
SSL_connect:SSLv3 read server hello A
depth=2 /C=IL/O=StartCom Ltd./OU=Secure Digital Certificate Signing
/CN=StartCom Certification Authority
verify return:1
depth=1 /C=IL/O=StartCom Ltd./OU=Secure Digital Certificate Signing
/CN=StartCom Class 1 Primary Intermediate Server CA
verify return:1
depth=0 /description=ABjQuqt3nPv7ebEG/C=US
/CN=www.igvita.com/emailAddress=ilya@igvita.com
verify return:1
SSL_connect:SSLv3 read server certificate A
SSL_connect:SSLv3 read server done A
SSL_connect:SSLv3 write client key exchange A
SSL_connect:SSLv3 write change cipher spec A
SSL_connect:SSLv3 write finished A
SSL_connect:SSLv3 flush data
SSL_connect:SSLv3 read finished A
---
Certificate chain
0 s:/description=ABjQuqt3nPv7ebEG/C=US
/CN=www.igvita.com/emailAddress=ilya@igvita.com
i:/C=IL/O=StartCom Ltd./OU=Secure Digital Certificate Signing
/CN=StartCom Class 1 Primary Intermediate Server CA
1 s:/C=IL/O=StartCom Ltd./OU=Secure Digital Certificate Signing
/CN=StartCom Class 1 Primary Intermediate Server CA
i:/C=IL/O=StartCom Ltd./OU=Secure Digital Certificate Signing
/CN=StartCom Certification Authority
---
Server certificate
-----BEGIN CERTIFICATE-----
... snip ...
---
No client certificate CA names sent
---
SSL handshake has read 3571 bytes and written 444 bytes
---
New, TLSv1/SSLv3, Cipher is RC4-SHA
Server public key is 2048 bit
Secure Renegotiation IS supported
Compression: NONE
Expansion: NONE
SSL-Session:
Protocol : TLSv1
Cipher : RC4-SHA
Session-ID: 269349C84A4702EFA7 ...
Session-ID-ctx:
Master-Key: 1F5F5F33D50BE6228A ...
Key-Arg : None
Start Time: 1354037095
Timeout : 300 (sec)
Verify return code: 0 (ok)
- client完毕 认证链的验证
- 接收到认证链(两个证书)
- 接收到的认证链的大小
- 有状态的TLS session 标识符
在此之样例中, 我们通过TLS的默认port(443) 连接到 igvita.com , 并运行TLS 握手。 因为 s_client 不清楚root证书,我们须要手动将 StartSSL Certifiecate Authority 导入到根文件夹(很重要的一步) , 否则 s_client 会看到一个校验失败的错误日志。
检測证书链的过程中,我们看到server发送了两个证书。 总的大小为3,571 bytes, 这是进军 3 至 4 分割 (TCP 老server初始拥塞窗口的大小 4 分割) 。终于, 我们检测磋商 SSL 变量 – 最新的协议。 加密演算法 , 对称密钥 – 我们也可以看到server发送一斤session 马克。
发布者:全栈程序员栈长,转载请注明出处:https://javaforall.cn/117252.html原文链接:https://javaforall.cn