簡體   English   中英

錯誤:javax.crypto.BadPaddingException:解密時填充塊損壞

[英]Error : javax.crypto.BadPaddingException: pad block corrupted while Decryption

我已經完成了加密,

public static String encrypt(String plainText) {
    try {
        byte[] keyData = secret_key.getBytes();
        SecretKeySpec secretKey = new SecretKeySpec(keyData, "AES/ECB/PKCS7Padding");
        Cipher cipher = Cipher.getInstance("AES/ECB/PKCS7Padding");
        cipher.init(Cipher.ENCRYPT_MODE, secretKey);

        byte[] cipherText = cipher.doFinal(plainText.getBytes("UTF-8"));
        String encryptedString = Base64.encodeToString(cipherText, Base64.NO_WRAP);

        return encryptedString;
    } catch (Exception e) {
        e.printStackTrace();
    }
    return null;
}

運行良好。

但是Decryption一部分給出了錯誤,例如

W/System.err: javax.crypto.BadPaddingException: pad block corrupted
W/System.err:     at com.android.org.bouncycastle.jce.provider.JCEBlockCipher.engineDoFinal(JCEBlockCipher.java:701)
W/System.err:     at javax.crypto.Cipher.doFinal(Cipher.java:1111)

像這樣decrypt代碼

public static String decrypt(String encryptedText) {
    try {
        byte[] keyData = secret_key.getBytes();
        SecretKeySpec secretKey = new SecretKeySpec(keyData, "AES/ECB/PKCS7Padding");
        Cipher cipher = Cipher.getInstance("AES/ECB/PKCS7Padding");
        cipher.init(Cipher.DECRYPT_MODE, secretKey);

        byte[] cipherText = Base64.decode(encryptedText,Base64.NO_WRAP);
        String decryptedString = new String(cipher.doFinal(cipherText),"UTF-8");

        return decryptedString;
    } catch (Exception e) {
        e.printStackTrace();
    }
    return null;
}

這是什么問題? 我該如何解決這個問題?

您的secret_key值可能包含在您使用的模棱兩可的編碼中不能很好表示的字節。 在不指定編碼的情況下調用String#getBytes() ,將獲得系統默認值,該默認值可能會有所不同。

每當將鍵表示為String時,都應使用十六進制編碼。 這將在每個平台上的序列化/反序列化中保持一致。 此編碼/解碼過程有許多標准實現( org.bouncycastle.util.encoders.Hex.decode("0123456789ABCDEFFEDCBA9876543210");org.apache.commons.codec.binary.Hex.decodeHex("0123456789ABCDEFFEDCBA9876543210".toCharArray());都返回原始byte[] )。

一些注意事項:

  1. 您正在使用ECB 操作模式 ,該模式極易受到頻率分析進行密碼分析的影響,除玩具密碼演示外,該方法已被棄用 建議您使用CBCCTRGCM
  2. 您沒有提供初始化向量(IV),因此使用相同密鑰加密的相同消息將始終產生相同的密文。 通過從SecureRandom生成16個字節並將其填充到IvParameterSpec對每個加密操作使用唯一且不可預測的IV。 您可以將IV字節放在密文之前,並以明文形式傳輸/存儲。
  3. 您的密文未經身份驗證,從而使惡意用戶既可以操縱加密的數據,也可以通過填充oracle / CCA攻擊來嘗試解密。 使用關聯數據(AEAD)模式的經過身份驗證的加密,例如GCM ,或在密文上使用HMAC/SHA-256消息身份驗證碼(MAC),並在嘗試進行任何解密之前,使用恆定時間等於方法對其進行驗證。
  4. 實例化密鑰時,無需提供操作模式或填充方案。 SecretKey key = new SecretKeySpec(keyData, "AES"); 足夠了。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM