TripleDES implementation in Javascript different comparing with C#

c#, cryptojs, javascript, tripledes

Solution

TripleDES requires 24-byte key (k1 + k2 + k3). Your key is only 16-byte. And .NET auto completes with k3 = k1. But Javascript does not, k3 = 0. Please modify the key:

if (useHashing){
   key = CryptoJS.MD5(key).toString();
   var k1 = key.substring(0, 16);
   key = key + k1;
}

Problem

I need to replicate the following C# method to encrypt some text from Javascript. Currently I am using Crypto JS, but the output from JS is not equals to the C# output. ``` const string EncryptKey = "hello"; private static String getHexStringFromArray(byte[] arr) { StringBuilder sBuilder = new StringBuilder(); for (int i = 0; i < arr.Length; i++) { sBuilder.Append(arr[i].ToString("x2")); } return sBuilder.ToString(); } public void Encrypt(string toEncrypt, bool useHashing) { byte[] keyArray; byte[] toEncryptArray = UTF8Encoding.UTF8.GetBytes(toEncrypt); string key = EncryptKey; if (useHashing) { MD5CryptoServiceProvider hashmd5 = new MD5CryptoServiceProvider(); keyArray = hashmd5.ComputeHash(UTF8Encoding.UTF8.GetBytes(key)); hashmd5.Clear(); } else keyArray = UTF8Encoding.UTF8.GetBytes(key); Console.WriteLine("hexadecimal key: " + getHexStringFromArray(keyArray)); TripleDESCryptoServiceProvider tdes = new TripleDESCryptoServiceProvider(); tdes.Key = keyArray; tdes.Mode = CipherMode.ECB; tdes.Padding = PaddingMode.PKCS7; ICryptoTransform cTransform = tdes.CreateEncryptor(); byte[] resultArray = cTransform.TransformFinalBlock(toEncryptArray, 0, toEncryptArray.Length); tdes.Clear(); Console.WriteLine("hexadecimal encrypted: " + getHexStringFromArray(resultArray)); //Return the encrypted data into unreadable string format string test = Convert.ToBase64String(resultArray, 0, resultArray.Length); Console.WriteLine("Output: " + test); } ``` The output for `Encrypt("password", true)` is: ``` hexadecimal key: 5d41402abc4b2a76b9719d911017c592 hexadecimal encrypted: 069c44845e907b346b9d82d1d553f391 Output: BpxEhF6QezRrnYLR1VPzkQ== ``` Now, the Javascript implementation (please, ignore the global variables): ``` window.text = "password"; window.key = "hello"; var useHashing = true; if (useHashing){ key = CryptoJS.MD5(key).toString(); } window.options = { mode: CryptoJS.mode.ECB, padding: CryptoJS.pad.Pkcs7 }; window.textWordArray = CryptoJS.enc.Utf8.parse(text); window.keyHex = CryptoJS.enc.Hex.parse(key); console.log('hexadecimal key: ' + keyHex); window.encrypted = CryptoJS.TripleDES.encrypt(textWordArray, keyHex, options); var base64String = encrypted.toString(); console.log('base64: ' + base64String); window.decrypted = CryptoJS.TripleDES.decrypt( { ciphertext: CryptoJS.enc.Base64.parse(base64String) }, keyHex, options); console.log('decrypted: ' + decrypted.toString(CryptoJS.enc.Utf8)); ``` Produces this result: ``` hexadecimal key: 5d41402abc4b2a76b9719d911017c592 base64: BK5f0AhEuUl9pYEy2Mliyw== ``` Which is different from the C# implementation. Here you can find the Javascript code. Any help?

Original source