按照以下逻辑进行解密时出现异常。请在下面的代码片段中向我建议任何问题。加密没问题,可以加密。
public String encryptDataSymmetric(String dataTobeEncrypted) {
String encryptedData = null;
try {
Charset CHARSET = Charset.forName("UTF8");
Security.addProvider(new org.bouncycastle.jce.provider.BouncyCastleProvider());
SecureRandom securerandom = new SecureRandom();
KeyGenerator keygenerator = KeyGenerator.getInstance("AES");
keygenerator.init(192, securerandom);
SecretKey key = keygenerator.generateKey();
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS7Padding");
// cipher.init(Cipher.ENCRYPT_MODE, key, ivspec);
cipher.init(Cipher.ENCRYPT_MODE, key, new IvParameterSpec(new byte[cipher.getBlockSize()]));
encryptedData = DatatypeConverter.printBase64Binary(cipher.doFinal(dataTobeEncrypted.getBytes(CHARSET)))
.trim();
System.out.println("---encryptedData-----" + encryptedData);
} catch (Exception ex) {
ex.printStackTrace();
}
return encryptedData;
}
public String decryptDataSymmetric(String dataTobeDecrypted) {
String decryptedData = null;
try {
Charset CHARSET = Charset.forName("UTF8");
Security.addProvider(new org.bouncycastle.jce.provider.BouncyCastleProvider());
SecureRandom securerandom = new SecureRandom();
KeyGenerator keygenerator = KeyGenerator.getInstance("AES");
keygenerator.init(192, securerandom);
SecretKey key = keygenerator.generateKey();
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS7Padding");
cipher.init(Cipher.DECRYPT_MODE, key, new IvParameterSpec(new byte[cipher.getBlockSize()]));
decryptedData = new String(
DatatypeConverter.parseBase64Binary(new String(cipher.doFinal(dataTobeDecrypted.getBytes()))));
System.out.println("---decryptedData----" + decryptedData);
} catch (Exception ex) {
ex.printStackTrace();
}
return decryptedData;
}
<块引用>
javax.crypto.BadPaddingException:填充块损坏于 org.bouncycastle.jce.provider.JCEBlockCipher.engineDoFinal(未知 来源)
答案 0 :(得分:3)
不是 Java 专家,但您需要从 Base64 解码为字节数组,然后在解密时将其传递给密码,而不是在尝试解密之后。
Base64 编码是将字节流编码为 ascii 字符,用于传输目的。在传输的接收端需要先将base64编码再转换为字节流。
解密后,您必须将解密后的字节数组转换为字符串。
总而言之,解密必须撤销加密方法的步骤。
加密方式:
解密方法:
据说,您的代码存在一些问题。 我能够将这个 Java 示例代码放在一起,仅用于演示我将在这里提出的要点。
/*
DO NOT USE THIS CODE! It is vulnerable to Padding Oracle Attack!
Instead use an Authenticated Encryption scheme or algorithm.
This code is written for demonstration purpose only!! Not secure!!
*/
import java.nio.ByteBuffer;
import java.nio.charset.Charset;
import java.io.Console;
import java.security.*;
import javax.crypto.*;
import javax.crypto.spec.*;
import java.util.Base64;
public class Main {
public static String encryptDataSymmetric(String dataTobeEncrypted, SecretKey key) {
String encryptedData = null;
try {
Charset CHARSET = Charset.forName("UTF8");
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
SecureRandom securerandom = new SecureRandom();
byte[] ivBytes = new byte[cipher.getBlockSize()];
securerandom.nextBytes(ivBytes);
IvParameterSpec iv = new IvParameterSpec(ivBytes);
cipher.init(Cipher.ENCRYPT_MODE, key, iv);
byte[] cipherText = cipher.doFinal(dataTobeEncrypted.getBytes(CHARSET));
System.out.println("---IV----" + Base64.getEncoder().encodeToString(ivBytes));
byte[] ivAndCipherText = new byte[ivBytes.length + cipherText.length];
System.arraycopy(ivBytes, 0, ivAndCipherText, 0, ivBytes.length);
System.arraycopy(cipherText, 0, ivAndCipherText, ivBytes.length, cipherText.length);
encryptedData = Base64.getEncoder().encodeToString(ivAndCipherText);
System.out.println("---encryptedData-----" + encryptedData);
} catch (Exception ex) {
ex.printStackTrace();
}
return encryptedData;
}
public static String decryptDataSymmetric(String cipherBase64Encoded, SecretKey key) {
String encryptedData = null;
try {
Charset CHARSET = Charset.forName("UTF8");
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
byte[] ivAndCipherText = Base64.getDecoder().decode(cipherBase64Encoded);
byte[] iv = new byte[cipher.getBlockSize()];
System.arraycopy(ivAndCipherText, 0, iv, 0, iv.length);
byte[] cipherText = new byte[ivAndCipherText.length - iv.length];
System.arraycopy(ivAndCipherText, iv.length, cipherText, 0, cipherText.length);
cipher.init(Cipher.DECRYPT_MODE, key, new IvParameterSpec(iv));
return new String(cipher.doFinal(cipherText),CHARSET);
} catch (Exception ex) {
ex.printStackTrace();
}
return encryptedData;
}
public static void main(String args[]) {
try {
SecureRandom securerandom = new SecureRandom();
KeyGenerator keygenerator = KeyGenerator.getInstance("AES");
keygenerator.init(192, securerandom);
SecretKey key = keygenerator.generateKey();
System.out.println("---key---" + key.getEncoded());
String str = "Hello bye";
//Console.Write(decryptDataSymmetric(encryptDataSymmetric(str)));
System.out.println(str);
String encrypted = encryptDataSymmetric(str, key);
String plainText = decryptDataSymmetric(encrypted, key);
System.out.println("plaintext: " + plainText);
System.out.println("The end!");
} catch (Exception ex) {
ex.printStackTrace();
}
}
}
答案 1 :(得分:0)