我正在尝试使用DEC 3.0 库(Delphi Encryption Compedium Part I)对 Delphi 7 中的数据进行加密,并通过 POST 将其发送到 PHP 脚本,在那里我使用mcrypt(RIJNDAEL_256,ECB 模式)对其进行解密。
德尔福部分:
uses Windows, DECUtil, Cipher, Cipher1;
function EncryptMsgData(MsgData, Key: string): string;
var RCipher: TCipher_Rijndael;
begin
RCipher:= TCipher_Rijndael.Create(KeyStr, nil);
RCipher.Mode:= cmECB;
Result:= RCipher.CodeString(MsgData, paEncode, fmtMIME64);
RCipher.Free;
end;
PHP部分:
function decryptMsgContent($msgContent, $sKey) {
return mcrypt_decrypt(MCRYPT_RIJNDAEL_256, $sKey, base64_decode($msgContent), MCRYPT_MODE_ECB, mcrypt_create_iv(mcrypt_get_iv_size(MCRYPT_RIJNDAEL_256, MCRYPT_MODE_ECB), MCRYPT_RAND));
}
问题是 PHP 的解密不起作用,输出是乱码,与实际数据不同。
当然,DelphiKey
和 PHP$Key
是相同的 24 个字符的字符串。
现在我知道 DEC 3.0 已经过时且过时了,而且我不是加密专家,无法判断实施是否实际上是 Rijndael 256。也许有人可以告诉我这个实现与 PHP 的 mcrypt w/RIJNDAEL_256 有何不同。也许密钥大小不同,或者块大小不同,但无法从代码中看出这一点。这是 Cipher1.pas 的摘录:
const
{ don’t change this }
Rijndael_Blocks = 4;
Rijndael_Rounds = 14;
class procedure TCipher_Rijndael.GetContext(var ABufSize, AKeySize, AUserSize: Integer);
begin
ABufSize := Rijndael_Blocks * 4;
AKeySize := 32;
AUserSize := (Rijndael_Rounds + 1) * Rijndael_Blocks * SizeOf(Integer) * 2;
end;
附带问题:
我知道不推荐使用 ECB 模式,我会在 ECB 工作后立即使用 CBC。问题是,我是否还必须将 Delphi 中生成的 IV 传输到 PHP 脚本?或者知道密钥就足够了,比如欧洲央行?