0

I'm trying to decode a string crypted using AES 128 in Salesforce and passed me via web by a vendor.
I know how they encrypt the string and the vendor gave me a "decryption script" written in Apex (see below), but I'm not able to transpose that in C# (or VB.NET).
Encrypt function (in Apex):

public static String getCryptedBase64Text(String decryptedText, String encryptionKey)
{
    Blob decryptedBlob = Blob.valueOf(decryptedText);
    
    //GENERATE ENCRYPTION KEY
    Blob blobKey = Blob.valueOf(encryptionKey);
    Blob hashKey = Crypto.generateDigest('MD5', blobKey);
    
    //CRYPT TEXT USING KEY
    Blob encryptedBlob1 = Crypto.encryptWithManagedIV('AES128', hashKey, decryptedBlob);
    String encryptedString1 = EncodingUtil.base64Encode(encryptedBlob1);
    
    return encryptedString1;
}

Decrypt function (in Apex):

public static String getPlainDecryptedText(String base64encrypted, String decryptionKey)
{
    Blob encryptedBlob = EncodingUtil.base64Decode(base64encrypted);
    
    //GENERATE DECRYPTION KEY
    Blob blobKey = Blob.valueOf(decryptionKey);
    Blob HashKey = Crypto.generateDigest('MD5', blobKey);
    
    //DECRYPT TEXT USING KEY
    Blob decryptedBlob = Crypto.decryptWithManagedIV('AES128', HashKey, encryptedBlob);
    String decryptedString = decryptedBlob.toString();
    
    return decryptedString;
} 

I have the encryptionKey that the vendor gave me, and it is a four-digit string like "abcd".
Knowing both the string "decryptedText" and the key "encryptionKey", how can I decrypt "decryptedText" using C# (or VB.NET)?

Here is my C# code so far:

public String Decrypt2(string encryptedbase64text, byte[] Key){
string plaintext;

byte[] IV = new byte[16];
byte[] phase = Convert.FromBase64String(encryptedbase64Password);
Array.Copy(phase, 0, IV, 0, IV.Length);
byte[] cipherText = new byte[phase.Length - 16];;
Array.Copy(phase, 16, cipherText, 0, cipherText.Length);

using (AesManaged aesAlg = new AesManaged())
{
    aesAlg.Key = Key;
    aesAlg.IV = IV;

    ICryptoTransform decryptor = aesAlg.CreateDecryptor(aesAlg.Key, aesAlg.IV);
    using (MemoryStream msDecrypt = new MemoryStream(cipherText))
    {
        using (CryptoStream csDecrypt = new CryptoStream(msDecrypt, decryptor, CryptoStreamMode.Read))
        {
            using (StreamReader srDecrypt = new StreamReader(csDecrypt))
            {
                plaintext = srDecrypt.ReadToEnd();
            }
        }
    }
}
return plaintext;

}

Flash
  • 142
  • 2
  • 12
  • See following : https://stackoverflow.com/questions/273452/using-aes-encryption-in-c-sharp – jdweng Jul 08 '20 at 15:52
  • Sorry, but it does'n allow me to use the four digit key the vendor gave me. – Flash Jul 08 '20 at 15:54
  • [`encryptWithManagedIV`](https://developer.salesforce.com/docs/atlas.en-us.apexcode.meta/apexcode/apex_classes_restful_crypto.htm) _implicitly_ stores the 16 bytes IV preceding the ciphertext. Therefore, when decrypting in .NET, IV and ciphertext must be separated _explicitly_ after Base64 decoding of the passed data. Did you do that? Please post your most recent C# code. – Topaco Jul 08 '20 at 16:00
  • You want to read key from a string. See YD4 solution in link : aes.IV = "this is your IV"; // your IV – jdweng Jul 08 '20 at 16:02
  • Yes, I have explicitly separated IV and cyphertext. I guess I am messing up something with the key. I'm updating the answer with my C# code. – Flash Jul 08 '20 at 16:02
  • The derivation of the key using MD5 is missing or is that implemented outside the method? – Topaco Jul 08 '20 at 16:16

2 Answers2

0

System.Security.Cryptography Your going to have to do some reading there. With the script already provided it should be pretty straight forward.

ForbiddenSoul
  • 138
  • 1
  • 9
0

Final code (in VB.NET) is:

Public Function AES_Decrypt(ByVal input As String, ByVal pass As String) As String
    Dim plaintext As String = ""
    Dim Hash_AES As New MD5CryptoServiceProvider
    Dim MD5Pass = Hash_AES.ComputeHash(Encoding.Default.GetBytes(pass))
    Dim Key As Byte() = MD5Pass
    Dim IV = New Byte(15) {}
    Dim phase As Byte() = Convert.FromBase64String(input)
    Array.Copy(phase, 0, IV, 0, IV.Length)
    Dim cipherText As Byte() = New Byte(phase.Length - 16 - 1) {}
    Array.Copy(phase, 16, cipherText, 0, cipherText.Length)

    Using aesAlg As AesManaged = New AesManaged()
        aesAlg.KeySize = 128
        aesAlg.Mode = CipherMode.CBC
        aesAlg.Padding = PaddingMode.PKCS7
        aesAlg.Key = Key
        aesAlg.IV = IV
        Dim decryptor As ICryptoTransform = aesAlg.CreateDecryptor(aesAlg.Key, aesAlg.IV)
        Using msDecrypt As MemoryStream = New MemoryStream(cipherText)
            Using csDecrypt As CryptoStream = New CryptoStream(msDecrypt, decryptor, CryptoStreamMode.Read)
                Using srDecrypt As StreamReader = New StreamReader(csDecrypt)
                    plaintext = srDecrypt.ReadToEnd()
                End Using
            End Using
        End Using
    End Using

    Return plaintext
End Function

Wich can be easily translated to C# if necessary. My error was to not correctly handle the derivation of the key using MD5.

Flash
  • 142
  • 2
  • 12