Node.js aes128到PHP的加密/解密端口

Node.js aes128到PHP的加密/解密端口,php,node.js,encryption,openssl,aes,Php,Node.js,Encryption,Openssl,Aes,因此,在node.js中,我有一个使用aes128的加密方案,但没有通过IV。下面是一个示例 var cipher = require('crypto').createCipher('aes128','password'); cipher.update('test','utf8','base64')+cipher.final('base64'); 输出CjZ3R/tW8jiyLvg+/TE6bA==。问题是,尽管我已经尝试了许多实现和变体,但我无法在PHP中重现这一点 然后,当我尝试通过o

因此,在node.js中,我有一个使用aes128的加密方案,但没有通过IV。下面是一个示例

 var cipher = require('crypto').createCipher('aes128','password');
 cipher.update('test','utf8','base64')+cipher.final('base64');
输出CjZ3R/tW8jiyLvg+/TE6bA==。问题是,尽管我已经尝试了许多实现和变体,但我无法在PHP中重现这一点

然后,当我尝试通过openssl运行此操作时,我运行以下操作:

 echo "test" | openssl enc -e -aes128 -a -k password
输出U2FSDGVKX19CCFV3SWVUZZWEOV9GDUWX1RMK2HWA/s=也不匹配。我也尝试过使用-md和所有可能的选项,但它们都不匹配,或者它们甚至不是相同的块大小。在PHP中运行时,我尝试过对键进行散列,而不是散列,使用填充,在输入上使用计算出的填充,其中填充字符是所需的填充字符数。我在网上看到一些信息,说这是nodejs使用的。我已经尝试将IV设置为密码,也设置为空字节,但仍然无法找到匹配项

这里有什么建议/想法吗

编辑:

因此,我刚刚在php中发现了函数openssl_encrypt,并通过该函数尝试了相同的测试,再次得到了完全不同的输出。该函数现在使用与node.js完全相同的参数,并且假设它们都使用openssl:

 openssl_encrypt ( "test" , 'aes128' , "password")
base64 JLEA91MVYHDENJ3KYHMOG==中已存在的输出,至少现在在块计数中匹配,但仍然不是相同的密文


我还应该提到,是的,将IV传递给nodejs是一个选项,可能会解决这个问题,但是php中的这个方案将取代nodejs中已经存在的旧方案,因此它必须能够解密已经创建的密文,所以我找到了解决方案。通过查看NoDE.js的C++源代码,我发现密钥和IV是使用OpenSSL函数EVPyByTestKEY生成的。在搜索此函数的实现后,我找到了此堆栈溢出帖子,其中包含此函数的一个版本。修改了这一点并添加了一个事实,即openssl版本使用ascii字符填充数据,ascii字符等于填充所需的字节数。我使用了以下函数,该函数与nodejs加密方案完全匹配:

function aes128Encrypt($key, $data) {
    $padding = 16 - (strlen($data) % 16);
    $data .= str_repeat(chr($padding), $padding);

    $keySize   = 16;
    $ivSize    = 16;

    $rawKey = $key;
    $genKeyData = '';
    do
    {
        $genKeyData = $genKeyData.md5( $genKeyData.$rawKey, true );
    } while( strlen( $genKeyData ) < ($keySize + $ivSize) );

    $generatedKey = substr( $genKeyData, 0, $keySize );
    $generatedIV  = substr( $genKeyData, $keySize, $ivSize );

    print($generatedIV);
    print($generatedKey);

    return mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $generatedKey, $data, MCRYPT_MODE_CBC, $generatedIV);
}

所以我想出了解决办法。通过查看NoDE.js的C++源代码,我发现密钥和IV是使用OpenSSL函数EVPyByTestKEY生成的。在搜索此函数的实现后,我找到了此堆栈溢出帖子,其中包含此函数的一个版本。修改了这一点并添加了一个事实,即openssl版本使用ascii字符填充数据,ascii字符等于填充所需的字节数。我使用了以下函数,该函数与nodejs加密方案完全匹配:

function aes128Encrypt($key, $data) {
    $padding = 16 - (strlen($data) % 16);
    $data .= str_repeat(chr($padding), $padding);

    $keySize   = 16;
    $ivSize    = 16;

    $rawKey = $key;
    $genKeyData = '';
    do
    {
        $genKeyData = $genKeyData.md5( $genKeyData.$rawKey, true );
    } while( strlen( $genKeyData ) < ($keySize + $ivSize) );

    $generatedKey = substr( $genKeyData, 0, $keySize );
    $generatedIV  = substr( $genKeyData, $keySize, $ivSize );

    print($generatedIV);
    print($generatedKey);

    return mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $generatedKey, $data, MCRYPT_MODE_CBC, $generatedIV);
}

你有没有检查过OpenSSL和PHP是否都会生成IV?我想他们都会,不管怎样,我刚刚发现了openssl_encrypt,我希望它能像预期的那样工作,因为它现在使用的是实际的aes128,而不是MCRYPT_RIJNDAEL_128,但仍然不匹配。你检查过openssl和PHP是否都能生成IV吗?我想它们都能,不管怎样,我刚刚发现了openssl_encrypt,我希望它能像预期的那样工作,因为它现在使用的是实际的aes128而不是MCRYPT_RIJNDAEL_128,但仍然不匹配