Jump to content
  • Advertisement
Sign in to follow this  
myvraccount

AesManaged error (WITH CODE)

This topic is 521 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Alright, you asked for it, and here it is.  I run this to encrypt and decrypt (depending on the mode enumeration variable).
Encryption works fine, and outputs seemingly random data, but decryption throws an exception when I try to set the cs.Position = 0.  The exception looks like this:

'cs.Position' threw an exception of type 'System.NotSupportedException'

But even if I disable that line, although I don't get an exception, buffer fills with only zeros.

I've tried to change the padding mode and the cipher mode, but that doesn't fix it either.  Here's the code:



        public byte[] aes(byte[] data, byte[] key, EncryptionMode mode)
        {
            byte[] result = null;
            AesManaged aesm = new AesManaged();
            aesm.BlockSize = 128;
            aesm.KeySize = 256;
            aesm.Padding = PaddingMode.Zeros;
            aesm.IV = new byte[16];
            aesm.Key = key;
            aesm.Mode = CipherMode.ECB;
            if(mode == EncryptionMode.Encrypt)
            {
                ICryptoTransform encryptor = aesm.CreateEncryptor(aesm.Key, aesm.IV);
                using(MemoryStream ms = new MemoryStream())
                {
                    using(CryptoStream cs = new CryptoStream(ms, encryptor, CryptoStreamMode.Write))
                    {
                        using(StreamWriter sw = new StreamWriter(cs))
                        {
                            sw.Write(data);
                        }
                        result = ms.ToArray();
                    }
                }
            }
            else
            {
                ICryptoTransform decryptor = aesm.CreateDecryptor(aesm.Key, aesm.IV);
                using(MemoryStream ms = new MemoryStream())
                {
                    ms.Position = 0;
                    using(CryptoStream cs = new CryptoStream(ms, decryptor, CryptoStreamMode.Read))
                    {
                        cs.Position = 0;
                        using(StreamReader sr = new StreamReader(cs))
                        {
                            char[] buffer = new char[16];
                            sr.Read(buffer, 0, 16);
                            result = new byte[16];
                            for(int i = 0; i < 16; i++)
                            {
                                result = Convert.ToByte(buffer);
                            }
                        }
                    }
                }
            }
            return result;
        }
 

Share this post


Link to post
Share on other sites
Advertisement
The `EncryptionMode.Decrypt` logic doesn’t initialize the decoding stream with the data provided by the argument. According to MemoryStream(byte[]) it should read something like:

ICryptoTransform decryptor = aesm.CreateDecryptor(aesm.Key, aesm.IV);
using(MemoryStream ms = new MemoryStream(data))
{

Share this post


Link to post
Share on other sites

fastcall22 is right, you're missing a parameter.  To make it a little less complicated though, try this instead.

 

if(mode == EncryptionMode.Encrypt)
{
System.Security.Cryptography.ICryptoTransform encryptor = aesm.CreateEncryptor(aesm.Key, aesm.IV);
result = encryptor.TransformFinalBlock(data, 0, data.Length);
}
else
{
System.Security.Cryptography.ICryptoTransform decryptor = aesm.CreateDecryptor(aesm.Key, aesm.IV);
result = decryptor.TransformFinalBlock(data, 0, data.Length);
}
Edited by Rattrap

Share this post


Link to post
Share on other sites

The other thing is your code is byte[] -> byte[].  The code on MSDN is string -> byte[] and byte[] -> string.  So just fixing that parameter doesn't fix the issue either.  When I did that with your code, it was passing the type name (System.Byte[]) to decryptor.  I'm assuming it took the input parameter and applied toString to it, returning the type name instead of the data itself.

Edited by Rattrap

Share this post


Link to post
Share on other sites

Well thanks, I can't believe I forgot the parameter!  Now it sort of works, but whatever I encrypt, when I decrypt it I get back bytes that literally translate into the string "System.Byte[]", so something is somehow not converting correctly.  The code looks fine to me!

Oh, sorry, you're already addressing that issue.  I should have refreshed the page.  Let me see what I'm doing in terms of any "ToString" calls or anything like that...

Edited by myvraccount

Share this post


Link to post
Share on other sites

I think your problem is actually in the encryptor, not the decryptor now.
 

sw.Write(data);

StreamWriter.Write takes a string, not byte[] (as mentioned before, their code was built around strings, not byte arrays). So I think your getting an implicit call to data.toString.

[edit]

I still recommend just using the TransformFinalBlock, but to fix the existing code just take out the StreamWriter and write directly from the CryptoStream.
 

System.Security.Cryptography.ICryptoTransform encryptor = aesm.CreateEncryptor(aesm.Key, aesm.IV);
using(System.IO.MemoryStream ms = new System.IO.MemoryStream())
{
using(System.Security.Cryptography.CryptoStream cs = new System.Security.Cryptography.CryptoStream(ms, encryptor, System.Security.Cryptography.CryptoStreamMode.Write))
{
cs.Write(data, 0, data.Length);
result = ms.ToArray();
}
}
Edited by Rattrap

Share this post


Link to post
Share on other sites

Oh, I see.  I was having trouble finding the call, and no wonder, if it was implicit.  But now I'm using the TransformFinalBlock, and it's working great.  Thanks!

Share this post


Link to post
Share on other sites

I don't have anything to add when it comes to the actual problem at hand (which seems to have been resolved now), but good on you for coming back with actual code :)

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!