【问题标题】:PHP : mcrypt & openssl producing different outputPHP:mcrypt & openssl 产生不同的输出
【发布时间】:2019-09-11 23:22:40
【问题描述】:

希望有人能对此有所了解。

我正在使用 DES-CBC 密码更新一些使用 mcrypt_generic 函数的旧代码

当我更新此代码以使用 openssl_encrypt 时,我得到相同的输出,但在我的编码字符串末尾附加了 8 个字节。

之前

$this->_cipher = mcrypt_module_open(MCRYPT_DES, '', MCRYPT_MODE_CBC,'');
mcrypt_generic_init($this->_cipher, $this->_key, $this->_iv) 
mcrypt_generic($this->_cipher, $text)

方法输出前:

27049189e7e08db6

之后

openssl_encrypt($text, "DES-CBC", $this->_key,  OPENSSL_RAW_DATA , $this->_iv);

方法输出后:

27049189e7e08db6d504d16516e1c567

为什么会发生这种情况,还有什么(除了子字符串)可以防止它发生?

【问题讨论】:

  • 我会查看填充。由于 openssl 是一个现代库,它可能使用现代填充标准(如 PKCS#7),而 mcrypt 可以使用较旧的技术(如零填充)。我不确定,但我遇到了类似的问题,我认为是填充不同。

标签: php encryption openssl


【解决方案1】:

根据this

1.3。数据大小

DES 算法在八个八位字节的块上运行。这通常需要在未加密的有效负载数据结束后进行填充。

它可能只是简单地填充输入。

mcrypt_encrypt() 似乎默认填充为 0(基于 docs 中的代码示例):

# creates a cipher text compatible with AES (Rijndael block size = 128)
# to keep the text confidential 
# only suitable for encoded input that never ends with value 00h
# (because of default zero padding)
$ciphertext = mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $key,
$plaintext, MCRYPT_MODE_CBC, $iv);

这可以解释长度的差异。

【讨论】:

    【解决方案2】:

    所以我设法找到了解决方案

    openssl_encrypt($text, "DES-CBC", $this->_key,  OPENSSL_NO_PADDING, $this->_iv);
    

    这种模式,

    OPENSSL_NO_PADDING

    似乎产生了我期望的输出

    【讨论】:

    • 奇怪的是,PHP 文档没有提到这种模式。只有“OPENSSL_RAW_DATA”和“OPENSSL_ZERO_PADDING”
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2020-06-12
    • 2014-05-06
    • 2014-08-24
    • 1970-01-01
    • 1970-01-01
    • 2016-06-28
    • 2019-12-12
    相关资源
    最近更新 更多