2011-12-19 90 views
-2

我們有一個Java客戶端,發送給我們一些加密的數據 1.隨機字符串使用RSA和我們提供給他們離線的公鑰加密。 2.使用在步驟1中生成的密鑰加密它們使用數據alg_tripleDES_CBC = http://www.w3.org/2001/04/xmlenc#tripledes-cbc無法解密使用.NET中的TripleDES加密Java

我能夠解密從這樣第一步驟這是工作的關鍵...。

public static string DecryptKey(string encryptedKey) 
    { 
     X509Certificate2 cert = new X509Certificate2("c:\\test.pfx", "test"); 
     RSACryptoServiceProvider privateKeyProvider = (RSACryptoServiceProvider)cert.PrivateKey; 

     string decryptedKey = System.Text.Encoding.UTF8.GetString(privateKeyProvider.Decrypt(Convert.FromBase64String(encryptedKey), false)); 

     return decryptedKey; 

    } 

我有這樣的代碼進行解密使用從第一步驟中生成的密鑰數據。

public static string DecryptString(string Message, string Passphrase) 
    { 
     byte[] Results; 
     System.Text.UTF8Encoding UTF8 = new System.Text.UTF8Encoding(); 

     MD5CryptoServiceProvider HashProvider = new MD5CryptoServiceProvider(); 
     byte[] TDESKey = HashProvider.ComputeHash(UTF8.GetBytes(Passphrase)); 

     TripleDESCryptoServiceProvider TDESAlgorithm = new TripleDESCryptoServiceProvider(); 

     TDESAlgorithm.Key = TDESKey; 
     TDESAlgorithm.Mode = CipherMode.ECB; 
     TDESAlgorithm.Padding = PaddingMode.PKCS7; 

     byte[] DataToDecrypt = Convert.FromBase64String(Message); 

     try 
     { 
      ICryptoTransform Decryptor = TDESAlgorithm.CreateDecryptor(); 
      Results = Decryptor.TransformFinalBlock(DataToDecrypt, 0, DataToDecrypt.Length); 
     } 
     finally 
     { 
      TDESAlgorithm.Clear(); 
      HashProvider.Clear(); 
     } 

     return UTF8.GetString(Results); 
    } 

第二步失敗,出現此異常。

System.Security.Cryptography.CryptographicException: Bad Data. 

    at System.Security.Cryptography.CryptographicException.ThrowCryptographicException(Int32 hr) 
    at System.Security.Cryptography.Utils._DecryptData(SafeKeyHandle hKey, Byte[] data, Int32 ib, Int32 cb, Byte[]& outputBuffer, Int32 outputOffset, PaddingMode PaddingMode, Boolean fDone) 
    at System.Security.Cryptography.CryptoAPITransform.TransformFinalBlock(Byte[] inputBuffer, Int32 inputOffset, Int32 inputCount) 
    at ConsoleApplication3.Program.DecryptString(String Message, String Passphrase) in C:\Documents and Settings\rjaladi\Desktop\ConsoleApplication3\ConsoleApplication3\Program.cs:line 66 
    at ConsoleApplication3.Program.Main(String[] args) in C:\Documents and Settings\rjaladi\Desktop\ConsoleApplication3\ConsoleApplication3\Program.cs:line 22 

什麼是我需要檢查我們的客戶?我知道我們傳遞給TDES的參數有問題。任何幫助?

編輯:加密消息的相應Java代碼。

public String encryptText(String plainText) throws Exception{ 

    byte[] plaintext = plainText.getBytes(); 
    byte[] tdesKeyData = key; 
    byte[] myIV = initializationVector; 

    Cipher c3des = Cipher.getInstance(""DESede/CBC/NoPadding""); 
    SecretKeySpec myKey = new SecretKeySpec(tdesKeyData, "DESede"); 
    IvParameterSpec ivspec = new IvParameterSpec(myIV); 
    c3des.init(Cipher.ENCRYPT_MODE, myKey, ivspec); 
    byte[] cipherText = c3des.doFinal(plaintext); 
    sun.misc.BASE64Encoder obj64=new sun.misc.BASE64Encoder(); 
    return obj64.encode(cipherText); 
} 
+1

它在TransformFinalBlock上失敗,提示您的數據長度錯誤。 – 2011-12-19 19:56:18

+0

'ECB' =>'OMG'。 – CodesInChaos 2011-12-19 19:56:38

+1

你做了什麼來調試參數,你是否證實它們是相同的值,基於它拋出異常的事實,我會說你什麼也沒做。 – 2011-12-19 20:01:17

回答

1

你的例外正在拋出_DecryptData(...),我注意到它包括一個PaddingMode參數。在最後一個塊的末尾填充將被檢查,並且如果找到不正確的填充,則會拋出錯誤。我建議你檢查發送數據的人,看看他們使用的填充模式。解密時您需要使用相同的填充模式。

正如@klartrex所說,你不應該使用ECB模式,它會泄漏信息; (文字)圖示參見here。如果可以說服另一端這樣做,請改用CBC或CTR模式。

+0

我也試過CBC模式,那是行不通的。我添加了加密消息的相應Java代碼。 – 2011-12-19 21:37:40

+0

其實我已經改變填充模式爲none,因爲我剛收到的java代碼沒有指定填充。並且chipermode以cbc ..現在沒有懷疑。但它給了垃圾,我認爲也許編碼是不正確的。 – 2011-12-19 21:45:52

+0

@破碎鏈接:CBC模式需要一個IV,錯誤的IV會給第一個塊的垃圾。您**必須**使用與發件人相同的密鑰,模式,填充和IV(如果使用)。如果所有消息都是垃圾,那麼請逐字節檢查密鑰,以便它完全匹配。 – rossum 2011-12-19 23:52:14

2

可能失敗:

TDESAlgorithm.Mode = CipherMode.ECB; 

你應該,如果你使用CBC的Java加密使用CBC ciphermode。不建議使用ECB,因爲它有一些安全缺陷。

+0

我也嘗試過使用CBC ..我能夠獲得加密此消息的Java代碼。如果這有幫助。 – 2011-12-19 21:36:13

+0

其實我已經改變填充模式爲none,因爲我剛剛收到的java代碼沒有指定填充。並且chipermode以cbc ..現在沒有懷疑。但它給了垃圾,我認爲也許編碼是不正確的。 – 2011-12-19 21:45:16