PHP Mcrypt - 解密函数不适用于一小部分字符串

标签 php mcrypt

我知道 PHP 的 mcrypt_decrypt 上已经有上百万篇文章,但我找不到与我的结果相同的文章。我有一对简单的加密/解密函数,我想用它们对数据执行双向加密。奇怪的是,对于我输入函数的任何随机字符串的大约 4%,它不会成功解密。例如,如果我创建一个从 0 到 9999 的“for 循环”,并对这些数字的字符串版本进行加密和解密,则相同的值每次都会失败,而这些值取决于我传递给函数的 key 。我可以传递任何键,虽然失败的具体值会发生变化,但失败值的百分比将大致保持不变。

我试过不带 IV 参数的 ECB 模式,我试过带 IV 参数的 CBC 模式,结果相同。

这是我在 ECB 模式下的加密函数:

function mc_encrypt($string, $mc_key) {
    $passcrypt = trim(mcrypt_encrypt(MCRYPT_RIJNDAEL_256, $mc_key, trim($string), MCRYPT_MODE_ECB));
    $encode = base64_encode($passcrypt);

    return $encode;
}

这是我在 ECB 模式下的解密函数:

function mc_decrypt($string, $mc_key) {
    $decoded = base64_decode($string);
    $decrypted = trim(mcrypt_decrypt(MCRYPT_RIJNDAEL_256, $mc_key, trim($decoded), MCRYPT_MODE_ECB));

    return $decrypted;
}

CBC模式版本相同,只是在加密时使用mcrypt_create_iv()函数创建IV,在解密时将其作为参数传入。

在我的服务器上使用这些函数并将“abc”作为测试加密 key ,如果我从 0 运行到 300,则以下值将无法正确解密:

4、6、70、145、151、176、237、254、275

如果我将我的加密 key 更改为其他内容,它会改变正确返回的值,但不会改变值返回的频率。

有什么建议吗???

提前致谢!

最佳答案

我刚刚从您的代码中调用了两次 trim(),它就可以工作了。基本上,mcrypt_encrypt 可能会返回带有尾随空字节 (\0) 的答案,需要保留这些字节。另外,出于同样的原因,不要将 $decoded 参数修剪为 mcrypt_decrypt。当修剪来自 mcrypt_decrypt 的响应时,仅使用 rtrim

function mc_encrypt($string, $mc_key) {
    $passcrypt = mcrypt_encrypt(MCRYPT_RIJNDAEL_256, $mc_key, trim($string), MCRYPT_MODE_ECB);
    $encode = base64_encode($passcrypt);

    return $encode;
}

function mc_decrypt($string, $mc_key) {
    $decoded = base64_decode($string);
    $decrypted = rtrim(mcrypt_decrypt(MCRYPT_RIJNDAEL_256, $mc_key, $decoded, MCRYPT_MODE_ECB));

    return $decrypted;
}

关于PHP Mcrypt - 解密函数不适用于一小部分字符串,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21101078/

相关文章:

docker - 如何在 Docker 上安装 mcrypt

php - SHA1 PHP mcrypt_decrypt 结果

NodeJS 中的 PHP mcrypt_decrypt

php - 安装 php5-mcrypt 时出错

php - 在 OSX Mountain Lion 上为 PHP 安装 mcrypt 扩展

php - 如何将短信网关与parse.com的服务器集成

php - Haversine 公式中的连接操作

php - Magento 原始图像调整大小仅显示占位符图像

php - mysql_insert_id 使用安全吗?

php - 避免 mysql 中的时间/日期重叠(laravel)