SSL&TLS協議執行機制概述
不使用SSL/TLS的HTTP通訊,就是不加密的通訊, 所有資訊明文傳播,帶來了三大風險。
(1) 竊聽風險(eavesdropping):第三方可以獲知通訊內容。
(2) 篡改風險(tampering):第三方可以修改通訊內容。
(3) 冒充風險(pretending):第三方可以冒充他人身份參與通訊。
協議希望達到的要求:
(1) 所有資訊都是加密傳播,第三方無法竊聽。
(2) 具有校驗機制,一旦被篡改,通訊雙方會立刻發現。
(3) 配備身份證書,防止身份被冒充。
基本執行過程:
SSL/TLS協議的基本思路是採用公鑰加密法,也就是說,客戶端先向伺服器端索要公鑰,然後用公鑰加密資訊,伺服器收到密文後,用自己的私鑰解密。
(1) 客戶端向伺服器端索要並驗證公鑰。
(2) 雙方協商生成"對話金鑰"。
(3) 雙方採用"對話金鑰"進行加密通訊。
握手階段分為五步:
第一步,愛麗絲給出協議版本號、一個客戶端生成的隨機數(Client random),以及客戶端支援的加密方法。
第二步,鮑勃確認雙方使用的加密方法,並給出數字證書、以及一個伺服器生成的隨機數(Server random)。
第三步,愛麗絲確認數字證書有效,然後生成一個新的隨機數(Premaster secret),並使用數字證書中的公鑰,加密這個隨機數,發給鮑勃。
第四步,鮑勃使用自己的私鑰,獲取愛麗絲髮來的隨機數(即Premaster secret)。
第五步,愛麗絲和鮑勃根據約定的加密方法,使用前面的三個隨機數,生成"對話金鑰"(session key),用來加密接下來的整個對話過程。
四、握手階段的詳細過程
1. 客戶端發出請求(ClientHello)
首先,客戶端(通常是瀏覽器)先向伺服器發出加密通訊的請求,這被叫做ClientHello請求。
在這一步,客戶端主要向伺服器提供以下資訊:
(1) 支援的協議版本,比如TLS 1.0版。
(2) 一個客戶端生成的隨機數,稍後用於生成"對話金鑰"。
(3) 支援的加密方法,比如RSA公鑰加密。
(4) 支援的壓縮方法。
2. 伺服器迴應(SeverHello)
伺服器收到客戶端請求後,向客戶端發出迴應,這叫做SeverHello。伺服器的迴應包含以下內容。
(1) 確認使用的加密通訊協議版本,比如TLS 1.0版本。如果瀏覽器與伺服器支援的版本不一致,伺服器關閉加密通訊。
(2) 一個伺服器生成的隨機數,稍後用於生成"對話金鑰"。
(3) 確認使用的加密方法,比如RSA公鑰加密。
(4) 伺服器證書。
除了上面這些資訊,如果伺服器需要確認客戶端的身份,就會再包含一項請求,要求客戶端提供"客戶端證書"。比如,金融機構往往只允許認證客戶連入自己的網路,就會向正式客戶提供USB金鑰,裡面就包含了一張客戶端證書
3. 客戶端迴應
如果證書沒有問題,客戶端就會從證書中取出伺服器的公鑰。然後,向伺服器傳送下面三項資訊。
(1) 一個隨機數。該隨機數用伺服器公鑰加密,防止被竊聽。
(2) 編碼改變通知,表示隨後的資訊都將用雙方商定的加密方法和金鑰傳送。
(3) 客戶端握手結束通知,表示客戶端的握手階段已經結束。這一項同時也是前面傳送的所有內容的hash值,用來供伺服器校驗。
此外,如果前一步,伺服器要求客戶端證書,客戶端會在這一步傳送證書及相關資訊。
4.伺服器的最後迴應
伺服器收到客戶端的第三個隨機數pre-master key之後,計算生成本次會話所用的"會話金鑰"。然後,向客戶端最後傳送下面資訊。
(1)編碼改變通知,表示隨後的資訊都將用雙方商定的加密方法和金鑰傳送。
(2)伺服器握手結束通知,表示伺服器的握手階段已經結束。這一項同時也是前面傳送的所有內容的hash值,用來供客戶端校驗。
至此,整個握手階段全部結束。接下來,客戶端與伺服器進入加密通訊,就完全是使用普通的HTTP協議,只不過用"會話金鑰"加密內容。
握手階段有三點需要注意。
(1)生成對話金鑰一共需要三個隨機數。
(2)握手之後的對話使用"對話金鑰"加密(對稱加密),伺服器的公鑰和私鑰只用於加密和解密"對話金鑰"(非對稱加密),無其他作用。
(3)伺服器公鑰放在伺服器的數字證書之中。
session的恢復
握手階段用來建立SSL連線。如果出於某種原因,對話中斷,就需要重新握手。
這時有兩種方法可以恢復原來的session:一種叫做session ID,另一種叫做session ticket。
session ID的思想很簡單,就是每一次對話都有一個編號(session ID)。如果對話中斷,下次重連的時候,只要客戶端給出這個編號,且伺服器有這個編號的記錄,雙方就可以重新使用已有的"對話金鑰",而不必重新生成一把。
session ID是目前所有瀏覽器都支援的方法,但是它的缺點在於session ID往往只保留在一臺伺服器上。所以,如果客戶端的請求發到另一臺伺服器,就無法恢復對話。session ticket就是為了解決這個問題而誕生的,目前只有Firefox和Chrome瀏覽器支援。
客戶端不再發送session ID,而是傳送一個伺服器在上一次對話中傳送過來的session ticket。這個session ticket是加密的,只有伺服器才能解密,其中包括本次對話的主要資訊,比如對話金鑰和加密方法。當伺服器收到session ticket以後,解密後就不必重新生成對話金鑰了。