我正在做一个简单的加密文件传输系统,现在停止运行时异常:
Exception in thread "main" javax.crypto.BadPaddingException: Given final block not properly padded
at com.sun.crypto.provider.CipherCore.doFinal(CipherCore.java:811)
at com.sun.crypto.provider.CipherCore.doFinal(CipherCore.java:676)
at com.sun.crypto.provider.AESCipher.engineDoFinal(AESCipher.java:313)
at javax.crypto.Cipher.doFinal(Cipher.java:2087)
at ftpclient.FTPClient.main(FTPClient.java:82)
我试图用一个字符串调试我的代码,用相同的密钥加密和解密,它是有效的。然而,当我试图从文件传输流时,这个异常总是出现。
以下是双方的代码。首先,他们将通过RSA交换对称密钥(AES密钥),然后通过AES加密传输大型文件。我们可以关注每段代码的最后一部分,其中文件通过AES密钥进行加密和解密。
服务器端:
package ftpserver;
import java.io.*;
import java.net.*;
import javax.crypto.*;
import java.security.*;
import javax.crypto.spec.SecretKeySpec;
import org.apache.commons.codec.binary.Base64;
/**
*
* @author Han
*/
public class FTPServer {
public static void main(String[] args) throws Exception {
//generate symmetric key and initialize cipher for AES
SecretKey skey = null;
Cipher aes = Cipher.getInstance("AES/ECB/PKCS5Padding");
KeyGenerator kg = KeyGenerator.getInstance("AES");
kg.init(128);
skey = kg.generateKey();
//get public key of the receive side
final String PUBLIC_KEY_PATH = "key_b.public";
PublicKey publickey = null;
try {
FileInputStream fis;
fis = new FileInputStream(PUBLIC_KEY_PATH);
ObjectInputStream oin = new ObjectInputStream(fis);
publickey = (PublicKey) oin.readObject();
oin.close();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (ClassNotFoundException e) {
e.printStackTrace();
};
//encrypte symmetric key with own private key and send out
Cipher rsa = Cipher.getInstance("RSA");
rsa.init(Cipher.ENCRYPT_MODE, publickey);
byte cipherSKey[] = rsa.doFinal(skey.getEncoded());
//System.out.println(skey); //debug
//create tcp server socket
ServerSocket tcp = new ServerSocket(2000);
Socket client = tcp.accept();
//get input&output stream from the TCP connection
InputStream in = client.getInputStream();
OutputStream out = client.getOutputStream();
//generate a file input stream to get stream from file
File sentFile = new File("F:\\test.txt");
FileInputStream fin = new FileInputStream(sentFile);
//send encrypted symmetric key first
out.write("Symmetric Key:\r\n".getBytes());
out.write(cipherSKey);
DataInputStream din = new DataInputStream(in);
while(true)
{
if(din.readLine().equals("Received."))
{
System.out.println("Send key successfully.");
break;
}
};
//send files
int count;
byte[] bytearray = new byte[8192];
byte[] cipherbuffer;
while((count = fin.read(bytearray))>0)
{
cipherbuffer = Base64.encodeBase64(aes.doFinal(bytearray));
out.write(cipherbuffer,0,cipherbuffer.length);
System.out.println(count+" bytes have been sent.");
};
out.flush();
out.close();
client.close();
}
}
客户端:
package ftpclient;
import java.io.*;
import java.net.*;
import java.security.PrivateKey;
import javax.crypto.*;
import javax.crypto.spec.SecretKeySpec;
import org.apache.commons.codec.binary.Base64;
/**
*
* @author Han
*/
public class FTPClient {
public static void main(String[] args) throws Exception
{
//get the private key of this side
final String PUBLIC_KEY_PATH = "key_b.privat";
PrivateKey privatkey = null;
try {
FileInputStream fis;
fis = new FileInputStream(PUBLIC_KEY_PATH);
ObjectInputStream oin = new ObjectInputStream(fis);
privatkey = (PrivateKey) oin.readObject();
oin.close();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (ClassNotFoundException e) {
e.printStackTrace();
};
Cipher rsa = Cipher.getInstance("RSA");
rsa.init(Cipher.DECRYPT_MODE, privatkey);
//create tcp client socket
Socket tcp = new Socket("192.168.1.185",2000);
InputStream in = tcp.getInputStream();
OutputStream out = tcp.getOutputStream();
DataInputStream din = new DataInputStream(in);
//receive symmetric key from server
byte keybuffer[] = new byte[128];
SecretKey skey = null;
while(true)
{
if(din.readLine().equals("Symmetric Key:"))
{
System.out.println("Start to receiving key...");
in.read(keybuffer);
byte[] skeycode = rsa.doFinal(keybuffer);
skey = new SecretKeySpec(skeycode, 0, skeycode.length, "AES");
out.write("Received.\r\n".getBytes());
break;
}
};
//create cipher for symmetric decryption
Cipher aes = Cipher.getInstance("AES/ECB/PKCS5Padding");
aes.init(Cipher.DECRYPT_MODE, skey);
//System.out.println(skey); //debug
//create file stream
FileOutputStream fos = new FileOutputStream("E:\\test_cp.txt");
int count;
int i = 0;
byte[] bytearray = new byte[8192];
byte[] buffer;
while((count = in.read(bytearray)) > 0)
{
buffer = (aes.doFinal(Base64.decodeBase64(bytearray)));
fos.write(buffer,0,buffer.length);
i +=count;
System.out.println(i+" bytes have been received.");
};
fos.flush();
fos.close();
in.close();
tcp.close();
System.out.println("File Transfer completed");
}
}
您正在多次调用doLast
,或者至少尝试这样做。
当您读取数据时,并非所有数据都会立即到达或读入缓冲区。所以你解密了一些,然后再读一遍。没关系。
但是当你这样做的时候,你每次都调用dofine
,而不是更新
。这是错误的,是错误的原因。相反,用更新
替换dofine
,然后添加一个额外的一旦你读完了所有的数据(有一个不需要任何参数的doFINE()
就是这个原因)。
看见http://docs.oracle.com/javase/7/docs/api/javax/crypto/Cipher.html
也看到http://en.wikipedia.org/wiki/Block_cipher_mode_of_operation#Electronic_codebook_.28ECB.29为什么ecb模式通常不是一个好主意(请看企鹅图片)。
我正在尝试编写方法来加密或解密字符串(大部分是数字)。它适用于某些文本(例如-'1010000011'、'1010000012'、'1010000013'),但也适用于其他文本(例如-'1010000014'、'1010000018'): javax.crypto.BadPadding异常:给定最后一个块没有正确填充 这是我的代码: 要加密的字符串从文件中读取,并在加密后写入其他文件。这些加密的文
首先,我会告诉你我的主要目标是什么。在客户端使用AES加密部分内容,然后使用RSA公钥加密重要的AES规范,并将AES加密数据和RSA加密的AES规范发送到服务器端。所以在服务器端,我将使用RSA私钥解密AES密钥规范,然后使用这些AES规范,我将解密AES加密数据。通过测试加密和解密,我成功地使RSA部分工作。在此实现RSa之前,我必须使AES art工作。 对于客户端,我使用crypto-js
问题内容: 我需要有关此错误的帮助:给最终块未正确填充。从标题中可以看到,我正在使用AES。 这是错误的行代码: 这是完整的代码: } 问题答案: 根据您的评论,您几乎可以使加密工作。 您需要将IV生成代码从您的加密/解密方法移动到其他地方,就像这样 然后将该ivspec传递到加密和解密方法中(使它们看起来像),这样您就可以为加密和解密使用相同的iv。 另外,不要调用decryptedByteAr
我想加密EnteredDetails(java bean)类型的arraylist,并将其序列化到一个文件中。我正在关注AES-128位加密的链接:http://www . code 2 learn . com/2011/06/encryption-and-decryption-of-data-using . html 要使用aes class的encrypt方法,我必须将arrarylist转换
问题内容: 我正在尝试实现基于密码的加密算法,但出现此异常: javax.crypto.BadPaddingException:给定的最终块未正确填充 可能是什么问题? 这是我的代码: (JUnit测试) 问题答案: 如果尝试使用错误的密钥解密填充了PKCS5的数据,然后取消填充(由Cipher类自动完成),则很可能会收到BadPaddingException(可能略小于255/256,约为99.