TLS和HTTPS加密,公鑰私鑰體系
寫在最前面
最近一段時間,國內各大網站紛紛用上了https連接,在訪問這些網站的時候,很多瀏覽器會給予“特別關照”,給它們的鏈接旁邊加上一個綠色的小鎖,那么,什么是https,它與網絡安全又有什么關系呢?今天我們就來談談https與tls(傳輸層安全)。
我不是計算機專業(yè)的學生,沒有系統(tǒng)學過計算機網絡相關的知識,寫這篇文章是因為之前給自己挖過一個坑不得不填上,文章內容大部分來自于網絡,我大概只是做了下整合,所以如果有什么錯誤還請大家指出,謝謝。
http之罪,為什么不安全?
http協議在制定之初,其目的僅僅是為了方便地完成html網頁內容的交換,沒有過多考慮安全性問題,http連接不進行身份認證,同時內容是明文傳輸,因此采用http協議傳輸的內容對于任何人來說都是公開的;這帶來了很嚴重的安全問題:如果有人創(chuàng)建一個開放熱點,并對連接該熱點的用戶http數據進行抓包,便可以輕松獲取用戶的用戶名、密碼或者其他敏感信息;這里有一個通過Wireshark抓包獲取用戶名、密碼的例子:Wireshark如何抓明文用戶名和密碼;其它情況下還可以做到的,諸如分析你瀏覽的頁面內容、替換頁面內容等等,在此不再一一舉例;
什么是https/TLS?
HTTPS(全稱:Hyper Text Transfer Protocol over Secure Socket Layer),是以安全為目標的HTTP通道,簡單講是HTTP的安全版,它建立在SSL(Secure Sockets Layer 安全套接層)之上,其目的是保障網絡數據傳輸的安全。TLS(Transport Layer Security 傳輸層安全)是SSL的繼任者,從對應關系上看應該可以算是SSL的子集??梢哉f,目前的https都是基于TLS而得以實現的,因此下面我們就來著重講一講TLS的實現及其安全性。
TLS
一個形象的解釋(感謝知乎的天才老哥們)
生活中大家應該都用過一種鎖,你可以用對應的鑰匙打開它,打開之后如果拔出鑰匙,你將合不上鎖(我知道現在很多鎖拔出鑰匙后也能合上了,但請大家稍微配合一下_(:з)∠)_):
下面我們用鎖來講一個故事,幫助大家更好地理解TLS的工作方式。
A和B是分隔兩地的商業(yè)伙伴,兩地之間除了信件往來沒有其他的通訊方式,并且兩地之間的信件通行狀況非常糟糕,經常有人偽裝成郵遞員私拆信件甚至更改信件內容,曾經也有人用普通鎖鎖上堅固的盒子來快遞,但是并沒有安全的方法能把鑰匙安全地送給對方而不被中間人復制;A與B想要互通信件,但是又不想讓交流的內容被別人知道;恰好兩人都了解有一個很聰明的人發(fā)明了一種鎖,這種鎖不同于以往,它需要用兩把鑰匙分別完成開鎖和合鎖的過程,一把鑰匙只能開不能合,另一把只能合不能開(非對稱加密),于是兩人在信件內容沒有被篡改的情況下約定了一種交流方式:
* A現在手持一把特殊鎖{Special_Lock}和兩把對應的鑰匙{Public_Key}(公鑰)與{Private_Key}(私鑰),其中{Public_Key}只能用來合鎖,{Private_Key}只能用來開鎖;首先A用私鑰打開{Special_Lock},并把打開的{Special_Lock}與{Public_Key}通過快遞寄給B; * B收到寄來的{Special_Lock}和{Public_Key}之后,把一把普通的鎖{Lock_B}(對稱加密)和鑰匙{Key_B1}裝到一個足夠堅固不會被破壞的盒子里,用寄來的{Special_Lock}鎖上(鎖的時候需要用到{Public_Key}),并寄還給A,同時B手上還有這把普通鎖的備用鑰匙{Key_B2},它與{Key_B1}一模一樣;
* A收到B寄來的使用{Special_Lock}鎖著的包裹后,悄悄地拿出藏起來的{Private_Key},把特殊鎖打開,拿到了屬于B的{Lock_B}和能夠鎖上、打開這把鎖的{Key_B1},于是A很開心地寫了封“Hello world!”,找了個堅固的盒子放了進去,并且用{Lock_B}和對應的鑰匙{Key_B1}鎖上了盒子,保留了{Key_B1}并把盒子寄還給了B * B收到快遞后,使用備用鑰匙{Key_B2}打開了鎖{Lock_B},得到了信件;
完成以上動作之后:A擁有了B提供的鎖與鑰匙,此后兩人便可以用這個鎖來進行安全的通信({Lock_B}的鑰匙只有兩人擁有),也就是說,兩人通過非對稱加密的方式協商了一個{Lock_B}以及對應的鑰匙{Key_B1}、{Key_B2},此后一直通過對稱加密{Lock_B}進行通訊;
現在還有一點疑問,誠然,有了第一步的特殊鎖之后,送信人員不可能打開這把鎖了(因為TA沒有私鑰{Private_Key}),但這還有一個問題,如果送信人員M悄悄扣留了A的特殊鎖及其公鑰,然后送給B一個自己的特殊鎖及其公鑰{FAKE_Special_Lock}和{FAKE_Public_Key},在B給A回信送{Lock_B}以及{Key_B1}的時候,M就可以用{FAKE_Private_Key}打開那個盒子,取出鎖和鑰匙,復制一份鑰匙,并用之前扣留的{Special_Lock}和{Public_Key}封裝起來還給A;經過這個操作,M在兩者都不知情的情況下獲得了接下來A、B通信所需要使用的加密密碼{Key_B1};
對此TLS提出了一個解決辦法: * 找一個德高望重的人(CA),用他獨一無二的簽名給最初的A的那把{Special_Lock}做一個認證:這把鎖是A所有——由“X”CA認證;這名德高望重的人X恪守規(guī)矩——絕對不會給不是A的鎖作這個認證;因為這位大人的簽名沒人能模仿,因此B收到特殊鎖之后只要看一眼簽名是不是發(fā)給A的就知道鎖有沒有被掉包過了,當然前提是,A、B都信任這位德高望重的大人。
可是某一天A需要和一位與B住在同一城市的商業(yè)伙伴C聯系,A與C想要效仿之前的操作建立一個安全的聯系方式,但是C并不信任X這個人,因此B只好又找了個德高望重的人Y,A、B、C都信任這個Y先生;Y先生很忙,沒法直接認證A的特殊鎖,因此Y僅僅簽名認證了X,并委托X在鎖上加上了“X經過Y的‘CA認證,可以認證鎖的從屬’”的字樣;下次C拿到{Special_Lock}之后,看到這行字,就選擇信任X對特殊鎖的認證,并成功和A建立了加密通信;
A的商業(yè)伙伴越來越多,人們的信任關系錯綜復雜,即使找來更有威望的Z給Y先生認證,也終究不是辦法,最后人們選出了一個最有威望的人“ROOT”,并且大家約定,只要是“ROOT”認證過的人或者是鎖,大家都無條件地信任;這位“ROOT”就是根CA,TA所寫的“ROOT認證xxx”的內容,稱為根證書。
至此信件的安全問題已經被完美解決了,然而在實際操作中還有一些細節(jié),比如非對稱加密很復雜,消耗的計算時間較長,因此不用在正常的通信中,僅作為鏈接發(fā)起時,協商對稱加密的密鑰時使用,正常通信是使用對稱加密進行的。
非對稱加密
因為本人實在水平有限,因此這部整段搬運了知乎用戶劉叔的文章非對稱加密算法與TLS中的內容,侵刪……
RSA利用的核心思想就是大素數分解的問題。這個問題雖然理解起來簡單,但是破解起來非常難,以至于RSA至今為止仍舊是應用最廣泛的非對稱加密算法。雖然描述起來是兩個大素數分解因式,但是實際的實現相對復雜很多。不是任何的兩個大素數都可以用,而必須要滿足一系列的條件。本書不是一本密碼學的書,不進行深入探討。
數學上,RSA算法的原理非常簡單(密文為X,明文為A):
加密:
解密:
也就是說加密和解密的運算形式是完全一樣的,公式里面或者叫做離散對數。RSA算法的數學基礎就建立在已知其他值,D不可解的前提下。這里面E和N共同組成公鑰,D和N共同組成私鑰。所以整個加密算法剩下的唯一問題就是如何確定E,D,N三個字母了。
確定的方法是取兩個大素數p和q。和相乘就是:N=pq。在計算和之前要計算一個中間值,這個值叫做:L=lcm(p-1,q-1)。lcm的意思是最小公倍數,也就是說的值等于和的最小公倍數。下面就可以得到了:gcd(E,L)=1。gcd表示最大公約數,也就是說的值為與互質的數。這個數在數學上的求法并不是多么的高端,而是簡單的隨機生成大數,然后與求最大公約數,看看結果是不是1。也就是說是一個暴力嘗試的方法。得到了E和N,我們就得到了公鑰了。D的值是根據E計算得到的:
解這個式子就可以得到D,也就是得到了私鑰。整個RSA過程就結束了。RSA的加密與解密非常的簡介易懂,這也是其迅速普及的原因。廣泛使用的原因。整個RSA的安全性依賴于分解,N對外部是已知的,已知N的情況下,如果能分解得到N=pq,那么RSA就沒有安全性可言。所以也可以說整個RSA的安全性就依賴于大素數分解因式了,當然也可以說依賴于求離散對數問題,他們是一個問題的兩個方面,主要的破解方式是大素數分解因式。主要依賴于離散對數安全性的非對稱加密算法是EIGamal算法。
ECC橢圓曲線
另一個常用的加密算法是ECC算法,采用橢圓曲線來構造密鑰:
Server Key Exchange里面的最重要的參數就是ECDHE算法需要構造的密碼學參數??梢钥吹揭粋€是橢圓曲線的名字:secp256r1。這個橢圓曲線不但在HTTPS中,還在比特幣中有廣泛的應用,所有的橢圓曲線實際上都是方程:
這里面兩個參數,這個橢圓曲線是一大類的曲線,對于secp256r1來說,a=0, b=7。所以對于secp256r1來說,這條曲線是,參數的取值并不是隨便取的,必須要滿足一定的條件,并且一條密碼學曲線都是固定取值的。不同的,會得到非常不一樣形狀的圖形,不同的圖形有不同的用途,我們這里討論的secp256r1曲線的圖形如下:
這條曲線的形狀如圖。在密碼學上,所有的橢圓曲線都是使用的有限域版本GF(p),所以p也是一個橢圓曲線的一個值。對于secp256k1來說,他的,橢圓曲線的方程是
橢圓曲線之所以被選擇出來是因為他有眾多非常有意思的特性,例如在橢圓曲線上拉一條直線,經過三個點,那三個點的和是0(那就看曲線怎么定義和這個操作了,這里是數論里的阿貝爾群)。本質上,使用橢圓曲線是使用了橢圓曲線的性質來得到一個數學運算系統(tǒng),最終在參與密碼學計算的是數論系統(tǒng),與橢圓曲線就沒有太大關系了,但是仍然可以用曲線來理解,因為數論運算是基于橢圓曲線構造的。
當這個橢圓曲線算法用于非對稱加密的密鑰交換的時候,我們知道兩個人都能看到對方的公鑰,并且都知道自己的私鑰。橢圓曲線算法在使用的時候能夠看到與RSA的一個最大的不同,就是RSA需要一個私鑰,橢圓曲線并不需要。對于橢圓曲線做密鑰交換,每一次通信的私鑰和公鑰都是臨時生成的,這也是橢圓曲線比RSA安全性高的原因。因為RSA一旦私鑰泄漏,歷史的加密數據都能破解,而橢圓曲線不能。每一次通信都用完全不同的私鑰公鑰對進行信道協商。所以對于橢圓曲線來說,在每一次通信的時候都會首先生成這個私鑰和公鑰,生成私鑰的方法就是在橢圓曲線上取一個點,根據上面說過的三點和等于0的特性,讓兩個點重合,重合之后,這條曲線就是橢圓的切線,與橢圓相交于兩個點。非切點的那個點就是私鑰,切點取反再多切線得到一個新的切點,如果多次取反做切點就得到了公鑰點。Q=NG,G是私鑰點,N是做切線的次數,是公鑰。已知Q,算不出G,就是橢圓曲線生成公鑰私鑰的原理了。這里面對于橢圓曲線來說,N是一個公開的常數,雙方都知道并且相同,也就是說,這個數學難題是已知了一個點,求次反向的求切線運算得到的那個點。這個點是計算難度上得不出來的。也就是說已知一點曲線上的切點,得到切線的難度比已知一個隨意點,對曲線做切線的計算度復雜很多,多到多次計算就是計算不可能問題。
當橢圓曲線生成的公鑰和私鑰用于交換的時候,因為雙方已經互換了公鑰,這個計算過程就變成了雙方同時用自己的私鑰乘以對方的公鑰。橢圓曲線的神奇特性保證了得到的結果是一樣的,也就是說是得到了同一個點。這個點就是協商得到的對稱加密的密鑰。
總結
已經寫昏了……總結先摸了,哪天想起來了再寫吧……