一篇文章帶你弄懂Kerberos的設計思路

榴蓮千層ya發表於2023-02-17


這篇文章將會帶大家詳細梳理和理解Kerberos的設計思路。

Basic
為了減輕伺服器的負擔,我們需要設計一個專門的認證伺服器AS,儲存所有使用者的口令,認證了使用者身份之後再通知應用伺服器

引入ticket:客戶把自己的ID(IDc),要訪問的伺服器的ID (IDv) 和自己的口令 (Pc) 發給AS,AS查驗使用者和口令是否合法,是否有權訪問V,都符合就給客戶發一張ticket,客戶憑藉ticket和IDc去訪問V

$ticket=E_{Kv}[IDc, ADc(使用者網路地址), IDv] $,ticket中包含的資訊,誰的票,訪問哪兒的票,這些資訊用V與AS之間的共享金鑰Kv加密,加密的同時也認證了AS(避免敵手假扮AS)

上述機制中還存在4個問題

Q1:訪問多個伺服器需要多次申請票據,多次輸入口令會造成不安全

solution:

  1. 引入票據許可伺服器(TGS,類似售票處),AS只認證,認證之後發放票據許可票據(類似允許你買票的身份證明)\(Ticket_{tgs}\),用來訪問V的服務許可票據\(TicketV\)由TGS來發。這樣ID和password就只在認證時使用1次
  2. 一類V之間可以共享Kv和票據

Q2:口令明文傳送(C->AS)

solution: AS與C之間共享使用者口令Pc->Kc,AS與TGS之間共享Ktgs,TGS和V之間共享Kv,不用再傳送口令

Q3:票據重用

solution:引入時間戳(TS,訊息傳送時間)和有效期(LT)

PS:時間戳和序列號可以保證訊息的新鮮性,但很容易被預測,可以使用挑戰-響應協議,用隨機數來防止重用,但複雜度比較高

Q4:票據冒領

solution:給誰的資訊就用誰的金鑰來加密,防止被冒領

但是TGS沒有Kc,C也沒有Kv,於是就由AS來幫TGS和C之間生成\(K_{c,tgs}\),TGS幫C和V生成\(K_{c,v}\),同時,這兩個金鑰也要放到票據中,用來身份認證,防止敵手等到使用者退出之後使用竊聽到的票據備份進行重用

AS為TGS和C生成了\(K_{c,tgs}\)後,就連同\(Ticket_{tgs}\)一起發給C,TGS收到\(Ticket_{tgs}\)後,解密得到裡面的\(K_{c,tgs}\),然後回覆C的訊息就用\(K_{c,tgs}\)加密。

現在我們解決了以上四個問題,來梳理一下,現在的票據長啥樣?

票據包含雙方的ID,為雙方生成的共享金鑰,TS,TL,給誰的票據就用誰的金鑰加密

\(Ticket_{tgs}=E_{Ktgs}\{Kc,tgs, IDc, ADc, IDtgs, TS_2, LT_2\}\)

更近一步的最佳化:C和V之間也要改成雙向認證,C也要確認V的身份,TGS、V回覆C的時候最外層就用會話金鑰加密(信任第三方)

V回覆C{\(TS_5\)+1} ,用\(TS_5\)(使用者傳送訊息的時戳)可以保證每次都不一樣,類似TCP的序列號,+1可以記錄互動了多少次

最後我們就得到了Kerberos的整個流程:

Kerbores流程示意圖

相關文章