Php mcrypt_decrypt:在少量数据上生成IV会导致结果损坏

Php mcrypt_decrypt:在少量数据上生成IV会导致结果损坏,php,cakephp,encryption,Php,Cakephp,Encryption,我查看了此条目并测试了一些建议: 我有一个非常小的pdf文件(141.06 kb),它是使用wkhtmltopdf从网页创建的,并使用此函数进行加密: public function encrypt($data) { if ($data !== '') { $iv = mcrypt_create_iv($this->iv_size, MCRYPT_DEV_URANDOM); $plaintext_utf8 = utf8_encode($data)

我查看了此条目并测试了一些建议:

我有一个非常小的pdf文件(141.06 kb),它是使用wkhtmltopdf从网页创建的,并使用此函数进行加密:

public function encrypt($data) {
    if ($data !== '') {

        $iv = mcrypt_create_iv($this->iv_size, MCRYPT_DEV_URANDOM);

        $plaintext_utf8 = utf8_encode($data);
        return base64_encode($iv) . base64_encode(mcrypt_encrypt(MCRYPT_RIJNDAEL_128, Configure::read('Cryptable.key'), $plaintext_utf8, MCRYPT_MODE_CBC, $iv));
    } else {
        return '';
    }
}
public function decrypt($data, $data2 = null) {
    if (is_object($data)) {
        unset($data);
        $data = $data2;
    }

    if ($data != '') {
        $iv = base64_decode(substr($data, 0, strlen(base64_encode(mcrypt_create_iv($this->iv_size, MCRYPT_DEV_URANDOM)))));
        $data = base64_decode(substr($data, strlen(base64_encode(mcrypt_create_iv($this->iv_size, MCRYPT_DEV_URANDOM)))));

        return trim(mcrypt_decrypt(MCRYPT_RIJNDAEL_128, Configure::read('Cryptable.key'), $data, MCRYPT_MODE_CBC, $iv));
    } else {
        return '';
    }
}
如上所述,我在SO帖子上测试了一些建议,发现:

iv_尺寸=16

iv的长度=18

使用相同函数加密的任何其他较大的文档都会正确解密,因此我试图弄清楚的是如何处理非常小的文件。是否在计算少量数据的iv时,结果可能是不可预测的

这是解密函数:

public function encrypt($data) {
    if ($data !== '') {

        $iv = mcrypt_create_iv($this->iv_size, MCRYPT_DEV_URANDOM);

        $plaintext_utf8 = utf8_encode($data);
        return base64_encode($iv) . base64_encode(mcrypt_encrypt(MCRYPT_RIJNDAEL_128, Configure::read('Cryptable.key'), $plaintext_utf8, MCRYPT_MODE_CBC, $iv));
    } else {
        return '';
    }
}
public function decrypt($data, $data2 = null) {
    if (is_object($data)) {
        unset($data);
        $data = $data2;
    }

    if ($data != '') {
        $iv = base64_decode(substr($data, 0, strlen(base64_encode(mcrypt_create_iv($this->iv_size, MCRYPT_DEV_URANDOM)))));
        $data = base64_decode(substr($data, strlen(base64_encode(mcrypt_create_iv($this->iv_size, MCRYPT_DEV_URANDOM)))));

        return trim(mcrypt_decrypt(MCRYPT_RIJNDAEL_128, Configure::read('Cryptable.key'), $data, MCRYPT_MODE_CBC, $iv));
    } else {
        return '';
    }
}
IV尺寸的计算如下:

$this->iv_size = mcrypt_get_iv_size(MCRYPT_RIJNDAEL_128, MCRYPT_MODE_CBC);

在我忘记之前,我正在使用CakePHP 2.6.4

为什么要对IV和密钥进行编码、解码和字符串操作?您知道CakePHP附带了加密功能吗。除了其他一些奇怪的东西,你为什么要盲目地修剪两端?你确定这不会删除必要的数据吗?奇怪的原因是,这是一个继承的代码,在这个代码下,使用这种方法已经有成百上千的加密文件。只有在添加了一个新的pdf创建一个已经存在的web表单之后,我们才注意到这一点。我不知道为什么不使用Cake的加密方案,但我相信这与docx文件的损坏有关。我只是想澄清一下,这种方法适用于所有其他文件,但非常小的文件除外。