4

Given this code in Delphi using DCrypt:

Uses DCPcrypt2, DCPblockciphers, DCPrijndael, DCPbase64;

procedure TForm1.Button1Click(Sender: TObject);
var Cipher : TDCP_rijndael;
    ss, k, Data, Key, IV : Ansistring;
const
  KeySize = 32; // 32 bytes = 256 bits
  BlockSize = 16; // 16 bytes = 128 bits // IV
begin
  key := '12345678901234567890123456789012';
  iv  := '1234567890123456';
  Data := 'thisis128bitstxt';

  Cipher := TDCP_rijndael.Create(nil);
  Cipher.Init(Key[1],128,@IV[1]);
  Cipher.EncryptCBC(Data[1],Data[1],Length(Data));
  Cipher.Free;

  Data := DCPBase64.Base64EncodeStr(Data);
  Memo1.Lines.Add(Data);
end;

I get the following: Eq7iMlVKysMMXdhR0rtrwA==

Trying the same in PHP with OpenSSL:

<?
    $s = "thisis128bitstxt";
    $s = openssl_encrypt($s, "AES-128-CBC", "12345678901234567890123456789012", 0, "1234567890123456");
    echo $s . "</br>";
?>

returns: Eq7iMlVKysMMXdhR0rtrwEbhkypNJyuwGafLILvwpbY=

What's wrong?

If I try to decrypt the delphi output I get an empty string:

$s = "Eq7iMlVKysMMXdhR0rtrwA==";
$s = openssl_decrypt($s, "AES-128-CBC", "12345678901234567890123456789012", 0, "1234567890123456");
echo $s . "</br>";
hikari
  • 3,393
  • 1
  • 33
  • 72
  • 2
    Looks like you are missing the padding – David Heffernan Dec 22 '16 at 14:51
  • What is your Delphi version ? Please, edit the question and add the proper tag – Arioch 'The Dec 22 '16 at 15:57
  • There is no such thing as "string" when it comes to crypto. There are sequences of bytes. But aren't strings sequences of bytes? they are, but there are many different rules how transofr text to bytes and bytes to text. They are called charsets, encodings and what not. You fixed Delphi string to `AnsiString`... Looks good. Twice so, if your copy of DCPCrypt also uses that type, not ambiguous `string` wildcard. But what does PHP use? ANYTHING your editor put into the file: http://php.net/manual/en/language.types.string.php#language.types.string.details – Arioch 'The Dec 22 '16 at 16:09
  • SO PHP string is... Well, anything. Anytrhing that web-server expects, or anything PHP IDE expects.... So i'd start fro mthe opposite direction: taking PHP-generated string and trying to decoding it in Delphi into `TBytes` or other raw sequence of bytes type, then seeing which charset can be used to turn those bytes into text. UTF-16, UTF-8, something else... – Arioch 'The Dec 22 '16 at 16:10
  • the text i need to handle is all ansi – hikari Dec 22 '16 at 17:35

1 Answers1

7

David Heffernan already guided you on the right direction. I here complete it.

you shouldn't miss padding. I fixed your code as follow.

procedure TForm1.Button1Click(Sender: TObject);
var Cipher : TDCP_rijndael;
    Data, Key, IV : ansistring;
    index, dataLength, bsize, pad: integer;
begin
  key := '12345678901234567890123456789012';
  IV  := '1234567890123456';
  Data := 'thisis128bitstxt';

  Cipher := TDCP_rijndael.Create(nil);
  try
    Cipher.Init(Key[1],128,@IV[1]);

    //don't miss padding
    {start padding}
    dataLength := Length(Data);
    bsize := (Cipher.BlockSize div 8);
    pad := bsize - (dataLength mod bsize);
    for index := 1 to pad do
      Data := Data+chr(pad);
    {end padding}

    Cipher.EncryptCBC(Data[1],Data[1],Length(Data));
  finally
    Cipher.Free;
  end;

  Data := DCPBase64.Base64EncodeStr(Data);
  Memo1.Lines.Add(Data);
end;

you will get the same result as php now.

Loghman
  • 1,500
  • 1
  • 14
  • 30
  • There is an issue with this, if now I want to decrypt the data I won't get the same original input since there is the extra padding, how would you detect how much to remove from the end of the file to get back 100% the original content? – hikari Jan 10 '17 at 03:38
  • nvm that, switched to CTR, then I don't need the padding. – hikari Jan 10 '17 at 06:11
  • @hikari It is easy. the last character shows how much you should delete. `slen:=Length(src); cipher.Init(key[0], 128, @iv[0]); cipher.Decrypt(src[0], dest[0], slen); pad := dest[slen - 1]; SetLength(dest, slen - pad); result := TEncoding.ASCII.GetString(dest);` – Loghman Jan 10 '17 at 11:34
  • 1
    but then how do you discern whether it's padding or actual data? – hikari Jan 10 '17 at 14:26