Search code examples
c#encryptionopensslaes

Cannot decrypt OPEN-SSL AES 128 ECB encrypted string using C# - The input data is not a complete block


After using current Open SSL command (decrypt content from file "encrypted.msg"):

openssl enc -d -aes-128-ecb -in "C:\encrypted.msg" -out "c:\temp\decrypted.msg" -K "e2fc714c4727ee9395f324cd2e7f331f" -nopad

I get a new file where the decrypted content is the same as the original.

If a try to decrypt the same encrypted file content from C# (NET 7) I always get an exception: ... The input data is not a complete block. ...

This is my decrypt Code


 private static string GetHASH(byte[] RawBytes, HashAlgorithm AlgoritmoDiHASH)
 {
     if (RawBytes is not { LongLength: > 0 }) return "";
     var bytes = AlgoritmoDiHASH.ComputeHash(RawBytes);
     var builder = new StringBuilder();
     foreach (var t in bytes)
     {
         builder.Append(t.ToString("x2"));
     }

     return builder.ToString();
 }

public static string GetMd5(string rawData)
{
    if (string.IsNullOrEmpty(rawData))
    {
        throw new Exception();
    }

    return GetHASH(Encoding.UTF8.GetBytes(rawData), MD5.Create());
}

  public static byte[] AESByteArrayDecryption(byte[] encryptedBytes, string key, CipherMode cipherMode = CipherMode.CBC, PaddingMode paddingMode = PaddingMode.PKCS7, int blockSize = 128, int keySize = 256)
  {
      if (string.IsNullOrEmpty(key))
      {
        throw new Exception("Chiave di decrittazione non valida");
      }

      if (encryptedBytes.LongLength == 0)
      {
         throw new Exception("Dati da decrittografare non validi");
      }

      var keyB = new byte[32];
      var tmp = Encoding.UTF8.GetBytes(key);
      Buffer.BlockCopy(tmp, 0, keyB, 0, Math.Min(tmp.Length, 32));

using (var rm = Aes.Create())
{
    rm.BlockSize = blockSize;
    rm.KeySize = keySize;
    rm.Mode = cipherMode;
    rm.Padding = paddingMode;

    using (var dencryptor = rm.CreateDecryptor(keyB, (cipherMode != CipherMode.ECB ? new byte[blockSize / 8] : null)))
    {
        using (var dencryptStream = new MemoryStream(encryptedBytes))
        {
            using (var cryptoStream = new CryptoStream(dencryptStream, dencryptor, CryptoStreamMode.Read))
            {
                var decryptBytes = new byte[encryptedBytes.Length];
                cryptoStream.Read(decryptBytes, 0, decryptBytes.Length);
                return decryptBytes;
            }
        }
    }
}
  }

 var cipherMode = CipherMode.ECB;
 var paddingMode = PaddingMode.None;
 var blockSize = 128;
 var keySize = 256;
 var pwdMD5 = CryptographyUtil.GetMd5("abcd");
 
   var decriptedData = CryptographyUtil.AESByteArrayDecryption(criptedData, pwdMD5, cipherMode, paddingMode, blockSize, keySize);
   var decriptedDataString = Encoding.UTF8.GetString(decriptedData);

String to derive MD5 = "abcd"

Encrypted File

j›}2}0‹ÂN_’-#€6µC÷úð+|™wyh”–Ú`WŽ µÄîôZÌ¢Cü‘Êœœ4zw=-á¶(ör»”qÛ‰ ÀðMl}Ï„%ðŸ9]Ë° $„üÌR†E)zÆÝ‚¦”J4-¸–éÇ  æ&þ`:¯ê—ç‹ß<+K/´ö#Ë‘’Âé·_NFò‚øCUk³`Ú¾µh-ïQõ£®®èá}R±}å,M\™û‡Í°öç/–ÌàOÙ”ÒšßN¥þÀP
ø'†èì—Nh
#Ä›á•ÆöjȦJæËãJ’^_«.ÂK¯‚ýR*ËdîdtÍB¶ÆpçZÑŸ·oM°Ž7I}ŠÏáˆjS½Ð4Æ=ßÙ¿ré(»²”=[ˆÿjй„cÕ.W®ºïI±PB/úuÓŸic¸D®_¾c£3D‰Èwë‚áJì&ÛÂÙû}Cùô
—ÆÀËl¬~ЧԲÈyÇα    ÈÆhbSê¾ ç»ûg¢çð²POêA–Á“üïbV|Ë "Æ‘G&éýù>ü µr ÒÅ/Í)®8XU›M}1E2ÚÀúaâ³’d¾¦Ý»TV‘°ŠÖÀñÁa  ¤×}:*ØίßLÿklÌÐÄàæ4úN››w—ÊÑ ù=Pzf›ÿ%J µµ¾Nf‚{eÔleÊs‹ðý…©m¤¸ò¬†0Ñü*D‰ÀøÖˆ’…RòÒ‰013¾QYó   ,&Ñ»§<»J{«»"©‡ÆÐñ,¦®â…òž~ËkAž<ꈘ]8i8ÿ0ãÚÔFÙ™ö\®ŠM—zOÓ¶·è”Y

Plain File Content

<reading version="2"><cam><name>Test-Road</name><serial>682719AE6F5E</serial><mac></mac></cam><date>2024-01-19T09:14:06.230Z</date><timestamp>1705655646230</timestamp><plate><adr><kemler>33</kemler><onu>1203</onu></adr><value>ABCDE123</value><direction>-1</direction><country>ITA</country><vehicle>truck</vehicle><speed>20</speed><x>1419</x><y>387</y><width>197</width><height>46</height></plate><images><ocr><url>http://localhost:7572/img/2024/01/19/10/2024-01-19-10-14-06-FG050EE_full.jpg</url></ocr><context><url>http://localhost:7572/img/2024/01/19/10/2024-01-19-10-14-06-FG050EE_ctx.jpg</url></context></images></reading>

Solution

  • I found and resolved my problem changing this below lines of my postal code, related to get password bytes value:

     var keyB = new byte[32];
     var tmp = Encoding.UTF8.GetBytes(key);
     Buffer.BlockCopy(tmp, 0, keyB, 0, Math.Min(tmp.Length, 32));
    

    With

    var keyB = StringToByteArrayFastest(key);
    
    private static byte[] StringToByteArrayFastest(string hex)
    {
       if (hex.Length % 2 == 1)
         throw new Exception("The binary key cannot have an odd number of  digits");
    
       byte[] arr = new byte[hex.Length >> 1];
    
       for (int i = 0; i < hex.Length >> 1; ++i)
       {
         arr[i] = (byte)((GetHexVal(hex[i << 1]) << 4) + (GetHexVal(hex[(i << 1) + 1])));
       }
    
       return arr;
    }
    
    private static int GetHexVal(char hex)
    {
        int val = (int)hex;
        //For uppercase A-F letters:
        //return val - (val < 58 ? 48 : 55);
        //For lowercase a-f letters:
        //return val - (val < 58 ? 48 : 87);
        //Or the two combined, but a bit slower:
        return val - (val < 58 ? 48 : (val < 97 ? 55 : 87));
    }
    

    I found the two new method mentioned above on this post: Decrypting AES in C# where the file was encryped using OpenSSL -nosalt; the AES is expecting a size 16 byte array IV?