2012-05-08 2 views
6

Mam program gniazda serwera i klienta, serwer wysłać zaszyfrowaną wiadomość do klienta, czyli kodu po stronie serwera:długość wejściowa musi być wielokrotnością 16 podczas odszyfrowywania z wyściełane szyfr

cipher2 = Cipher.getInstance("AES"); 
secretKeySpec = new SecretKeySpec(decryptedText, "AES"); 
cipher2.init(Cipher.ENCRYPT_MODE, secretKeySpec); 
feedback = "Your answer is wrong".getBytes(); 
cipher2.doFinal(feedback); 
dos.writeInt(feedback.length); 
dos.write(feedback); 

po stronie klienta Kod:

int result_len = 0; 
result_len = din.readInt();    
byte[] result_Bytes = new byte[result_len]; 
din.readFully(result_Bytes); 
cipher2 = Cipher.getInstance("AES"); 
cipher2.init(Cipher.DECRYPT_MODE, aesKey);    
byte[] encrypt = cipher2.doFinal(result_Bytes); 

Wyjątek rzucić na byte[] encrypt = cipher2.doFinal(result_Bytes);

javax.crypto.IllegalBlockSizeException: Input length must be multiple of 16 when decrypting with padded cipher 
    at com.sun.crypto.provider.CipherCore.doFinal(CipherCore.java:750) 
    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:2086) 

jaki jest problem?

+0

Czy result_len wielokrotność 16? Jeśli nie, upewnij się, że jest, a wynik_Bytes powinien mieć odpowiednią długość. – Ewald

Odpowiedz

-3

miałem ten problem raz. Właściwie mój kod był poprawny i działał, gdy używam go bez serwera. Błąd polegał na tym, że gdy otrzymywałem parametr z adresu url, zaszyfrowany URL posiadający symbol plus (+) zmienił się automatycznie na spację. To może być problem ur jeden raz. Oto moja logika szyfrowania i odszyfrowywania za pomocą generatora kluczy, jeśli chcesz, możesz z niego korzystać.

public class Anything 
{ 
    private static final String ALGO = "AES"; 
    //generate 128bit key 
    private static final String keyStr = "Z8LSq0wWwB5v+6YJzurcP463H3F12iZh74fDj4S74oUH4EONkiKb2FmiWUbtFh97GG/c/lbDE47mvw6j94yXxKHOpoqu6zpLKMKPcOoSppcVWb2q34qENBJkudXUh4MWcreondLmLL2UyydtFKuU9Sa5VgY/CzGaVGJABK2ZR94="; 

    private static Key generateKey() throws Exception { 
     byte[] keyValue = keyStr.getBytes("UTF-8"); 
     MessageDigest sha = MessageDigest.getInstance("SHA-1"); 
     keyValue = sha.digest(keyValue); 
     keyValue = Arrays.copyOf(keyValue, 16); // use only first 128 bit  
     Key key = new SecretKeySpec(keyValue, ALGO); 
     return key; 
    } 

    public static String encrypt(String Data) throws Exception { 
      Key key = generateKey(); 
      Cipher c = Cipher.getInstance(ALGO); 
      c.init(Cipher.ENCRYPT_MODE, key); 
      byte[] encVal = c.doFinal(Data.getBytes()); 
      String encryptedValue = DatatypeConverter.printBase64Binary(encVal); 
      return encryptedValue; 
    } 

    public static String decrypt(String encryptedData) throws Exception { 
     Key key = generateKey(); 
     Cipher c = Cipher.getInstance(ALGO); 
     c.init(Cipher.DECRYPT_MODE, key);  
     byte[] decordedValue = DatatypeConverter.parseBase64Binary(encryptedData); 
     byte[] decValue = c.doFinal(decordedValue); 
     String decryptedValue = new String(decValue); 
     return decryptedValue; 
    } 
} 
2

Znam ten komunikat jest stary i było dawno temu - ale miałem też problemu z z dokładnie tego samego błędu:

problem miałam dotyczy faktu, zaszyfrowany tekst został przekonwertowane na String i na byte[] podczas próby ZAPROJEKTOWANIA.

private Key getAesKey() throws Exception { 
    return new SecretKeySpec(Arrays.copyOf(key.getBytes("UTF-8"), 16), "AES"); 
} 

private Cipher getMutual() throws Exception { 
    Cipher cipher = Cipher.getInstance("AES"); 
    return cipher;// cipher.doFinal(pass.getBytes()); 
} 

public byte[] getEncryptedPass(String pass) throws Exception { 
    Cipher cipher = getMutual(); 
    cipher.init(Cipher.ENCRYPT_MODE, getAesKey()); 
    byte[] encrypted = cipher.doFinal(pass.getBytes("UTF-8")); 
    return encrypted; 

} 

public String getDecryptedPass(byte[] encrypted) throws Exception { 
    Cipher cipher = getMutual(); 
    cipher.init(Cipher.DECRYPT_MODE, getAesKey()); 
    String realPass = new String(cipher.doFinal(encrypted)); 
    return realPass; 
} 
+0

Czy możesz sprawić, że będzie jaśniejszy pod względem: czy powyższy kod daje problem, czy to ten, który rozwiązuje problem? – Feng

+0

@Feng to rozwiązało problem – 2Big2BeSmall

5

Miał podobny problem. Ważne jest jednak zrozumienie podstawowej przyczyny i może być różna w różnych przypadkach użycia.

Scenariusz 1
Próbujesz odszyfrować wartość, która nie została prawidłowo zakodowany w pierwszej kolejności.

byte[] encryptedBytes = Base64.decodeBase64(encryptedBase64String); 

Jeśli łańcuch jest źle skonfigurowane dla pewnej przyczyny lub nie został zakodowany prawidłowo, czy widzisz błąd „długość wejściowa musi być wielokrotnością 16 podczas odszyfrowywania z wyściełane szyfr”

Scenariusz 2
teraz, jeśli przypadkiem używasz tego zakodowany ciąg w adresie URL (stara się przekazać w base64Encoded wartości w url, zakończy się niepowodzeniem. należy zrobić URLEncoding a następnie przechodzą w zasadzie, to będzie działać.

Scenariusz 3
Po integracji z jednym z dostawców, okazało się, że mieliśmy do czynienia szyfrowanie Base64 przy użyciu URLEncoder ale wtedy nie musimy dekodować go, ponieważ została wykonana wewnętrznie przez Sprzedającego

Powiązane problemy