深入淺出ssl技術
安全,是互聯網服務中和應用中最重要也是最容易被忽視的問題。大多數廠商在系統開發初期對安全問題考慮甚少,甚至直接忽略。本文旨在對互聯網安全中扮演重要角色的ssl加密技術進行介紹。
我們都在互聯網中“裸奔”
internet技術在設計之初,基本沒有考慮安全問題,并沒有對數據傳輸中的安全問題進行太多規范和考慮。時至今日,tcp/ip已經成為互聯網數據通訊的事實標準,但是還是有大量的服務和應用沒有采用任何加密技術,我們的每一次數據傳輸,每一次互聯網行為,其實都是在“裸奔”。當你進行一次搜索,發布一條日志,閱讀一條新聞時,你的行跡都完全暴露于互聯網之中。可能你要問,上了十幾年網了,貌似也沒啥啊?這是因為你的記錄在茫茫互聯網之海中不過滄海一粟,很難引起別有用心之人的興趣罷了。這就好比你現在去街上裸奔,必定引起眾人注目;但是如果全世界大部分都在裸奔,穿衣服的是少數時,也沒有人關注你了(⊙o⊙)…也許你又要問一個問題了,既然互聯網這么不安全,那些廠商都不做點什么保護大家隱私么?是的,時至今日,像微博這種有大量用戶數據的網站依然默認沒有采用加密傳輸。這是為什么呢?原因很多。
- 成本問題。很多產品在開發初期的重心都是focus在業務上,對安全考慮甚少,業務發展起來后,再考慮安全問題也會涉及大量的業務修改和代碼升級,很多廠商包著僥幸心理,在“出大事”之前都不愿意投入人力和時間去解決安全問題。(還記得csdn密碼泄露事件吧?)
- 性能問題。數據的加密和解密都會消耗額外的運算資源,很多廠商處于成本考慮,都會選擇敏感業務加密,不敏感業務明文的策略。(比如你在淘寶上看商品的時候是不加密的,一旦要付錢了,你懂的)
- 業務問題。有一些網站確實是沒有必要加密的,比如新聞站點。但是在web2.0時代,大部分的新聞站點還是攜帶很多用戶信息的,這里不加密也是廠商聊以自慰而已。
說了這么多原因,你發現了么?以上其實都是廠商從自己的角度出發,要不是為了省成本,要不是覺得不必要,都是廠商的借口。身為用戶的你,其實是在不知情的情況下被廠商扒光了衣服,然后告訴你你穿了衣服別擔心(皇帝的新衣?)。當然這種情況近些年已經大大改善,國內網一些主要站點非死book,google, baidu等,已經痛下決心,全站升級為加密技術了。
如何保護我們的隱私
在以上所述的明文通信方式中,都面臨以下三種風險:
- 竊聽:第三方通過抓包工具抓取到的內容可以直接被理解
- 篡改:第三方可以修改通信的內容然后再轉發
- 偽裝:第三方可以假冒發送方或接收方進行通信
如何解決這三點風險呢?如果我們能做到讓上面那個可惡的“第三方”無法抓取我們的通信內容,上面的三個風險全部一下化解了。但是現實是殘酷的,我們沒法做到,這是internet的基礎通信架構決定的。要解決問題,只能試試各自擊破,下面一一分析
- 針對竊聽,如果對傳輸的內容進行加密,就算第三方抓取到通信內容,也無法理解。加密技術早在二戰時期就開始成為科學家們研究熱點,目前已經有很多成熟方案。
- 針對篡改,需要在通信雙方增加校驗機制,一旦通信內容被篡改,就可以通過校驗立即被發現,通信雙方可以不信任該消息。
- 針對偽裝,通信雙方必須配備由權威第三方機構頒發的通信證書,以此證明自己的身份。
所有的加密技術都是某種程度基于一個或多個密鑰,最常見的就是對稱加密技術:
通信雙方持有相同的密鑰,可同時用于通信內容的加密解密。
對稱加密的根本數學原理就是單向函數,對于f(a)=b,輸入a可以求出b,但是知道b很難猜出a。
也許你會想,這不,只要雙方都有同一個密鑰,通信的內容就很容易被加密了,也只有收信人才能解密理解,竊聽風險不就迎刃而解了么?so easy!確實如此,但是有兩個問題就很蛋疼了:
- 密鑰如何分發?假如alice和bob需要進行加密通訊,但是在他們進行加密通訊之前alice總得想辦法告訴bob她的密鑰是啥吧!但是alice又不能通過網絡明文發給bob啊(因為網絡不安全啊魂淡)!alice能做的只能是把密鑰寫在紙條上,寫信寄給bob了(呵呵了)。如果alice要給jim,tony…等等各種人通信,我已經不敢想象這有多蛋疼了…
- 密鑰泄露風險。如果alice和bob協商好的通信蜜鑰被任何一方泄露,后果都是不堪設想的。任何人都能收到alice發給bob的“私密信息”,任何人都能假裝alice給bob發信…
對于第二個問題,如果我們能夠每次通訊都使用不同的密鑰,就算密鑰泄露,下次通話之前泄露的密鑰還是沒有用的。這時,如何安全的進行密鑰協商就成了最關鍵的問題。這時就可以采用非對稱加密技術:
非對稱加密算法需要兩個密鑰:公開密鑰(publickey)和私有密鑰(privatekey)。公開密鑰與私有密鑰是一對,如果用公開密鑰對數據進行加密,只有用對應的私有密鑰才能解密;如果用私有密鑰對數據進行加密,那么只有用對應的公開密鑰才能解密。
非對稱加密的基本數學原理是大數難分解。以最常用的rsa算法為例,其基本原理如下:
1.隨機選擇兩個大質數p和q,p不等于q,計算N=pq;
2.選擇一個大于1小于N的自然數e,e必須與(p-1)×(q-1)互素。
3.用公式計算出d:(d×e)mod( (p-1)×(q-1) )= 1 。
4.銷毀p和q。
最終得到的N和e就是“公鑰”,N和d就是“私鑰”,發送方使用公鑰去加密數據,接收方只有使用私鑰才能解開數據內容。
在通信之前alice的公鑰是公開的,所以無論是bob還是tony,以及其他任何人,都是知道這個公鑰的。alice和bob在通信之前,可以用自己的私鑰加密一些有意義的信息,bob通過公鑰解密來驗證這個信息,如果是對的,則證明alice確實持有該公鑰對應的私鑰,bob則放心的與其通信。這時alice可以選擇一個對稱加密算法并隨機生成一個密鑰發送給bob,后續通話他們采用該密鑰對稱加密通信即可。好吧,我相信你一定又有兩個疑問,;-)
- 干嗎還要回到對稱加密來通信啊,直接全稱非對稱通信不行么?答案是可以,但是非對稱加密的開銷非常大,會對通信速度造成顯著影響,所以強烈不建議這樣。
- bob怎么知道他手上拿到的alice的公鑰就是alice給的呢?萬一有黑心的搗蛋鬼到處謊稱自己是alice并散播自己制作的公鑰給所有人呢?(如何證明你媽是你媽(⊙o⊙)…)答案是,bob確實無法知道,所以一般需要有權威的第三方機構,對alice進行認證,bob也會到第三方權威機構去獲取alice的公鑰,而不是隨便相信某個無名小卒。
- 通信雙方如何校驗?good question,我們可以在alice和bob的所有通話中增加一個校驗和,比較常用的有md5或者sha1等,這樣,雙方針對通信內容計算的校驗和如果不匹配,那就說明消息被篡改過啦!
好吧,上面講的這些不是ssl,但是基本上涵蓋ssl的基本原理啦!哈哈,其實也不是那么復雜。下面再具體講下ssl的工作流程。
ssl工作流程
ssl工作流程大體可分為握手和記錄兩個階段,其中握手階段是不包含實際需要傳輸的數據,通信數據都是在握手成功后,在記錄階段傳送。記錄階段,發送方對傳輸的數據進行壓縮、計算校驗和并采用協商的對稱密鑰進行加密,接收方通過該過程的逆過程進行解密。ssl工作流中關鍵的是握手階段,下面重點介紹。
ssl握手允許服務器和客戶機相互驗證,協商加密和校驗算法以及保密密鑰,用來保護在SSL記錄中發送的數據。握手協議是在應用程序的數據傳輸之前使用的。握手協議的4個階段如圖:
第一階段:問候
SSL握手的第一階段啟動邏輯連接,雙方互通信息。首先客戶機向服務器發出client hello消息并等待服務器響應,隨后服務器向客戶機返回server hello消息,對client hello消息中的信息進行確認。
Client Hello消息包括Version(客戶端支持的ssl版本號),Random(一個客戶端生成的隨機數,用于生成對稱密鑰),Session id(會話id),Cipher suite(客戶端支持的加密算法表),Compression method(客戶端支持的壓縮算法)等信息。
Server Hello服務器用ServerHello信息應答客戶,包括Version(取客戶端支持的最高版本號和服務器支持的最高版本號的較低者),Random(一個服務器生成的隨機數,也是用于生成對稱密鑰),Session id(會話id),Cipher(從客戶端支持的加密算法中選擇的一個算法),Compression(從客戶端支持的壓縮算法中選擇的一個算法)
第二階段: 服務器鑒別與密鑰交換
該階段只有服務端向客戶端發送消息。該階段分為4步:
(a)服務器將數字證書發給客戶端
(b)服務器密鑰交換(可選):這里視密鑰交換算法而定
(c)證書請求(可選):服務端可能會要求客戶自身進行驗證。
(d)服務器發送結束命令,結束該階段
第三階段:密鑰鑒定與密鑰交換:
該階段只有客戶端向服務器發送消息。該階段分為3步:
(a)證書(可選):為了對服務器證明自身,客戶要發送一個證書信息。
(b)密鑰交換(Pre-master-key):這里客戶端生成的第二個隨機數,連通之前生成的兩個隨機數共同作為對稱密鑰的生成因子。使用服務端的公鑰進行加密后將該隨機數發送給服務端。
(c)證書驗證(可選),對Pre-master-key進行簽名,證明擁有(a)證書的公鑰。
第四階段:完成
客戶機啟動SSL握手第4階段,整個握手過程結束。該階段分為4步,前2個消息來自客戶機,后2個消息來自服務器。
(a)客戶端發送編碼改變通知,表示隨后的信息都將用雙方商定的加密方法和密鑰發送。
(b)客戶端握手結束通知,表示客戶端的握手階段已經結束。
(c)服務器發送編碼改變通知,表示隨后的信息都將用雙方商定的加密方法和密鑰發送。
(d)服務器握手結束通知,表示客戶端的握手階段已經結束。
現在和將來
如今,ssl已經基本成為了互聯網安全加密的事實標準。從谷歌、非死book、BAT這種一線廠商,到初創企業,甚至銀行、券商等金融機構,都在大量使用ssl技術進行加密通信。世界似乎很美好!我們的互聯網已經安全了么?
前不久,使用最廣泛的開源ssl實現庫openssl被發現重大漏洞,人稱Heartbleed漏洞。這次漏洞的嚴重性和影響范圍之大堪稱慘烈。這里就不做詳細介紹了,具體分析可以看這里。隨后不久,又爆出了同樣相當嚴重的FREAK漏洞。是的,很多時候我們大意了,以為大家都用,肯定沒啥大問題。也許有人要怒吼一聲:不如自己設計一個閉源的加密算法,源代碼沒有,別人肯定難破解了!強烈不建議這樣,因為
- 加密算法的安全性和閉源開源沒有太多關聯。一個加密算法的本身安全性其實是純數學問題,開發者不是密碼專家,基本不可能設計出現在最常用的加密算法安全級別的加密算法,就算你設計的算法閉源,相信破解難度很可能還小于目前的公開算法!
- 軟件的bug和漏洞永遠是無法避免的。就算是不公開的實現,也很可能有各種漏洞。反而開源的加密算法實現漏洞會少一些,因為經過很多人圍觀、測試以及修正。
所以,除非你是做密碼學研究,工程中還是建議別折騰了!
相信ssl技術在未來能依然保持主流地位,我們也能看到ssl技術一直在發展,比如這個項目就很贊,可以讓我們從證書申請的復雜申請流程和不菲申請費用中解脫出來!這也是ssl部署最繁瑣的痛點。
來自:http://blog.pandocloud.com/?p=376