RC4加密演算法及其scala實現
阿新 • • 發佈:2019-02-06
最近用到了rc4演算法和base64簡單寫一篇關於rc4的文章。
RC4演算法的特點是演算法簡單,執行速度快,而且金鑰長度是可變的,可變範圍為1-256位元組(8-2048位元),在如今技術支援的前提下,當金鑰長度為128位元時,用暴力法搜尋金鑰已經不太可行,所以可以預見RC4的金鑰範圍任然可以在今後相當長的時間裡抵禦暴力搜尋金鑰的攻擊。實際上,如今也沒有找到對於128bit金鑰長度的RC4加密演算法的有效攻擊方法。
關鍵變數:
1、金鑰流:RC4演算法的關鍵是根據明文和金鑰生成相應的金鑰流,金鑰流的長度和明文的長度是對應的,也就是說明文的長度是500位元組,那麼金鑰流也是500位元組。當然,加密生成的密文也是500位元組,因為密文第i位元組=明文第i位元組^金鑰流第i位元組;
2、狀態向量S:長度為256,S[0],S[1].....S[255]。每個單元都是一個位元組,演算法執行的任何時候,S都包括0-255的8位元數的排列組合,只不過值的位置發生了變換;
3、臨時向量T:長度也為256,每個單元也是一個位元組。如果金鑰的長度是256位元組,就直接把金鑰的值賦給T,否則,輪轉地將金鑰的每個位元組賦給T;
4、金鑰K:長度為1-256位元組,注意金鑰的長度 keylen 與明文長度、金鑰流的長度沒有必然關係,通常金鑰的長度趣味16位元組(128位元)。
下面是scala程式碼,由於scala中Byte型和Java中一樣都是-128到127,所以有一些防止越界的操作:
class RC4( val data:Array[Byte],key:String){ private val s=new Array[Byte](256)//狀態向量S val len=key.length rc4_init() private def rc4_init(){ val t=new Array[Byte](256)//備用向量T for (i <- 0 to 255){ s(i)=i.toByte t(i)=key(i%len).toByte } var j=0 var tmp:Byte=0 for (i <- 0 to 255){ j=(j+s(i)+t(i)+256)%256 //println(j) tmp =s(i) s(i)=s(j) s(j)=tmp } } def rc4_crypt() :Array[Byte]={ val Data=new Array[Byte](data.length) for (i <-0 until(data.length)){ Data(i)=data(i) } var k=0 var i=0 var j=0 var t=0 var tmp:Byte=0 for(k <- 0 until(Data.length)){ i=(i+1)%256 j=(j+s(i)+128)%256 tmp=s(i) s(i)=s(j) s(j)=tmp t=(s(i)+s(j)+256)%256 Data(k)=(Data(k)^s(t)).toByte } Data } }
注意:使用new String()會改變非法字元的編碼