Goneja
Goneja

Reputation: 3

DES Encryption from C# to PHP not working as expected

I have to recreate things from c# to php. I dont really know what to do cuz I never really had to deal with things like encryption or something.

In c# I got this:

public static byte[] decrypt(byte[] data, byte[] key)
    {
        DESCryptoServiceProvider des = new DESCryptoServiceProvider();

        des.Key = key;
        des.Mode = CipherMode.ECB;
        des.Padding = PaddingMode.None;

        return des.CreateDecryptor().TransformFinalBlock(data, 0, data.Length);
    }

public static byte[] encrypt(byte[] data, byte[] key)
    {
        DESCryptoServiceProvider des = new DESCryptoServiceProvider();

        des.Key = key;
        des.Mode = CipherMode.ECB;
        des.Padding = PaddingMode.None;

        return des.CreateEncryptor().TransformFinalBlock(data, 0, data.Length);
    }

public static byte[] get8byte(string input)
    {
        byte[] ByteArray = new byte[8];
        string tmp = string.Empty;
        int j = 0;
        for (int i = 0; i < 16; i++)
        {
            tmp = "" + input[i];
            tmp = tmp + input[i + 1];
            ByteArray[j] = byte.Parse(tmp, System.Globalization.NumberStyles.HexNumber);
            j++;
            i++;
        }
        return ByteArray;
    }

and the key i have to use is encrypted like the following:

var Buffer = new char[16];
var cMasterKey = new byte[8];
byte[] Key = {
       (byte) '1', (byte) '2', (byte) '3', (byte) '4', (byte) '5',
       (byte) '6', (byte) '7', (byte) '8'
}; 
cMasterKey = DESUtils.get8byte(new string(Buffer));
MasterKey = DESUtils.decrypt(cMasterKey, Key);

The "Buffer" comes from an USB Drive which has a File on it which contains a Masterkey of 16 Chars. I really don't know how to realize it in PHP. I tried a lot of things like pack('C*', $var) and things like that but I didnt get the same result. Is there anyone here who knows how to handle it? I dont know if I'm on the right way but I tried things like this:

$key = pack('C*', 1, 2, 3, 4, 5, 6, 7, 8);
$masterbyte = pack('C*', $buffer);
$decmasterkey = mcrypt_decrypt(MCRYPT_DES, $key, $masterbyte, MCRYPT_MODE_ECB);

Upvotes: 0

Views: 383

Answers (1)

Artjom B.
Artjom B.

Reputation: 61952

'1' in C# is a character literal. Characters can be directly cast to a byte under the default ASCII assumption. So '1' is actually a 0x31 byte and not a 0x01 byte like you have in PHP.

You "want":

$key = "12345678";

Whether the decoding of $buffer is correct depends on its content and how you read it.


Some notes:

  • Don't use DES nowadays. It's really insecure. AES is a better alternative.

  • Never use ECB mode. It's deterministic and therefore not semantically secure. You should at the very least use a randomized mode like CBC or CTR. It is better to authenticate your ciphertexts so that attacks like a padding oracle attack are not possible. This can be done with authenticated modes like GCM or EAX, or with an encrypt-then-MAC scheme.

Upvotes: 1

Related Questions