Delphi DEC库(Rijndael)加密 [英] Delphi DEC library (Rijndael) encryption

查看:276
本文介绍了Delphi DEC库(Rijndael)加密的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试使用 DEC 3.0库 Delphi Encryption Compedium Part I )来加密Delphi 7中的数据,并通过POST将其发送到PHP脚本,其中我使用 mcrypt (RIJNDAEL_256,ECB模式)进行解密。 p>

Delphi部分:

 使用Windows,DECUtil,Cipher,Cipher1; 

函数EncryptMsgData(MsgData,Key:string):string;
var RCipher:TCipher_Rijndael;
begin
RCipher:= TCipher_Rijndael.Create(KeyStr,nil);
RCipher.Mode:= cmECB;
结果:= RCipher.CodeString(MsgData,paEncode,fmtMIME64);
RCipher.Free;
结束

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解密不起作用,输出是乱码,与实际数据不同。



当然,Delphi Key 和PHP $ Key 是相同的24个字符的字符串。



现在我知道DEC 3.0是旧的和过时的,不是加密专家,不能确定实现是否实际上是Rijndael 256.也许有人可以告诉我这个实现与PHP的mcrypt w / RIJNDAEL_256的区别。也许keyize是不同的,或块的大小,但是不能从代码中得出这个。以下是Cipher1.pas的摘录:

  const 
{不要更改}
Rijndael_Blocks = 4;
Rijndael_Rounds = 14;

类过程TCipher_Rijndael.GetContext(var ABufSize,AKeySize,AUserSize:Integer);
begin
ABufSize:= Rijndael_Blocks * 4;
AKeySize:= 32;
AUserSize:=(Rijndael_Rounds + 1)* Rijndael_Blocks * SizeOf(Integer)* 2;
结束

侧面问题:



我知道ECB不建议使用模式,一旦得到ECB工作,我将使用CBC。问题是,我必须将Delphi中生成的IV传递给PHP脚本吗?或者知道密钥是否足够,像ECB一样?

解决方案

您正在调用TCipher.Create(const Password:String; AProtection :TProtection);构造函数,它将在将其传递给执行所实现的算法的标准密钥调度的Init方法之前计算密码的哈希值。要重写此密钥派生,请使用:

 函数EncryptMsgData(MsgData,Key:string):string; 
var RCipher:TCipher_Rijndael;
begin
RCipher:= TCipher_Rijndael.Create('',nil);
RCipher.Init(指针(Key)^,Length(Key),nil);
RCipher.Mode:= cmECB;
结果:= RCipher.CodeString(MsgData,paEncode,fmtMIME64);
RCipher.Free;

结束;


I am trying to use the DEC 3.0 library (Delphi Encryption Compedium Part I) to encrypt data in Delphi 7 and send it to a PHP script through POST, where I am decrypting it with mcrypt (RIJNDAEL_256, ECB mode).

Delphi part:

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 part:

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));
}

The problem is that the decryption from PHP doesn't work and the output is gibberish, differing from the actual data.

Of course, Delphi Key and PHP $Key is the same 24 characters string.

Now I know DEC 3.0 is old and outdated, and I'm not an expert in encryption and can't tell if the inplementation is actually Rijndael 256. Maybe someone can tell me how this implementation differs from PHP's mcrypt w/ RIJNDAEL_256. Maybe the keysize is different, or the block size, but can't tell this from the code. Here's an excerpt from 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;

Side question:

I know ECB mode isn't recommended and I'll use CBC as soon as I get ECB working. The question is, do I have to transmit the generated IV in Delphi to the PHP script also? Or knowing the key is sufficient, like for ECB?

解决方案

You are calling the TCipher.Create(const Password: String; AProtection: TProtection); constructor, which will compute a hash of the password before passing it to the Init method, which performs the standard key schedule of the implemented algorithm. To override this key derivation, use:

function EncryptMsgData(MsgData, Key: string): string;
var RCipher: TCipher_Rijndael;
begin
  RCipher:= TCipher_Rijndael.Create('', nil);
  RCipher.Init(Pointer(Key)^,Length(Key),nil);
  RCipher.Mode:= cmECB;
  Result:= RCipher.CodeString(MsgData, paEncode, fmtMIME64);
  RCipher.Free;

end;

这篇关于Delphi DEC库(Rijndael)加密的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆