openssl_get_cipher_methods openssl_encrypt openssl_decrypt encrypt empty decrypt cbc php security openssl

php - openssl_decrypt - Uso del Vector de Inicialización en openssl_encrypt



php openssl_encrypt aes 128 ecb (1)

Un IV es generalmente un número aleatorio que garantiza que el texto encriptado sea único.

Para explicar por qué es necesario, imaginemos que tenemos una base de datos de nombres de personas cifrada con la clave ''secreto'' y sin IV.

1 John dsfa9p8y098hasdf 2 Paul po43pokdfgpo3k4y 3 John dsfa9p8y098hasdf

Si John 1 conoce su texto de cifrado (dsfa9p8y098hasdf) y tiene acceso a los otros textos de cifrado, puede encontrar fácilmente a otras personas llamadas John.

Ahora, en realidad, un modo de encriptación que requiere IV siempre usará uno. Si no especifica un IV, se establece automáticamente en un grupo de bytes nulos. Imagine el primer ejemplo pero con una constante IV (00000000).

1 John dsfa9p8y098hasdf 00000000 2 Paul po43pokdfgpo3k4y 00000000 3 John dsfa9p8y098hasdf 00000000

Para evitar textos de cifrado repetidos, podemos encriptar los nombres usando la misma clave ''secreta'' y IV''s aleatorias:

1 John sdf875n90mh28458 45gh3546 2 Paul fg9087n5b60987nf 56897ngq 3 John gjhn0m89456vnler 8907345f

Como puede ver, los dos textos de cifrado de ''Juan'' ahora son diferentes. Cada IV es único y ha influido en el proceso de cifrado, por lo que el resultado final también es único. John 1 ahora no tiene idea de cuál es el nombre del usuario 3.

El descifrado requiere el uso de la misma IV con la que se encripta el texto, por lo que debe almacenarse en la base de datos. La IV no sirve de nada sin la clave, por lo que no es necesario transmitirla o almacenarla con el texto encriptado.

Este es un ejemplo excesivamente simplista, pero la verdad es que no usar IV tiene graves ramificaciones de seguridad.

Ahora su código parece estar configurando el IV (1234567812345678) pero no lo usa en el descifrado. Eso es seguro que fallará.

También es posible que desee utilizar algunas de las funciones de generación IV de PHP. Creo que esto debería funcionar para ti:

$iv_size = mcrypt_get_iv_size(MCRYPT_RIJNDAEL_128, MCRYPT_MODE_CBC); $iv = mcrypt_create_iv($iv_size, MCRYPT_RAND); $encryptedMessage = openssl_encrypt($textToEncrypt, $encryptionMethod, $secretHash, 0, $iv); $decryptedMessage = openssl_decrypt($encryptedMessage, $encryptionMethod, $secretHash, 0, $iv);

Para el almacenamiento / transmisión, puede concatenar el texto IV y cifrado de la siguiente manera:

$data = $iv.$encryptedMessage;

Luego, en la recuperación, extraiga el IV para descifrarlo:

$iv_size = mcrypt_get_iv_size(MCRYPT_RIJNDAEL_128, MCRYPT_MODE_CBC); $iv = substr($data, 0, $iv_size); $decryptedMessage = openssl_decrypt(substr($data, $iv_size), $encryptionMethod, $secretHash, 0, $iv);

Para obtener más información, consulte la biblioteca Mcrypt de PHP. Es bastante completo y tiene muchos ejemplos, muchos de los cuales pueden ayudarte con las implementaciones de cifrado de openssh. http://php.net/manual/en/function.mcrypt-encrypt.php

Eché un vistazo a this pregunta y quería hacerlo por mí mismo. Cuando ejecuté este código (tomado directamente de esta respuesta ):

$textToEncrypt = "My super secret information."; $encryptionMethod = "AES-256-CBC"; // AES is used by the U.S. gov''t to encrypt top secret documents. $secretHash = "25c6c7ff35b9979b151f2136cd13b0ff"; //To encrypt $encryptedMessage = openssl_encrypt($textToEncrypt, $encryptionMethod, $secretHash, ''1234567812345678''); //To Decrypt $decryptedMessage = openssl_decrypt($encryptedMessage, $encryptionMethod, $secretHash); //Result echo "Encrypted: $encryptedMessage <br>Decrypted: $decryptedMessage";

Sin embargo, recibo la advertencia

openssl_encrypt(): Using an empty Initialization Vector (iv) is potentially insecure and not recommended

Así que fui y eché un vistazo a los docs , pero "no hay documentación". Encontré este comment , pero todavía no menciono qué debería ser el Vector de inicialización y cómo debería usarlo. ¿Alguien puede iluminarme?

Sé que podría haber hecho algo más de Googleing, pero Stackoverflow aparece primero en tantos resultados de búsqueda que pensé que esta pregunta podría ser útil para cualquier otra persona que tuviera este problema.