如果您想在 mcrypt 已被弃用的较新版本的 PHP 上使用 mcrypt,请尝试使用它的垫片
https://github.com/phpseclib/mcrypt_compat
如果您想在 mcrypt 已被弃用的较新版本的 PHP 上使用 mcrypt,请尝试使用它的垫片
https://github.com/phpseclib/mcrypt_compat
安装 php7.2-mcrypt 时问题解决
我也遇到了同样的问题。查看此链接 https://stackoverflow.com/q/48275494/7713811 以获取在 PHP 中安装它的正确解决方案
这之前由另一位用户发布,但已被否决。我只想确认我们在 CentOS (PHP 5.6.32) 上遇到了与 mcrypt 相关的重大性能问题,而在其他 Linux 版本中则不存在此问题。
在 CentOS 7 上运行 mcrypt 时,25,000 次加密/解密的采样时间比 Ubuntu 长 4-5 倍。在 CentOS 上将 mcrypt 替换为 OpenSSL 将导致性能大幅提升。
对于流量较低的网站,它可能可以忽略不计,但当您开始看到大量的流量/负载时,它会很快使服务器崩溃。
如果使用 phpmyadmin 但没有安装 mcrypt,则会被重定向到此手册。如果要在 Debian 上安装 mcrypt,请先检查您的 PHP 版本
yourserver# php --version
然后安装相应版本的 mcrypt (如果您的 PHP 版本为 5.x,则安装 php5-mcrypt)
yourserver# apt-get install php4-mcrypt
…或者…
yourserver# apt-get install php5-mcrypt
请注意,在许多 CentOS 版本上,PHP mcrypt 存在严重的性能问题。请查看此 CentOS 错误
http://bugs.centos.org/view.php?id=8954
如果您想快速查看服务器上支持哪些密码、模式、密钥、块和 IV 大小,请尝试以下操作。
注意:我在 Mac OS X 上的终端中使用了这个简单的 bash:`locate libmcrypt` 来确定算法和模式目录的安装路径。许多函数调用会为某些密码生成警告,因此使用了错误抑制。
<?php
$modes = mcrypt_list_modes();
$algorithms = mcrypt_list_algorithms();
foreach($algorithms as $cipher)
{
echo "<h1 style=\"border-top:1px solid black;\">".$cipher."</h1>\n";
foreach($modes as $mode)
{
echo "<h3>".$mode."</h3>\n";
@$td = mcrypt_module_open(
$cipher,
'/usr/local/libmcrypt-2.5.8/modules/algorithms/',
$mode,
'/usr/local/libmcrypt-2.5.8/modules/modes/');
@$key_size = mcrypt_enc_get_key_size($td);
@$block_size = mcrypt_get_block_size($cipher,$mode);
@$iv_size = mcrypt_get_iv_size($cipher, $mode);
@mcrypt_module_close($td);
echo "
<pre>
key_size: ". ($key_size?$key_size:'n/a')
." block_size: ". ($block_size?$block_size:'n/a')
." iv_size: ". ($iv_size?$iv_size:'n/a')
." </pre>\n";
$td=NULL;
$key_size=NULL;
$block_size=NULL;
$iv_size=NULL;
}
}
?>
这是我为使用 mcrypt 进行 256 位加密/解密而构建的两个简单函数。我决定使用 MCRYPT_RIJNDAEL_128,因为它符合 AES 标准,并且使用 MCRYPT_MODE_CBC。(ECB 模式对于许多目的来说是不够的,因为它不使用 IV。)
此函数存储数据的哈希值,以验证数据是否已成功解密,但如果需要,可以轻松删除它。
<?php
function encrypt($decrypted, $password, $salt='!kQm*fF3pXe1Kbm%9') {
// 构建一个 256 位的 $key,它是 $salt 和 $password 的 SHA256 哈希值。
$key = hash('SHA256', $salt . $password, true);
// 构建 $iv 和 $iv_base64。我们使用 128 位的块大小(符合 AES 标准)和 CBC 模式。(注意:ECB 模式不足,因为没有使用 IV。)
srand(); $iv = mcrypt_create_iv(mcrypt_get_iv_size(MCRYPT_RIJNDAEL_128, MCRYPT_MODE_CBC), MCRYPT_RAND);
if (strlen($iv_base64 = rtrim(base64_encode($iv), '=')) != 22) return false;
// 使用 $key 加密 $decrypted 和 $decrypted 的 MD5。这里可以使用 MD5,因为它只是为了验证解密是否成功。
$encrypted = base64_encode(mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $key, $decrypted . md5($decrypted), MCRYPT_MODE_CBC, $iv));
// 我们完成了!
return $iv_base64 . $encrypted;
}
function decrypt($encrypted, $password, $salt='!kQm*fF3pXe1Kbm%9') {
// 构建一个 256 位的 $key,它是 $salt 和 $password 的 SHA256 哈希值。
$key = hash('SHA256', $salt . $password, true);
// 获取 $iv,它是前 22 个字符加上 ==,并进行 base64_decoded。
$iv = base64_decode(substr($encrypted, 0, 22) . '==');
// 从 $encrypted 中删除 $iv。
$encrypted = substr($encrypted, 22);
// 解密数据。rtrim 不会破坏数据,因为最后 32 个字符是 md5 哈希值;因此任何 \0 字符都必须是填充。
$decrypted = rtrim(mcrypt_decrypt(MCRYPT_RIJNDAEL_128, $key, base64_decode($encrypted), MCRYPT_MODE_CBC, $iv), "\0\4");
// 获取 $hash,它是 $decrypted 的最后 32 个字符。
$hash = substr($decrypted, -32);
// 从 $decrypted 中删除最后 32 个字符。
$decrypted = substr($decrypted, 0, -32);
// 完整性检查。如果失败,则数据已损坏,或者密码/盐不正确。
if (md5($decrypted) != $hash) return false;
// 成功!
return $decrypted;
}
?>