Php mcrypt加密添加一组';%00';结束

Php mcrypt加密添加一组';%00';结束,php,encryption,padding,mcrypt,Php,Encryption,Padding,Mcrypt,使用OAuth并使用下面的函数用一个字符串加密密钥,我们称之为“foo”(实际上是OAuth令牌) 当我使用反函数解密它时,我得到: 功能: public function decrypt( $text ) { $text = base64_decode( $text ); return mcrypt_decrypt( MCRYPT_RIJNDAEL_128, $this->key, $text, MCRYPT_MODE_ECB, $this

使用OAuth并使用下面的函数用一个字符串加密密钥,我们称之为“foo”(实际上是OAuth令牌)

当我使用反函数解密它时,我得到:

功能:

    public function decrypt( $text )
    {
        $text = base64_decode( $text );
        return mcrypt_decrypt( MCRYPT_RIJNDAEL_128, $this->key, $text, MCRYPT_MODE_ECB, $this->iv );
    }
结果:

    public function decrypt( $text )
    {
        $text = base64_decode( $text );
        return mcrypt_decrypt( MCRYPT_RIJNDAEL_128, $this->key, $text, MCRYPT_MODE_ECB, $this->iv );
    }
foo%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00

编辑:

    public function decrypt( $text )
    {
        $text = base64_decode( $text );
        return mcrypt_decrypt( MCRYPT_RIJNDAEL_128, $this->key, $text, MCRYPT_MODE_ECB, $this->iv );
    }

再看一看,我意识到它实际上是对%00的URL编码,这意味着我的字符串不知何故被空字符填充了?因此,我目前正在使用trim()来消除它们,但我想了解为什么会发生这种情况。

Rijndael是一个,这意味着它对特定长度的数据块(本例中为128位)进行操作。这意味着,如果输入文本的长度不是块大小的倍数,则必须将其填充以适合。在这种情况下,填充为零;有许多其他可能的方法可以使用,但是如果您想使用PHP的mcrypt,您必须手动应用它们。

您可以使用此方法修复它,以消除填充字符:在我们的示例中,我们使用的是Zend

$filter = new Zend_Filter_Decrypt(array('adapter' => 'mcrypt'));
$filter->setVector($lpt->_seed);
str_replace("\x0", '', trim($filter->filter(base64_decode($textToDecrypt))));

MCRYPT\u MODE\u ECB
表示您正在使用分组密码操作模式ECB。分组密码既可以用于分组密码操作模式,也可以用于流密码操作模式。常见的分组密码模式是ECB和CBC,常见的流密码模式是CTR,通常称为计数器模式操作

MCRYPT_RIJNDAEL_128
是AES的一种实现。AES是Rijndael密码,块大小为128位,三种可能的密钥大小为128、192和256位。因此,如果使用分组密码加密模式,则需要将明文分成128位(16字节)的大小。当然,这给您留下了一个问题:当最后一个块不是16字节时,该怎么办

PHP或多或少地让用户自己决定。如果块未满到块大小,则用
00
值字符填充。如果输入是一个字符串,这是很好的;您只需从返回的字符串中删除
00
字符即可。但是,如果输入是以
00
字符结尾的二进制数据,则该字符将丢失(+当然是从字符串开头和结尾提取的任何其他字符)。当然,您也可以发送与明文一起加密的字符串长度

要获得更好的方案,只需查看PKCS#7填充。可以找到多个用于实现填充的代码段


mcrypt\u encrypt
目前似乎不支持AES的流模式,因此如果您想保留PHP mcrypt库,则该选项不可用。

恰恰相反。编辑以显示。默认填充(并且是
mcrypt
内部支持的唯一填充)是
NULL
-填充(而不是
0
)。
%00
是一个URL编码的
NULL
字符
x00
@SteanGehrig:“零”可能意味着字符U+0030或字符U+0000。@如果两者都不正常,因为我们谈论的是具有该值的字节,不是字符。这看起来像是删除了所有0x00字节,而不仅仅是填充的0x00字节。您真的应该只使用
rtrim($decrypted,“\0”)