HTTPS協議詳解(轉載)
參考HTTPS的加密流程|一篇文章讀懂HTTPS及其背後的加密原理|HTTPS協議詳解|Https加密過程|Https握手過程
HTTPS
(全稱: Hypertext Transfer Protocol Secure,超文字傳輸安全協議
),是以安全為目標的HTTP通道,簡單講是HTTP
的安全版。
- HTTP: 直接通過明文在瀏覽器和伺服器之間傳遞資訊。
- HTTPS: 採用 對稱加密 和 非對稱加密 結合的方式來保護瀏覽器和服務端之間的通訊安全。
對稱加密演算法加密資料+非對稱加密演算法交換金鑰+數字證書驗證身份=安全
HTTPS其實是有兩部分組成:HTTP + SSL / TLS,也就是在HTTP上又加了一層處理加密資訊的模組。服務端和客戶端的資訊傳輸都會通過TLS進行加密,所以傳輸的資料都是加密後的資料。
- 傳統的HTTP協議通訊:傳統的HTTP報文是直接將報文資訊傳輸到TCP然後TCP再通過TCP套接字傳送給目的主機上。
- HTTPS協議通訊:HTTPS是HTTP報文直接將報文資訊傳輸給SSL套接字進行加密,SSL加密後將加密後的報文傳送給TCP套接字,然後TCP套接字再將加密後的報文傳送給目的主機,目的主機將通過TCP套接字獲取加密後的報文給SSL套接字,SSL解密後交給對應程序。
具體是如何進行加密,解密,驗證的,且看下圖。
HTTPS加密請求(一次握手)過程
- 首先,客戶端發起握手請求,以明文傳輸請求資訊,包含版本資訊,加密-套件候選列表,壓縮演算法候選列表,隨機數,擴充套件欄位等資訊(
這個沒什麼好說的,就是使用者在瀏覽器裡輸入一個HTTPS網址,然後連線到服務端的443埠。
) - 服務端的配置,採用HTTPS協議的伺服器必須要有一套數字證書,可以自己製作,也可以向組織申請。區別就是自己頒發的證書需要客戶端驗證通過,才可以繼續訪問,而使用受信任的公司申請的證書則不會彈出提示頁面。
這套證書其實就是一對公鑰和私鑰。
如果對公鑰不太理解,可以想象成一把鑰匙和一個鎖頭,只是世界上只有你一個人有這把鑰匙,你可以把鎖頭給別人,別人可以用這個鎖把重要的東西鎖起來,然後發給你,因為只有你一個人有這把鑰匙,所以只有你才能看到被這把鎖鎖起來的東西。 - 服務端返回協商的資訊結果,包括選擇使用的協議版本 version,選擇的加密套件 cipher suite,選擇的壓縮演算法 compression method、隨機數 random_S 以及證書。(
這個證書其實就是公鑰,只是包含了很多資訊,如證書的頒發機構,過期時間等等。
) - 客戶端驗證證書的合法性,包括可信性,是否吊銷,過期時間和域名。(
這部分工作是由客戶端的SSL/TLS來完成的,首先會驗證公鑰是否有效,比如頒發機構,過期時間等等,如果發現異常,則會彈出一個警示框,提示證書存在的問題。如果證書沒有問題,那麼就生成一個隨機值。然後用證書(也就是公鑰)對這個隨機值進行加密。就好像上面說的,把隨機值用鎖頭鎖起來,這樣除非有鑰匙,不然看不到被鎖住的內容。
) - 客戶端使用公匙對對稱密匙加密,傳送給服務端。(
這部分傳送的是用證書加密後的隨機值,目的是讓服務端得到這個隨機值,以後客戶端和服務端的通訊就可以通過這個隨機值來進行加密解密了。
) - 伺服器用私鑰解密,拿到對稱加密的密匙。(
服務端用私鑰解密後,得到了客戶端傳過來的隨機值,然後把內容通過該隨機值進行對稱加密,將資訊和私鑰通過某種演算法混合在一起,這樣除非知道私鑰,不然無法獲取內容,而正好客戶端和服務端都知道這個私鑰,所以只要加密演算法夠彪悍,私鑰夠複雜,資料就夠安全。
) - 傳輸加密後的資訊,這部分資訊就是服務端用私鑰加密後的資訊,可以在客戶端用隨機值解密還原。
- 客戶端解密資訊,客戶端用之前生產的私鑰解密服務端傳過來的資訊,於是獲取瞭解密後的內容。整個過程第三方即使監聽到了資料,也束手無策。
加密
客戶端和服務端之間的加密機制:
TLS握手
TLS協議是基於TCP協議之上的,圖中第一個藍色往返是TCP的握手過程,之後兩次橙色的往返,我們可以叫做TLS的握手。握手過程如下:
-
client1:TLS版本號+所支援加密套件列表+希望使用的TLS選項
-
Server1:選擇一個客戶端的加密套件+自己的公鑰+自己的證書+希望使用的TLS選項+(要求客戶端證書);
-
Client2:(自己的證書)+使用伺服器公鑰和協商的加密套件加密一個對稱祕鑰(自己生成的一個隨機值);
-
Server2:使用私鑰解密出對稱祕鑰(隨機值)後,傳送加密的Finish訊息,表明完成握手
這裡可能要提一下什麼是對稱加密和非對稱加密:
一般的對稱加密像這樣:
encrypt(明文,祕鑰) = 密文
decrypt(密文,祕鑰) = 明文
共享金鑰加密也稱對稱金鑰加密。採用的是使用相同金鑰對報文進行加密解密
我們可以將共享金鑰加密這樣理解:我們把我們要給別人的東西放到一個箱子裡面,然後給箱子上了一把鎖。當箱子到了我們想給的那個人
身上時,他也需要這把鑰匙才能開鎖。
這樣就產生了一個問題了,我們怎麼將這把鑰匙安全的交給對方呢,如果鑰匙在半路被人截取了,那麼對箱子有沒有加鎖有什麼區別呢。因此
共享金鑰加密需要解決的一個大問題就是如何安全的將金鑰交給解密方。
也就是說加密和解密用的是同一個祕鑰。而非對稱加密是這樣的:
encrypt(明文,公鑰) = 密文
decrypt(密文,私鑰) = 明文
假設客戶傳送報文,伺服器接收報文。客戶在傳送報文的時候需要對報文加密,伺服器有兩把金鑰,一把私鑰,一把公鑰。客戶在傳送報文前需要先向伺服器獲取公鑰進行報文的加密。這把公鑰只能加密,不能解密,因此被任何人截獲到都沒什麼用處。伺服器收到加密後的報文,使用私鑰解密。整個過程中只涉及到公鑰的獲取,加密,密文傳輸,解密。並不涉及到解密用的私鑰傳輸。因此這種方式是安全的。但是涉及到太多細節,整個流程
下來耗時耗費資源。
再拿上面那個例子,這時候我們還想把一些東西鎖到箱子裡給某人,我們稱他為大傻。我們先跟大傻聯絡,大傻身上有兩把鑰匙,我們稱為鑰匙A和鑰匙B。鑰匙A可以用來造鎖,但是造好的鎖自己卻不能開,只能通過鑰匙B來開。跟大傻取得聯絡後大傻把鑰匙A給我們。我們拿著鑰匙A找造鎖師傅造了一把鎖,並且給箱子上鎖。然後將帶鎖的箱子通過物流發給大傻,就算鑰匙A被強盜截取了,強盜也開不了箱子。大傻收到箱子後使用那把鑰匙B進行開鎖,拿到東西。由於鑰匙B一直再大傻身上,所以不用擔心被人拿走。
加密和解密是需要不同的祕鑰的。
經過這幾次握手成功後,客服端和服務端之間通訊的加密演算法和所需要的金鑰也就確定下來了,之後雙方的互動都可以使用對稱加密演算法加密了。
HTTPS為了追求效能,又要保證安全,採用了共享金鑰加密和公開金鑰加密混合的方式進行報文傳輸。
還是拿上面的鎖和箱子的例子來說明。現在我們嫌棄每次加鎖都要造個新的鎖效率太慢了。我們現在有兩個箱子,一個箱子用於方我們要給大傻的東西,並且
這個箱子加上了鎖。另一個箱子用於存放那把鎖的鑰匙。我們這時候找大傻拿到鑰匙A造了一把鎖後將那個存放鑰匙的箱子鎖起來,然後將這個箱子給大傻,
大傻拿到箱子使用鑰匙B開鎖拿到鑰匙。這時候我們將那個存放了東西的箱子給大傻,大傻就可以通過這把鑰匙開鎖拿到東西了。這樣以後我們就可以一直通過
這把鎖和箱子互相給東西了,而不用發一次資料造一次鎖了。
就是說採用共有金鑰加密方式傳輸共享金鑰,當共享金鑰安全到達服務端後往後的資料就都採用該金鑰進行加密解密。
轉載:https://www.jianshu.com/p/e30a8c4fa329