GeekZilla
Triple DES encryption wrapper
Here is a handy wrapper for Triple DES encryption:
using System; using System.Collections.Generic; using System.Text; using System.Security.Cryptography; using System.IO; namespace Security { /// <summary> /// Wrapper class for Triple Des encryption /// </summary> /// <remarks> /// Author : Paul Hayman<br></br> /// Date : Feb 2006<br></br> /// info@PaulHayman.com /// </remarks> public class Encryption { private TripleDESCryptoServiceProvider des = new TripleDESCryptoServiceProvider(); private UTF8Encoding utf8 = new UTF8Encoding(); private byte[] keyValue; private byte[] iVValue; /// <summary> /// Key to use during encryption and decryption /// </summary> /// <remarks> /// <example> /// byte[] key = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24 }; /// </example> /// </remarks> public byte[] Key { get { return keyValue; } set { keyValue = value; } } /// <summary> /// Initialization vetor to use during encryption and decryption /// </summary> /// <remarks> /// <example> /// byte[] iv = { 8, 7, 6, 5, 4, 3, 2, 1 }; /// </example> /// </remarks> public byte[] iV { get { return iVValue; } set { iVValue = value; } } /// <summary> /// Constructor, allows the key and initialization vetor to be provided /// </summary> /// <param name="key"><see cref="Key"/></param> /// <param name="iV"><see cref="iV"/></param> public Encryption(byte[] key, byte[] iV) { this.keyValue = key; this.iVValue = iV; } /// <summary> /// Decrypt bytes /// </summary> /// <param name="bytes"></param> /// <returns>Decrypted data as bytes</returns> public byte[] Decrypt(byte[] bytes) { return Transform(bytes, des.CreateDecryptor(this.keyValue, this.iVValue)); } /// <summary> /// Encrypt bytes /// </summary> /// <param name="bytes"></param> /// <returns>Encrypted data as bytes</returns> public byte[] Encrypt(byte[] bytes) { return Transform(bytes, des.CreateEncryptor(this.keyValue, this.iVValue)); } /// <summary> /// Decrypt a string /// </summary> /// <param name="text"></param> /// <returns>Decrypted data as string</returns> public string Decrypt(string text) { byte[] input = Convert.FromBase64String(text); byte[] output = Transform(input, des.CreateDecryptor(this.keyValue, this.iVValue)); return utf8.GetString(output); } /// <summary> /// Encrypt a string /// </summary> /// <param name="text"></param> /// <returns>Encrypted data as string</returns> public string Encrypt(string text) { byte[] input = utf8.GetBytes(text); byte[] output = Transform(input, des.CreateEncryptor(this.keyValue, this.iVValue)); return Convert.ToBase64String(output); } /// <summary> /// Encrypt or Decrypt bytes. /// </summary> /// <remarks> /// This is used by the public methods /// </remarks> /// <param name="input">Data to be encrypted/decrypted</param> /// <param name="cryptoTransform"> /// <example>des.CreateEncryptor(this.keyValue, this.iVValue)</example> /// </param> /// <returns>Byte data containing result of opperation</returns> private byte[] Transform(byte[] input, ICryptoTransform cryptoTransform) { // Create the necessary streams MemoryStream memory = new MemoryStream(); CryptoStream stream = new CryptoStream(memory, cryptoTransform, CryptoStreamMode.Write); // Transform the bytes as requesed stream.Write(input, 0, input.Length); stream.FlushFinalBlock(); // Read the memory stream and convert it back into byte array memory.Position = 0; byte[] result = new byte[memory.Length]; memory.Read(result, 0, result.Length); // Clean up memory.Close(); stream.Close(); // Return result return result; } } }
Example usage
using System; using System.Collections.Generic; using System.Text; namespace test { class Program { static void Main(string[] args) { byte[] key = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24 }; byte[] iv = { 8, 7, 6, 5, 4, 3, 2, 1 }; Security.Encryption enc = new Security.Encryption(key, iv); Console.WriteLine(enc.Encrypt("test")); Console.WriteLine(enc.Decrypt((string)enc.Encrypt("test"))); Console.ReadLine(); } } }
Paul is the COO of kwiboo ltd and has more than 20 years IT consultancy experience. He has consulted for a number of blue chip companies and has been exposed to the folowing sectors: Utilities, Telecommunications, Insurance, Media, Investment Banking, Leisure, Legal, CRM, Pharmaceuticals, Interactive Gaming, Mobile Communications, Online Services.
Paul is the COO and co-founder of kwiboo (http://www.kwiboo.com/) and is also the creator of GeekZilla.
Comments
Marc said:
Thank you so much,
I needed a solution that doesn't use files.
I found many samples everywhere, MSDN and so on, but only samples with FileStream. I was just studiing a solution using MemoryStream as your, but
I don't feel comfortable at all with Stream, and was spending a lot of time, when I fall on your tutorial.
Your tutorial made me save so precious hours, because I found exactly what I was searching for.
Thanks again
Marc
Anuj Sharma said:
I am the person who really don't like to give any one bad comments. but this code doesn't work well. coz when you decrypt text why u write the plain text, just pass cipher text here. its decryption not going well. Its decryption is failure. just check out u r code. really.
phayman said:
Anuj,
I wrote the plain text here for the example. You can see I'm encrypting it before it's passed into decrypt.
In real life, you'd just pass the cypher text in.
Paul
Mallikarjun said:
Your Decryption Code is not working well if the string is greater than 7 characters. It's throwing error "--> Length of the data to decrypt is invalid. at stream.FlushFinalBlock(); in Transform function at decryption time.
Mallikarjun said:
private void btnDecrypt_Click(object sender, EventArgs e)
{ SqlConnection conn = new SqlConnection(@"server = sqlexpress;" + "user=****;pwd=****;" + "database=****"); byte[] key = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24 }; byte[] iv = { 8, 7, 6, 5, 4, 3, 2, 1 }; //SqlCommand cmd = new SqlCommand("storeprocedure", conn); //SqlDataAdapter adapter = new SqlDataAdapter(cmd); //DataSet ds = new DataSet(); //adapter.Fill(ds); //foreach (DataTable t in ds.Tables) //{ // BindingSource bindSource = new BindingSource(); // bindSource.DataSource = t; // dataGridView1.DataSource = bindSource; // Decryption.Encryption dec = new Encryption(key, iv); // MessageBox.Show("Before Decrypt"+t.Rows[0]["FirstName"].ToString()); // MessageBox.Show("After Decrypt"+dec.Decrypt(t.Rows[0]["FirstName"].ToString())); // MessageBox.Show("Before Decrypt" + t.Rows[0]["LastName"].ToString()); // MessageBox.Show("After Decrypt"+dec.Decrypt(t.Rows[0]["LastName"].ToString())); //} Decryption.Encryption dec = new Encryption(key, iv); string s1 = "QT7+ZmO0rCSv8kx10xRL"; string s2 = "CtJtlYafVplIbHJ"; MessageBox.Show("Before Decrypt \t" + s1 + "\tAfter Decrypt \t" + dec.Decrypt(s1)); MessageBox.Show("Before Decrypt \t" + s2 + "\tAfter Decrypt \t" + dec.Decrypt(s2)); }
I am using the above code to decrypt data which reside in sql table in encrypted form. But i am getting "Length of the data to decrypt is invalid", can you please help me in rectifying the error. I had passed the same encrypted text of database to strings here!!
Thanks in advance
Arun said:
Beautiful article. It worth a lot. Thanks man
phayman said:
Mallikarjun, I've not had any problems with data over 7 characters long.
sun0119 said:
Paul i have been led to believe that triple des produced output of the same length as the input. Howevefr all sample i have seen show some sort of text input and a base 64 output.
I need to encrypt a hex string in an incoming xml message. the encrypted text will overwrite the un-encrypted data within the mesage but it must be of the same length.
any ideas.
Jason said:
I have been using very similar (a little more inear vb) code that is giving me a fit. i keep getting an error (which of course is note documented of the text to decrypt being an improper length, so I am sure I have missed a step somewhere.
erdogan said:
great example. thank you.
Frank said:
Hello,
is it possible to encrypt/decrypt this in java? I code a socket communication and like to encrypt the streams?
Thanks
Nagos said:
It was the Base64 conversion that I was missing. This works like a charm. Thank you very much!
user said:
how can we user your c# in php..??? so that when we encrypt in php we get the same output ... which we are getting in c#..