2012-03-23 62 views
1

我從加密根據他們在一個外部方的一些數據編碼的文本:「Rijndeal 256用私鑰」解密的Rijndael 256(從PHP)在Java中有一些信息

除了這些記錄有公鑰和私鑰證書,看起來像RSA證書。

從我迄今爲止所瞭解的情況來看,使用加密技術與證書通用的方法是在初始化向量中生成一個'密鑰'或某種類型,並將其用於加密文本。所以我想這可能是他們所做的(數據被加密的PHP應用程序)

我想解密這個文本與javax.crypto.Cipher,但我想我可能需要更多的信息特定的加密,但我真的不知道需要什麼信息,並認爲它可能'默認選項'可能會起作用。 (與供應方的溝通困難且緩慢)。

我目前使用下面的代碼來獲取私鑰:

InputStreamReader ir = new InputStreamReader(the_inputstream_for_the_private_key_record); 
    Security.addProvider(new BouncyCastleProvider()); 
    pemr = new PEMReader(ir); 
    Object o = pemr.readObject(); 
    keyPair kp = (KeyPair) o; 
    return kp.getPrivate(); 

這似乎是工作,因爲我得到一個實例化的專用密鑰對象沒有錯誤了toString樣子:

RSA Private CRT Key 
      modulus: c98faa50ba69<trimmed> 
    public exponent: 10001 
    private exponent: bb889fbe5cb2a6763f...<trimmed> 
      primeP: eb73e85dc636f5751b...<trimmed> 
      primeQ: db269bd603a2b81fc9...<trimmed> 
    primeExponentP: 85b9f111c190595cc8...<trimmed> 
    primeExponentQ: a66d59a75bb77530de...<trimmed> 
    crtCoefficient: 79415b078c4c229746...<trimmed> 

對於每條記錄,我也有類似以下的條目:

{ 
"decryptedLength":128389, 
"symKeyLength":32, 
"symKey":"SImE8VnSZaAu1Ve...<trimmed (this is always 685 chars long) >...ayaJcnpSeOqAGM7q=" 
} 

基本上這是我有點卡住的地方。 我的猜測是,那是symkey「值與RSA這反過來解密會產生對AES部分祕密密鑰加密時,但如果我嘗試:

Cipher rsaCipher = Cipher.getInstance("RSA"); 
rsaCipher.init(Cipher.DECRYPT_MODE, key); 
byte[] b = rsaCipher.doFinal('symkey'.getbytes()); 

這讓我「javax.crypto.IllegalBlockSizeException :數據不能超過512字節「,這似乎是合乎邏輯的,因爲這個字符串是685個字符長

我可能在這裏丟失的東西很明顯... 任何建議表示讚賞。

+0

相關:http://stackoverflow.com/questions/587357/rijndael-support-in-java – bezmax 2012-03-23 12:38:22

+0

正如你可能從我給的鏈接中發現的,Rijndael不是RSA,而是AES。 – bezmax 2012-03-23 12:42:50

+0

我知道Rijndael是EAS RSA部分是因爲我提供了私鑰證書 – pvgoddijn 2012-03-23 13:05:28

回答

1

與GregS的回答我最終得到了這個工作。 (添加一個答案,以防其他人需要解密類似的PHP編碼的東西)。

的第一部分是從所述元數據串 這是格雷戈注意到Base64編碼的解密德symmetricKey(「symkey」),RSA加密將其解碼像這樣鍵:

Cipher rsaCipher = Cipher.getInstance("RSA"); 
rsaCipher.init(Cipher.DECRYPT_MODE, key); 
byte[] encryptedRijndaelKey = Base64.decodeBase64(base64EncodedSymetricKey); //from the metaData 
byte[] rijndaelKeyBytes = rsaCipher.doFinal(encryptedRijndaelKey); 

這Rijndael的鍵然後用於解密像這樣去實際的加密數據:

RijndaelEngine rijndaelEngine = new RijndaelEngine(256); // *1 *2 
KeyParameter keyParam = new KeyParameter(rijndaelKeyBytes) 
rijndaelEngine.init(false, keyParam); //false == decrypt 
PaddedBufferedBlockCipher bbc = new PaddedBufferedBlockCipher(rijndaelEngine, new ZeroBytePadding()); // *3 

byte[] decryptedBytes = new byte[decryptedLenght]; //from the storageOptions string 
int processed = bbc.processBytes(inputBytes, 0, inputBytes.length, decryptedBytes, 0); 
bbc.doFinal(decryptedBytes, processed); 

* 1因爲太陽JCA僅支持具有128位密鑰長度我不得不使用不同的提供者(BouncyCastle的)共同AES。 * 2顯然塊大小也是256位(線索&錯誤) * 3顯然沒有使用填充,因此填充的ZeroPadding(再次跟蹤&錯誤)。

2

只是猜測,但我覺得值

"symKey":"SImE8VnSZaAu1Ve...<trimmed (this is always 685 chars long) >...ayaJcnpSeOqAGM7q=" 

是使用4096位公鑰從RSA加密輸出的base64編碼。您需要先將base64解碼爲byte []數組,然後使用私鑰對其進行解密,其結果將是一個256位密鑰。請注意,「Rijndael 256」不明確,因爲Rijndael支持256位塊大小和256位密鑰大小。

+0

謝謝,這幫助我解決它。 – pvgoddijn 2012-03-26 12:14:42

0

symKey值是Base64編碼,必須解碼後才能對其進行私鑰解密。此外,對稱加密聽起來像是AES-256。 (AES基於Rijndael密碼)。