准备在PHP 7.2中删除Mcrypt

Scr*_*lex 7 php openssl mcrypt php-7.1

因此,随着时间的推移,mcrypt将进入PHP 7.2.当然还有另一种选择:openssl.

我发现很难从mcrypt切换到openssl,使用AES 256 CBC并保留IV.我对密码学有点新意,所以我真的不知道所有内容,但我理解基础知识.

假设我有以下代码

function encrypt($masterPassword, $data) 
{
    $keySize = mcrypt_get_key_size(MCRYPT_RIJNDAEL_256, MCRYPT_MODE_CBC);
    $ivSize = mcrypt_get_iv_size(MCRYPT_RIJNDAEL_256, MCRYPT_MODE_CBC);
    $iv = mcrypt_create_iv($ivSize, MCRYPT_DEV_URANDOM);
    $key = mb_substr(hash('SHA256', $masterPassword), 0, $keySize);
    $encrypted = mcrypt_encrypt(MCRYPT_RIJNDAEL_256, $key, $data, MCRYPT_MODE_CBC, $iv);
    return base64_encode($iv . $encrypted);
}

function decrypt($masterPassword, $base64) 
{
    $keySize = mcrypt_get_key_size(MCRYPT_RIJNDAEL_256, MCRYPT_MODE_CBC);
    $ivSize = mcrypt_get_iv_size(MCRYPT_RIJNDAEL_256, MCRYPT_MODE_CBC);
    $key = mb_substr(hash('SHA256', $masterPassword), 0, $keySize);
    $data = base64_decode($base64);
    $iv = substr($data, 0, $ivSize);
    $encrypted = substr($data, $ivSize, strlen($data));
    $decrypted = mcrypt_decrypt(MCRYPT_RIJNDAEL_256, $key, $encrypted, MCRYPT_MODE_CBC, $iv);
    return trim($decrypted);
}
Run Code Online (Sandbox Code Playgroud)

如何"转换"此代码以使用mcrypt的openssl?

Nar*_*arf 12

你不能转换它,因为Rijndael-256不是AES-256,而OpenSSL扩展不支持Rijndael-256.
AES-256是Rijndael-128,带有256位(32字节)密钥.

不幸的是,您必须重新加密所有数据.

编辑:此外,您当前使用的方案有一些问题:

  • 它缺乏身份验证(HMAC是PHP中最简单的方法)
  • 它没有适当的填充(mcrypt pad只有零字节;你需要像PKCS#5填充这样的东西),这是块模式加密安全所必需的.
  • 这不是字节安全的(你正在使用mb_substr())

好消息是OpenSSL会自动为你做PKCS#5填充,但你应该更进一步,使用像defuse/php-encryption这样的可靠加密库.