J'essaie d'implémenter un algorithme de cryptage basé sur un mot de passe, mais j'obtiens cette exception:
javax.crypto.BadPaddingException: le bloc final donné n'est pas correctement rempli
Quel pourrait être le problème?
Voici mon code:
public class PasswordCrypter {
private Key key;
public PasswordCrypter(String password) {
try{
KeyGenerator generator;
generator = KeyGenerator.getInstance("DES");
SecureRandom sec = new SecureRandom(password.getBytes());
generator.init(sec);
key = generator.generateKey();
} catch (Exception e) {
e.printStackTrace();
}
}
public byte[] encrypt(byte[] array) throws CrypterException {
try{
Cipher cipher = Cipher.getInstance("DES/ECB/PKCS5Padding");
cipher.init(Cipher.ENCRYPT_MODE, key);
return cipher.doFinal(array);
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
public byte[] decrypt(byte[] array) throws CrypterException{
try{
Cipher cipher = Cipher.getInstance("DES/ECB/PKCS5Padding");
cipher.init(Cipher.DECRYPT_MODE, key);
return cipher.doFinal(array);
} catch(Exception e ){
e.printStackTrace();
}
return null;
}
}
(Le test JUnit)
public class PasswordCrypterTest {
private static final byte[] MESSAGE = "Alpacas are awesome!".getBytes();
private PasswordCrypter[] passwordCrypters;
private byte[][] encryptedMessages;
@Before
public void setUp() {
passwordCrypters = new PasswordCrypter[] {
new PasswordCrypter("passwd"),
new PasswordCrypter("passwd"),
new PasswordCrypter("otherPasswd")
};
encryptedMessages = new byte[passwordCrypters.length][];
for (int i = 0; i < passwordCrypters.length; i++) {
encryptedMessages[i] = passwordCrypters[i].encrypt(MESSAGE);
}
}
@Test
public void testEncrypt() {
for (byte[] encryptedMessage : encryptedMessages) {
assertFalse(Arrays.equals(MESSAGE, encryptedMessage));
}
assertFalse(Arrays.equals(encryptedMessages[0], encryptedMessages[2]));
assertFalse(Arrays.equals(encryptedMessages[1], encryptedMessages[2]));
}
@Test
public void testDecrypt() {
for (int i = 0; i < passwordCrypters.length; i++) {
assertArrayEquals(MESSAGE, passwordCrypters[i].decrypt(encryptedMessages[i]));
}
assertArrayEquals(MESSAGE, passwordCrypters[0].decrypt(encryptedMessages[1]));
assertArrayEquals(MESSAGE, passwordCrypters[1].decrypt(encryptedMessages[0]));
try {
assertFalse(Arrays.equals(MESSAGE, passwordCrypters[0].decrypt(encryptedMessages[2])));
} catch (CrypterException e) {
// Anything goes as long as the above statement is not true.
}
try {
assertFalse(Arrays.equals(MESSAGE, passwordCrypters[2].decrypt(encryptedMessages[1])));
} catch (CrypterException e) {
// Anything goes as long as the above statement is not true.
}
}
}
javax.crypto.BadPaddingException: Given final block not properly padded
. Dois-je traiter cela comme une mauvaise clé?en fonction de l'algorithme de cryptographie que vous utilisez, vous devrez peut-être ajouter des octets de remplissage à la fin avant de chiffrer un tableau d'octets afin que la longueur du tableau d'octets soit multiple de la taille du bloc:
Plus précisément dans votre cas, le schéma de remplissage que vous avez choisi est PKCS5 qui est décrit ici: http://www.rsa.com/products/bsafe/documentation/cryptoj35html/doc/dev_guide/group_ CJ _SYM__PAD.html
(Je suppose que vous avez le problème lorsque vous essayez de chiffrer)
Vous pouvez choisir votre schéma de remplissage lorsque vous instanciez l'objet Cipher. Les valeurs prises en charge dépendent du fournisseur de sécurité que vous utilisez.
Au fait, êtes-vous sûr de vouloir utiliser un mécanisme de cryptage symétrique pour crypter les mots de passe? Ne serait-il pas meilleur hash à sens unique? Si vous avez vraiment besoin de pouvoir déchiffrer les mots de passe, DES est une solution assez faible, vous voudrez peut-être utiliser quelque chose de plus fort comme AES si vous devez rester avec un algorithme symétrique.
la source
J'ai rencontré ce problème en raison du système d'exploitation, d'une plate-forme simple à différente sur la mise en œuvre de JRE.
obtiendra la même valeur sous Windows, alors qu'elle est différente sous Linux. Donc, sous Linux, il faut changer pour
"SHA1PRNG" est l'algorithme utilisé, vous pouvez vous référer ici pour plus d'informations sur les algorithmes.
la source
Cela peut également être un problème lorsque vous entrez un mot de passe incorrect pour votre clé de connexion.
la source