1.15 RC2加密算法
RC2是Ron Rivest于1987年為RSA數據安全公司(RSADSI)設計的專用分組加密算法,它與RC4和RC5加密算法一起被收入RSADSI的加密工具箱BSAVE。1996年2月有人通過逆性分析,將該加密算法的細節公布在互聯網上。1997年6月RSADSI正式公布了RC2加密算法,并將它提交給國際互聯網工程任務組(Internet Engineering Task Force, IETF)作為國際互聯網上的標準草案(Internet-Draft)進行評論。RC2加密算法是RSADSI開發的、并已提交IETF作為標準審查的電子郵件安全協議S/MIME的重要組成部分,RSADSI公布RC2加密算法是為了讓IETF對它進行審查,這是對S/MIME進行標準化工作的一部分。
RC2加密算法的輸入、輸出分組長度為64比特,輸入密鑰長度可變(為1~128字節)。輸入密鑰經密鑰擴展算法生成128字節的擴展密鑰 L[0]~L[127],作為進行加、脫密運算時的層密鑰。RC2加密算法以16比特的字為單位進行運算,輸入的64比特明文先預置4個字R[0]~R[3],然后經兩種基本運算——mix(混亂)和mash(掩亂)多層迭代生成密文,共有16層mix運算,并在第5~6層之間和第11~12層mix運算之間分別夾有一層mash運算。
密鑰擴展算法是由輸入密鑰和π表生成128字節的層密鑰的過程。π表是0~255的排列,是由π=3.14159…的各位數值決定的。π表的具體值如表1.15.1所示。
表1.15.1 π表的具體值

由表1.15.1可知,π(0)=d9, π(1)=78, …, π(ff)=ad。
令t為輸入密鑰的字節數,s為有效密鑰比特數的上界(注意:這里輸入密鑰長度和有效密鑰長度不是一回事,有效密鑰長度的比特數為min(8t, s),即窮盡搜索密鑰時需要的窮盡量為min(28t,2s)。
令t1=‘s/8’為s比特對應字節數的上界,s1=(s mod 8)+(‘(s+1) /8’-t1)+8,即s比特按8比特劃分余下的比特數,但當s能被8整除時,s1=8。密鑰擴展過程如下:
(1)將輸入的t字節密鑰置入L[0], …, L[t-1]。
(2)對于i=t, t+1, …,127,計算:
L[i]=π[(L[i-1]+L[i-t])mod 256]
(3)計算:
L[128-t1]=π[L[128-t1]&(2S1-1)]
式中,“&”表示按比特“與”,該運算以L[128-t1]的低位s1比特為地址碼,取π表中的相應值作為新的L[128-t1]。
(4)對于i=127-t1, …,0,計算:
L[i]=π(L[i+1]⊕L[i+t1])
經過上述四步運算可得層密鑰 L[0]~L[127],其中步驟(3)和(4)是為了控制有效密鑰比特數不超過 s,以適應美國政府對出口密碼的限制要求。當美國政府限制出口密碼的密鑰長度不能超過40比特時,只要將有效密鑰長度的上界s設置為40即可。即使用戶采用很長的密鑰(可達128字節=1024比特),但實際有效密鑰長度小于或等于s。這是對密碼算法設置陷門的方法之一。
RC2加密算法的加密過程由mix和mash兩個基本運算組成,運算以16比特為單位(稱其為字)進行。層密鑰 L[0]~L[127]以16比特的字作為單位,記為 K[0]~K[63],這時K[i]=L[2i]+256L[2i+1]。每層的mix用4個K[i]作為層密鑰,第1層的mix用K[0]~K[3],第2層的mix用K[4]~K[7], …,第i層的mix用K[4(i-1)]~K[4(i-1)+3],16層共用64個K[i],所以K[0]~K[63]中的每個字恰好都被用一次。下面先出mix和mash的概念,然后介紹一個明文分組的加密過程。
對R[i]進行mix運算由以下三步組成:
R [i]=R[i]+K[j]+(R[i-1]&R[i-2])+(R[i-1]&R[i-3])
j=j+ 1
R[i]=R[i]<<<r[i]
式中,“+”為模216加,“&”為按比特與,x<<<r[i]表示x循環左移r[i]位,r[0]~r[3]分別表示1、2、3、5。R[i]中的i進行的是模4運算,如R[-1]=R[3]。
對R[i]進行mix運算,實際上就是在R[i]上加上相應的層密鑰K[j],同時在R[i-1]的指示下選取 R[i-2]或 R[i-3]的比特合成一個16比特的字,即對 R[i-1]為“0”的比特、取 R[i-3]的相應比特;對R[i-1]為“1”的比特,取R[i-2]的相應比特,組成一個字,加到R[i]上,然后循環左移r[i]位。這相當于一個非平衡的Feistel結構。
每層的mix運算是對i=0、1、2、3逐一對R[i]進行mix運算。
mash R[i]的定義為:
R[i]=R[i]+K[R[i-1]&63]
即把密鑰擴展中的一個字加到R[i]上,以此攪亂R[i]。具體選取密鑰擴展中的K[0]~K[63]中的哪個字,由R[i-1]的低6比特決定,所以K[i]的選取依賴于數據。
每層的mash運算是對i=0、1、2、3逐一進行mash R[i]。
一個明文分組的加密過程如下:
(1)用64比特的輸入明文分組預置R[0]~R[3];
(2)由輸入密鑰、π表以及有效密鑰長度的上界s進行密鑰擴展運算,得到K[0]~K[63];
(3)令j=0;
(4)進行5層的mix運算;
(5)進行1層的mash運算;
(6)進行6層的mix運算;
(7)進行1層的mash運算;
(8)進行5層的mix運算。
經上述處理后的R[0]~R[3]即密文。