說到密碼,咱們第一個想到的就是登錄帳戶的密碼,可是從密碼學的角度來看,這種根本就不算合格的密碼。git
爲何呢,由於咱們的帳戶密碼,是依靠隱蔽性來達到加密做用:密碼藏在我內心,你不知道,因此你登不上個人帳戶。算法
然而密碼技術認爲,「保密」信息總有一天會被扒出來,因此加密算法不該該依靠「保密」來保證機密性,而應該作到:即使知道了加密算法,依然機關用盡。說的魔幻一點就是,告訴你個人密碼,你依然不知道個人密碼。瀏覽器
最玄學的就是 Diffie-Hellman 密鑰交換算法,我當初就以爲很驚奇,兩我的當着你的面互相報幾個數字,他們就能夠擁有一個共同的祕密,而你卻根本不可能算出來這個祕密。下文會着重介紹一下這個算法。安全
本文討論的密碼技術要解決的主要是信息傳輸中的加密和解密問題。要假設數據傳輸過程是不安全的,全部信息都在被竊聽的,因此發送端要把信息加密,接收方收到信息以後,確定得知道如何解密。有意思的是,若是你可以讓接收者知道如何解密,那麼竊聽者不是也可以知道如何解密了嗎?服務器
PS:我認真寫了 100 多篇原創,手把手刷 200 道力扣題目,所有發佈在 labuladong的算法小抄,持續更新。建議收藏,按照個人文章順序刷題,掌握各類算法套路後投再入題海就如魚得水了。網絡
下面,咱們會介紹對稱加密算法、密鑰交換算法、非對稱加密算法、數字簽名、公鑰證書,看看解決安全傳輸問題的一路坎坷波折。app
對稱性密碼,也叫共享密鑰密碼,顧名思義,這種加密方式用相同的密鑰進行加密和解密。ide
好比我說一種最簡單的對稱加密的方法。首先咱們知道信息均可以表示成 0/1 比特序列,也知道相同的兩個比特序列作異或運算的結果爲 0。函數
那麼咱們就能夠生成一個長度和原始信息同樣的隨機比特序列做爲密鑰,而後用它對原始信息作異或運算,就生成了密文。反之,再用該密鑰對密文作一次異或運算,就能夠恢復原始信息。網站
這是一個簡單例子,不過有些過於簡單,有不少問題。好比密鑰的長度和原始信息徹底一致,若是原始信息很大,密鑰也會同樣大,並且生成大量真隨機比特序列的計算開銷也比較大。
固然,有不少更復雜優秀的對稱加密算法解決了這些問題,好比 Rijndael 算法、三重 DES 算法等等。它們從算法上是無懈可擊的,也就是擁有巨大的密鑰空間,基本沒法暴力破解,並且加密過程相對快速。
可是,一切對稱加密算法的軟肋在於密鑰的配送。加密和解密用同一個密鑰,發送方必須設法把密鑰發送給接收方。若是竊聽者有能力竊取密文,確定也能夠竊取密鑰,那麼再無懈可擊的算法依然不攻自破。
因此,下面介紹兩種解決密鑰配送問題最多見的算法,分別是 Diffie-Hellman 密鑰交換算法和非對稱加密算法。
咱們所說的密鑰通常就是一個很大的數字,算法用這個數加密、解密。問題在於,信道是不安全的,全部發出的數據都會被竊取。換句話說,有沒有一種辦法,可以讓兩我的在衆目睽睽之下,光明正大地交換一個祕密,把對稱性密鑰安全地送到接收方的手中?
Diffie-Hellman 密鑰交換算法能夠作到。準確的說,該算法並非把一個祕密安全地「送給」對方,而是經過一些共享的數字,雙方「心中」各自「生成」了一個相同的祕密,並且雙方的這個祕密,是第三方竊聽者沒法生成的。
也許這就是傳說中的心有靈犀一點通吧。
這個算法規則不算複雜,你甚至均可以找個朋友嘗試一下共享祕密,等會我會簡單畫出它的基本流程。在此以前,須要明確一個問題:並非全部運算都有逆運算。
最簡單的例子就是咱們熟知的單向散列函數,給一個數字 a
和一個散列函數 f
,你能夠很快計算出 f(a)
,可是若是給你 f(a)
和 f
,推出 a
是一件基本作不到的事。密鑰交換算法之因此看起來如此玄幻,就是利用了這種不可逆的性質。
下面,看下密鑰交換算法的流程是什麼,按照命名慣例,準備執行密鑰交換算法的雙方稱爲 Alice 和 Bob,在網絡中企圖竊取他倆通訊內容的壞人稱爲 Hack 吧。
首先,Alice 和 Bob 協商出兩個數字 N
和 G
做爲生成元,固然協商過程能夠被竊聽者 Hack 竊取,因此我把這兩個數畫到中間,表明三方都知道:
如今 Alice 和 Bob 心中各自想一個數字出來,分別稱爲 A
和 B
吧:
如今 Alice 將本身內心的這個數字 A
和 G
經過某些運算得出一個數 AG
,而後發給 Bob;Bob 將本身內心的數 B
和 G
經過相同的運算得出一個數 BG
,而後發給 Alice:
如今的狀況變成這樣了:
注意,相似剛纔舉的散列函數的例子,知道 AG
和 G
,並不能反推出 A
是多少,BG
同理。
那麼,Alice 能夠經過 BG
和本身的 A
經過某些運算獲得一個數 ABG
,Bob 也能夠經過 AG
和本身的 B
經過某些運算獲得 ABG
,這個數就是 Alice 和 Bob 共有的祕密。
而對於 Hack,能夠竊取傳輸過程當中的 G
,AG
,BG
,可是因爲計算不可逆,怎麼都沒法結合出 ABG
這個數字。
以上就是基本流程,至於具體的數字取值是有講究的,運算方法在百度上很容易找到,限於篇幅我就不具體寫了。
該算法能夠在第三者竊聽的前提下,算出一個別人沒法算出的祕密做爲對稱性加密算法的密鑰,開始對稱加密的通訊。
對於該算法,Hack 又想到一種破解方法,不是竊聽 Alice 和 Bob 的通訊數據,而是直接同時冒充 Alice 和 Bob 的身份,也就是咱們說的「中間人***」:
這樣,雙方根本沒法察覺在和 Hack 共享祕密,後果就是 Hack 能夠解密甚至修改數據。
可見,密鑰交換算法也不算徹底解決了密鑰配送問題,缺陷在於沒法覈實對方身份。因此密鑰交換算法以前通常要覈實對方身份,好比使用數字簽名。
PS:我認真寫了 100 多篇原創,手把手刷 200 道力扣題目,所有發佈在 labuladong的算法小抄,持續更新。建議收藏,按照個人文章順序刷題,掌握各類算法套路後投再入題海就如魚得水了。
非對稱加密的思路就是,乾脆別偷偷摸摸傳輸密鑰了,我把加密密鑰和解密密鑰分開,公鑰用於加密,私鑰用於解密。只把公鑰傳送給對方,而後對方開始給我發送加密的數據,我用私鑰就能夠解密。至於竊聽者,拿到公鑰和加密數據也沒用,由於只有我手上的私鑰才能解密。
能夠這樣想,私鑰是鑰匙,而公鑰是鎖,能夠把鎖公開出去,讓別人把數據鎖起來發給我;而鑰匙必定要留在本身手裏,用於解鎖。咱們常見的 RSA 算法就是典型的非對稱加密算法,具體實現比較複雜,我就不寫了,網上不少資料。
在實際應用中,非對稱性加密的運算速度要比對稱性加密慢不少的,因此傳輸大量數據時,通常不會用公鑰直接加密數據,而是加密對稱性加密的密鑰,傳輸給對方,而後雙方使用對稱性加密算法傳輸數據。
須要注意的是,相似 Diffie-Hellman 算法,非對稱加密算法也沒法肯定通訊雙方的身份,依然會遭到中間人***。好比 Hack 攔截 Bob 發出的公鑰,而後冒充 Bob 的身份給 Alice 發送本身的公鑰,那麼不知情的 Alice 就會把私密數據用 Hack 的公鑰加密,Hack 能夠經過私鑰解密竊取。
那麼,Diffie-Hellman 算法和 RSA 非對稱加密算法均可以必定程度上解決密鑰配送的問題,也具備相同的缺陷,兩者的應用場景有什麼區別呢?
簡單來講,根據兩種算法的基本原理就能夠看出來:
若是雙方有一個對稱加密方案,但願加密通訊,並且不能讓別人獲得鑰匙,那麼可使用 Diffie-Hellman 算法交換密鑰。
若是你但願任何人均可以對信息加密,而只有你可以解密,那麼就使用 RSA 非對稱加密算法,公佈公鑰。
下面,咱們嘗試着解決認證發送方身份的問題。
剛纔說非對稱加密,把公鑰公開用於他人對數據加密而後發給你,只有用你手上對應的私鑰才能將密文解密。其實,私鑰也可用用來加密數據的,對於 RSA 算法,私鑰加密的數據只有公鑰才能解開。
數字簽名也是利用了非對稱性密鑰的特性,可是和公鑰加密徹底顛倒過來:仍然公佈公鑰,可是用你的私鑰加密數據,而後把加密的數據公佈出去,這就是數字簽名。
你可能問,這有什麼用,公鑰能夠解開私鑰加密,我還加密發出去,不是畫蛇添足嗎?
是的,可是數字簽名的做用原本就不是保證數據的機密性,而是證實你的身份,證實這些數據確實是由你本人發出的。
你想一想,你的私鑰加密的數據,只有你的公鑰才能解開,那麼若是一份加密數據可以被你的公鑰解開,不就說明這份數據是你(私鑰持有者)本人發佈的嗎?
固然,加密數據僅僅是一個簽名,簽名應該和數據一同發出,具體流程應該是:
一、Bob 生成公鑰和私鑰,而後把公鑰公佈出去,私鑰本身保留。
二、用私鑰加密數據做爲簽名,而後將數據附帶着簽名一同發佈出去。
三、Alice 收到數據和簽名,須要檢查此份數據是不是 Bob 所發出,因而用 Bob 以前發出的公鑰嘗試解密簽名,將收到的數據和簽名解密後的結果做對比,若是徹底相同,說明數據沒被篡改,且確實由 Bob 發出。
爲何 Alice 這麼確定呢,畢竟數據和簽名是兩部分,均可以被掉包呀?緣由以下:
一、若是有人修改了數據,那麼 Alice 解密簽名以後,對比發現兩者不一致,察覺出異常。
二、若是有人替換了簽名,那麼 Alice 用 Bob 的公鑰只能解出一串亂碼,顯然和數據不一致。
三、也許有人企圖修改數據,而後將修改以後的數據製成簽名,使得 Alice 的對比沒法發現不一致;可是一旦解開簽名,就不可能再從新生成 Bob 的簽名了,由於沒有 Bob 的私鑰。
綜上,數字簽名能夠必定程度上認證數據的來源。之因此說是必定程度上,是由於這種方式依然可能受到中間人***。一旦涉及公鑰的發佈,接收方就可能收到中間人的假公鑰,進行錯誤的認證,這個問題始終避免不了。
說來好笑,數字簽名就是驗證對方身份的一種方式,可是前提是對方的身份必須是真的… 這彷佛陷入一個先有雞仍是先有蛋的死循環,要想肯定對方的身份,必須有一個信任的源頭,不然的話,再多的流程也只是在轉移問題,而不是真正解決問題。
證書其實就是公鑰 + 簽名,由第三方認證機構頒發。引入可信任的第三方,是終結信任循環的一種可行方案。
證書認證的流程大體以下:
一、Bob 去可信任的認證機構證明本人真實身份,並提供本身的公鑰。
二、Alice 想跟 Bob 通訊,首先向認證機構請求 Bob 的公鑰,認證機構會把一張證書(Bob 的公鑰以及本身對其公鑰的簽名)發送給 Alice。
三、Alice 檢查簽名,肯定該公鑰確實由這家認證機構發送,中途未被篡改。
四、Alice 經過這個公鑰加密數據,開始和 Bob 通訊。
PS:以上只是爲了說明,證書只須要安裝一次,並不須要每次都向認證機構請求;通常是服務器直接給客戶端發送證書,而不是認證機構。
也許有人問,Alice 要想經過數字簽名肯定證書的有效性,前提是要有該機構的(認證)公鑰,這不是又回到剛纔的死循環了嗎?
咱們安裝的正規瀏覽器中都預存了正規認證機構的證書(包含其公鑰),用於確認機構身份,因此說證書的認證是可信的。
Bob 向機構提供公鑰的過程當中,須要提供不少我的信息進行身份驗證,比較嚴格,因此說也算是可靠的。
得到了 Bob 的可信公鑰,Alice 和 Bob 之間的通訊基於加密算法的保護,是徹底無懈可擊的。
如今的正規網站,大都使用 HTTPS 協議,就是在 HTTP 協議和 TCP 協議之間加了一個 SSL/TLS 安全層。在你的瀏覽器和網站服務器完成 TCP 握手後,SSL 協議層也會進行 SSL 握手交換安全參數,其中就包含該網站的證書,以便瀏覽器驗證站點身份。SSL 安全層驗證完成以後,上層的 HTTP 協議內容都會被加密,保證數據的安全傳輸。
這樣一來,傳統的中間人***就幾乎沒有了生存空間,***手段只能由技術缺陷轉變爲坑蒙拐騙。事實上,這種手段的效果反而更高效,好比我就發現網上很多下載網站發佈的瀏覽器,不只包含亂七八糟的導航和收藏網址,還包含一些不正規的認證機構證書。任何人均可以申請證書,這些不正規證書極可能形成安全隱患。
對稱性加密算法使用同一個密鑰加密和解密,難以破解,加密速度較快,可是存在密鑰配送問題。
Diffie-Hellman 密鑰交換算法可讓雙方「心有靈犀一點通」,必定程度解決密鑰配送問題,可是沒法驗證通訊方的身份,因此可能受到中間人***。
非對稱性加密算法生成一對兒密鑰,把加密和解密的工做分開了。
RSA 算法做爲經典的非對稱加密算法,有兩種用途:若是用於加密,能夠把公鑰發佈出去用於加密,只有本身的私鑰能夠解密,保證了數據的機密性;若是用於數字簽名,把公鑰發佈出去後,用私鑰加密數據做爲簽名,以證實該數據由私鑰持有者所發送。可是不管那種用法,涉及公鑰的發佈,都沒法避免中間人***。
公鑰證書就是公鑰 + 簽名,由可信任的第三方認證機構頒發。因爲正規瀏覽器都預裝了可信的認證機構的公鑰,因此能夠有效防止中間人***。
HTTPS 協議中的 SSL/TLS 安全層會組合使用以上幾種加密方式,因此說不要安裝非正規的瀏覽器,不要亂安裝未知來源的證書。
密碼技術只是安全的一小部分,即使是經過正規機構認證的 HTTPS 站點,也不意味着可信任,只能說明其數據傳輸是安全的。技術永遠不可能真正保護你,最重要的仍是得提升我的的安全防範意識,多留心眼兒,謹慎處理敏感數據。
_____________