Шифрование с использованием AES-128 в Java

У меня проблема с шифрованием данных с использованием AES-128 / ecb / PKCS5Padding + base64. Для шифрования моих данных я использую следующий код:

String input = "{\"action\":\"getQuestion\"}"; String key = "4288f0b8060ca1b682bf795f2617cfdc"; byte[] data = input.getBytes(); byte[] encrypted = null; byte[] keyBytes = new BigInteger(key, 16).toByteArray(); SecretKeySpec keySpec = new SecretKeySpec(keyBytes, "AES"); Cipher cipher = Cipher.getInstance("AES/ECB/PKCS5Padding"); cipher.init(Cipher.ENCRYPT_MODE, keySpec); encrypted = cipher.doFinal(data); System.out.println(Base64.encodeBytes(encrypted)); 

Я получаю 6GuKXA6FFR+yMmO8ksAEOLL5e574a5tLob7tt5IG+jk= после шифрования, но я не могу расшифровать на сервере с помощью функции PHP.

Когда я шифрую эти данные с помощью функции PHP:

 function encrypt($encrypt, $key=null) { $iv = mcrypt_create_iv(mcrypt_get_iv_size(MCRYPT_RIJNDAEL_128, MCRYPT_MODE_ECB), MCRYPT_RAND); $encrypted = base64_encode(mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $key, $encrypt, MCRYPT_MODE_ECB, $iv)); return $encrypted; } 

Я получаю 6Wc3LPWvfJ7T86iG0igmdQaeZ8xs9qY419mAVWfNH+M= и я могу успешно выполнить дешифрование с использованием следующей функции PHP:

 function decrypt($decrypt, $key=null) { $iv = mcrypt_create_iv(mcrypt_get_iv_size(MCRYPT_RIJNDAEL_128, MCRYPT_MODE_ECB), MCRYPT_RAND); $decrypted = mcrypt_decrypt(MCRYPT_RIJNDAEL_128, $key, base64_decode($decrypt), MCRYPT_MODE_ECB, $iv); return $decrypted; } 

При шифровании и расшифровке base64 проблем нет; Я только сталкиваюсь с проблемой при шифровании с использованием AES-128.

Проблема не в том, что я или подушка, как я изначально думал. Именно с тем, как вы обрабатываете ключ в PHP-коде. Если вы используете фактическую строку 4288f0b8060ca1b682bf795f2617cfdc в качестве ключа, переданного в mcrypt_encrypt и mcrypt_decrypt то вы не используете тот же ключ, что и в коде Java. Вам нужно будет преобразовать эту шестую строку в байты. Вы можете сделать это следующим образом:

 $decrypted = mcrypt_decrypt(MCRYPT_RIJNDAEL_128, pack("H*", $key), base64_decode($decrypt), MCRYPT_MODE_ECB, $iv); 

Обратите внимание на добавление pack("H*", $key) для преобразования значения. Я нашел это здесь в комментариях к функции PHP bin2hex . Это устранит текущую проблему. Вы можете столкнуться с неприятностями при работе с данными разной длины, так как PHP не выполняет добавление PKCS5. См. Этот комментарий о реализации этой недостающей функции. Кроме того, я бы рекомендовал рассматривать CBC вместо ECB из-за непригодности и недостатков ECB для шифрования данных.

Вы можете проверить результат с помощью Java-метода в командной строке с помощью openssl. Java будет отклонять ваш IV до 0, если это не указано.

 The file "enc.txt" contains "6GuKXA6FFR+yMmO8ksAEOLL5e574a5tLob7tt5IG+jk=" [corrected] 

Бег

 openssl aes-128-ecb -in enc.txt -a -K 4288f0b8060ca1b682bf795f2617cfdc -iv 0 -d 

Результат:

 {"action":"getQuestion"} 

Попробуйте mcrypt_decrypt с значением $ iv 0.