我试图通过PHP7.4 (Laravel)和OpenSSL加密DES的值,我尝试使用在线工具https://emvlab.org/descalc/加密值,结果是预期的。
密钥:96187BBAB2BD19ACF899B74FB4E37972
输入数据:F01DCCE40F8C365ADE0A7DC03BC11DDE
加密的数据是在线工具上的355A627E977D8ECF4953C98D801E472F。https://emvlab.org/descalc/?key=96187BBAB2BD19ACF899B74FB4E37972&iv=0000000000000000&input=f01dcce40f8c365ade0a7dc03bc11dde&mode=ecb&action=Encrypt&output=D5131A2B35766D371420F679F15969FF
当用PHP编写的下一段代码无法复制结果时:
$data = "F01DCCE40F8C365ADE0A7DC03BC11DDE";
$key = "96187BBAB2BD19ACF899B74FB4E37972";
$encrypted = openssl_encrypt($data, 'DES-ECB', $key, OPENSSL_RAW_DATA | OPENSSL_NO_PADDING);
echo base64_encode($encrypted); // KV8Vie63pG2ZyjW7U5NRJUwOrbsEt+lnG1hNyS331Yk=有没有一种方法可以获得与在线工具相同的字符串?谢谢!

发布于 2021-09-15 21:36:54
网站必须考虑什么?
该网站允许在2 2TDEA变体(双长密钥)中使用DES和TripleDES加密。该算法由密钥大小决定:对于一个8字节的密钥DES,对于一个16字节的密钥TripleDES/2 2TDEA。支持的模式是欧洲央行和CBC。
密钥,IV (在CBC模式下),明文和密文必须输入十六进制编码在网站上。应用零填充(如果明文长度已经是DES/TripleDES块大小8字节的整数倍数,则不填充)。
这对公布的数据意味着什么?
由于已发布的十六进制编码密钥96187BBAB2BD19ACF899B74FB4E37972的大小为16字节,所以使用TripleDES/2 2TDEA(在欧洲央行模式下)。
十六进制编码的明文F01DCCE40F8C365ADE0A7DC03BC11DDE的大小为16字节,因此不填充。因此,得到的十六进制编码的密文355A627E977D8ECF4953C98D801E472F具有相同的长度。
如何修复PHP代码?
发布的PHP代码提供了不同的结果,因为DES被用作算法(在ECB模式下),而且也缺少十六进制编码/解码。因此,要产生网站的结果,必须对编码/解码进行修正,并且必须将DES-EDE-ECB作为算法(不要与3 3TDEA/三重长度密钥的DES-EDE3-ECB混淆):
$data = hex2bin("F01DCCE40F8C365ADE0A7DC03BC11DDE"); // hex decode the 16 bytes data
$key = hex2bin("96187BBAB2BD19ACF899B74FB4E37972"); // hex decode the 16 bytes key key
$encrypted = openssl_encrypt($data, 'DES-EDE-ECB', $key, OPENSSL_RAW_DATA | OPENSSL_ZERO_PADDING); // apply DES-EDE-ECB; use OPENSSL_ZERO_PADDING
echo bin2hex($encrypted); // 355a627e977d8ecf4953c98d801e472f // hex encode the 16 bytes ciphertext产出如下:
355a627e977d8ecf4953c98d801e472f,它等于网站s. 这里的结果。
如何才能使DES取得一致的结果?
当前PHP代码应用DES,因此仅使用前8个字节隐式地将键截断为8个字节。这可以很容易地通过删除键的最后8个字节来验证。结果不会改变。
如果将缩短的键应用于网站,则结果将再次匹配。
$data = hex2bin("F01DCCE40F8C365ADE0A7DC03BC11DDE"); // hex decode the 16 bytes data
$key = hex2bin("96187BBAB2BD19AC"); // hex decode the 8 bytes key
$encrypted = openssl_encrypt($data, 'DES-ECB', $key, OPENSSL_RAW_DATA | OPENSSL_ZERO_PADDING); // apply DES-ECB; use OPENSSL_ZERO_PADDING
echo bin2hex($encrypted); // 692370230b8176f011760ddc07392a4f // hex encode the 16 bytes ciphertext产出如下:
692370230b8176f011760ddc07392a4f这等于网站s. 这里的结果。
https://stackoverflow.com/questions/69196261
复制相似问题