通过mcrypt加密,并通过opensl以CBC模式和密码BLOWFISH解密

时间:2018-09-18 13:06:20

标签: php encryption openssl mcrypt

我们已使用mcrypt密码BLOWFISH加密了某些数据,并且模式为CBCphp5.5中加密的字符串,并且需要在php7.1中进行解密(PHP版本已升级)

以下是我们尝试使用openssl解密mcrypt字符串的代码

$data = "Lorem ipsum";
$key = "12345678";
$iv = "12345678";

$encrypted = mcrypt_encrypt(
    MCRYPT_BLOWFISH, $key, $data, MCRYPT_MODE_CBC, $iv);
echo $encrypted . PHP_EOL;

$decrypted = openssl_decrypt(
    $encrypted, "BF-CBC", $key,
    OPENSSL_RAW_DATA | OPENSSL_ZERO_PADDING, $iv);

echo $decrypted;

以上代码未解密字符串。 请建议我任何解密字符串的方法

1 个答案:

答案 0 :(得分:2)

您在openssl方面缺少一个选择:OPENSSL_DONT_ZERO_PAD_KEY

如果给openssl_decrypt()的密钥的长度小于密码的默认密钥长度(在这种情况下为Blowfish),PHP openssl粘合代码会通过添加其他密码来将密钥扩展为该长度零。您可以看到它here发生了。 mcrypt实现不执行该键填充。 Blowfish的openssl默认密钥长度为16个字节,因此,如果您的密钥短于16个字节,则mcryptopenssl的密钥将有所不同-除非您使用{{ 1}}选项不进行键的填充。

确认确实如此:

openssl

# bf.php
$data = "Lorem ipsum";
$key = "12345678";
$iv = "12345678";

$encrypted = mcrypt_encrypt(
    MCRYPT_BLOWFISH, $key, $data, MCRYPT_MODE_CBC, $iv);
#echo $encrypted . PHP_EOL;

$decrypted = openssl_decrypt(
    $encrypted, "BF-CBC", $key,
    OPENSSL_RAW_DATA | OPENSSL_ZERO_PADDING | OPENSSL_DONT_ZERO_PAD_KEY, $iv);

echo $decrypted . PHP_EOL;

This comment by t.m.adam对于结尾处的零也很重要。扩展该建议:

$ php bf.php
Lorem ipsum

给予

var_dump($decrypted);
var_dump(rtrim($decrypted));

您当然不能对二进制数据执行string(16) "Lorem ipsum" string(11) "Lorem ipsum" ,在这种情况下,您将必须记住或存储原始明文的大小,或者根据一些有用的填充模式手动填充数据零填充。 rtrim似乎无法做到这一点。