My code below is getting an error stating "Length of the data to decrypt is invalid."
when I try to copy it to MemoryStream. How can I solve this?
var table = (Encoding.Default.GetString(result, 0, result.Length - 1))
.Split(new string[] { "\r\n", "\r", "\n" }, StringSplitOptions.None);
MemoryStream encryptedStream = new MemoryStream();
encryptedStream.Write(result, 0, filelength);
DESCryptoServiceProvider DES = new DESCryptoServiceProvider();
DES.Key = ASCIIEncoding.ASCII.GetBytes(sKey);
DES.IV = ASCIIEncoding.ASCII.GetBytes(sKey);
ICryptoTransform desdecrypt = DES.CreateDecryptor();
MemoryStream decryptedStream = new MemoryStream();
encryptedStream.Position = 0;
CryptoStream decryptStream = new CryptoStream(encryptedStream, desdecrypt,
CryptoStreamMode.Read);
decryptStream.CopyTo(decryptedStream);
decryptedStream.Position = 0;
Related
This is my current implementation of the Data Encryption Standard algorithm in .NET, both encryption and decryption:
static string Encrypt(string text, string key)
{
byte[] textBytes = ASCIIEncoding.ASCII.GetBytes(text);
byte[] keyBytes = ASCIIEncoding.ASCII.GetBytes(key);
DESCryptoServiceProvider provider = new DESCryptoServiceProvider();
provider.Mode = CipherMode.OFB;
ICryptoTransform transform = provider.CreateEncryptor(keyBytes, keyBytes);
CryptoStreamMode mode = CryptoStreamMode.Write;
MemoryStream memoryStream = new MemoryStream();
CryptoStream cryptoStream = new CryptoStream(memoryStream, transform, mode);
cryptoStream.Write(textBytes, 0, textBytes.Length);
cryptoStream.FlushFinalBlock();
byte[] encryptedTextBytes = new byte[memoryStream.Length];
memoryStream.Position = 0;
memoryStream.Read(encryptedTextBytes, 0, encryptedTextBytes.Length);
string encryptedText = Convert.ToBase64String(encryptedTextBytes);
return encryptedText;
}
static string Decrypt(string text, string key)
{
byte[] textBytes = Convert.FromBase64String(text);
byte[] keyBytes = ASCIIEncoding.ASCII.GetBytes(key);
DESCryptoServiceProvider provider = new DESCryptoServiceProvider();
provider.Mode = CipherMode.OFB;
ICryptoTransform transform = provider.CreateDecryptor(keyBytes, keyBytes);
CryptoStreamMode mode = CryptoStreamMode.Write;
MemoryStream memoryStream = new MemoryStream();
CryptoStream cryptoStream = new CryptoStream(memoryStream, transform, mode);
cryptoStream.Write(textBytes, 0, textBytes.Length);
cryptoStream.FlushFinalBlock();
byte[] decryptedMessageBytes = new byte[memoryStream.Length];
memoryStream.Position = 0;
memoryStream.Read(decryptedMessageBytes, 0, decryptedMessageBytes.Length);
string decryptedText = ASCIIEncoding.ASCII.GetString(decryptedMessageBytes);
return decryptedText;
}
But it returns exception: OFB is not supported by this implementation.
Any ideas how to fix it, or where to find working OFB implementation?
Can someone explain me why these two pieces of code don't give the same result, and yet the StreamWriter in the 2nd example is using the UTF8 encoding:
var TokenEncryptKey = "D268197CF891452844441A143AAEAAEB";
var key = Encoding.UTF8.GetBytes(TokenEncryptKey);
var alg = new RijndaelManaged();
alg.Key = key;
alg.Mode = CipherMode.ECB;
var mem = new MemoryStream();
CryptoStream encryptStream = new CryptoStream(mem, alg.CreateEncryptor(), CryptoStreamMode.Write);
var validReservation = Encoding.UTF8.GetBytes("AAAAAAAAAAAAAAAAAAAAAAA");
encryptStream.Write(validReservation, 0, validReservation.Length);
encryptStream.Flush();
encryptStream.FlushFinalBlock();
Console.Out.WriteLine(Convert.ToBase64String(mem.GetBuffer(), 0, (int)mem.Length));
2nd Example
var TokenEncryptKey = "D268197CF891452844441A143AAEAAEB";
var key = Encoding.UTF8.GetBytes(TokenEncryptKey);
var alg = new RijndaelManaged();
alg.Key = key;
alg.Mode = CipherMode.ECB;
var mem = new MemoryStream();
CryptoStream encryptStream = new CryptoStream(mem, alg.CreateEncryptor(), CryptoStreamMode.Write);
StreamWriter sw = new StreamWriter(encryptStream, Encoding.UTF8);
sw.Write("AAAAAAAAAAAAAAAAAAAAAAA");
sw.Flush();
encryptStream.FlushFinalBlock();
Console.Out.WriteLine(Convert.ToBase64String(mem.GetBuffer(), 0, (int)mem.Length));
When you are using StreamWriter(encryptStream, Encoding.UTF8), this will add a Unicode BOM (byte order mark) of 3 bytes. To avoid that, use new StreamWriter(m, new UTF8Encoding()) instead.
Encoding.UTF8.GetBytes will not add the BOM even though the encoding is setup to do that - you can retrieve it if needed using GetPreamble instead.
I M using code to decrypt my file. But when i am writing back to output file it is showing error : BAD DATA
Below is my code provide , line is mentioned where error is coming.
public static void DecryptFile(string sInputFilename, string sOutputFilename, string sKey)
{
try
{
DESCryptoServiceProvider DES = new DESCryptoServiceProvider();
//A 64 bit key and IV is required for this provider.
//Set secret key For DES algorithm.
DES.Key = ASCIIEncoding.ASCII.GetBytes(sKey);
//Set initialization vector.
DES.IV = ASCIIEncoding.ASCII.GetBytes(sKey);
//Create a DES decryptor from the DES instance.
ICryptoTransform desdecrypt = DES.CreateDecryptor();
//Create a file stream to read the encrypted file back.
using (FileStream fsread = new FileStream(sInputFilename, FileMode.Open, FileAccess.Read))
{
//Create crypto stream set to read and do a
//DES decryption transform on incoming bytes.
using (CryptoStream cryptostreamDecr = new CryptoStream(fsread, desdecrypt, CryptoStreamMode.Read))
{
fsread.Flush();
//Print the contents of the decrypted file.
StreamWriter fsDecrypted = new StreamWriter(sOutputFilename);
////----ERROR IN THIS LINE----////
fsDecrypted.Write(new StreamReader(cryptostreamDecr).ReadToEnd());
fsDecrypted.Flush();
fsDecrypted.Close();
}
}
}
catch(XamlParseException XEx)
{
//throw XEx;
System.Windows.MessageBox.Show(XEx.Message.ToString());
}
}
ENCRYPTION CODE
USING SAME GETBYTE IN ENCYPTION ALSO
public static void EncryptFile(string sInputFilename,string sOutputFilename,string sKey)
{
FileStream fsInput = new FileStream(sInputFilename,FileMode.Open,FileAccess.Read);
FileStream fsEncrypted = new FileStream(sOutputFilename,FileMode.Create,FileAccess.Write);
DESCryptoServiceProvider DES = new DESCryptoServiceProvider();
DES.Key = ASCIIEncoding.ASCII.GetBytes(sKey);
DES.IV = ASCIIEncoding.ASCII.GetBytes(sKey);
ICryptoTransform desencrypt = DES.CreateEncryptor();
CryptoStream cryptostream = new CryptoStream(fsEncrypted, desencrypt, CryptoStreamMode.Write);
byte[] bytearrayinput = new byte[fsInput.Length - 1];
fsInput.Read(bytearrayinput, 0, bytearrayinput.Length);
cryptostream.Write(bytearrayinput, 0, bytearrayinput.Length);
}
The most likely reason is that you're initializing DES.IV with sKey bytes. You should use the same initialization vector here that you used dyring encryption.
I need to perform data hiding in encrypted image. To perform data hiding i need to have bitmap Image. But i don't know how to save the image as bitmap.
Below is my encryption code.
public void EncryptFile(string source, string destination)
{
string sKey = "super545";
FileStream fsInput = new FileStream(source, FileMode.Open, FileAccess.Read);
FileStream fsEncrypted = new FileStream(destination, FileMode.Create, FileAccess.Write);
DESCryptoServiceProvider DES = new DESCryptoServiceProvider();
DES.Key = ASCIIEncoding.ASCII.GetBytes(sKey);
DES.IV = ASCIIEncoding.ASCII.GetBytes(sKey);
ICryptoTransform desencrypt = DES.CreateEncryptor();
CryptoStream cryptostream = new CryptoStream(fsEncrypted, desencrypt, CryptoStreamMode.Write);
byte[] bytearrayinput = new byte[fsInput.Length - 1];
fsInput.Read(bytearrayinput, 0, bytearrayinput.Length);
cryptostream.Write(bytearrayinput, 0, bytearrayinput.Length);
cryptostream.Close();
fsInput.Close();
fsEncrypted.Close();
}
This is called like:
EncryptFile(originalimage, output);
output is a string variable with the path to store the encrypted image.
How can I call the function to run the encryption?
I receive the error the parameter is invalid when i hit this line:
Bitmap bitmap3 = new Bitmap(output);
I guess what you are trying to do is pretty close to this:
public void EncryptFile(string source, string destination)
{
string sKey = "super545";
FileStream fsInput = new FileStream(source, FileMode.Open, FileAccess.Read);
FileStream fsEncrypted = new FileStream(destination, FileMode.Create, FileAccess.Write);
//Consider to use something else, DES is dead
DESCryptoServiceProvider DES = new DESCryptoServiceProvider();
//use some key derivation function like pbkdf2 instead
DES.Key = ASCIIEncoding.ASCII.GetBytes(sKey);
//should be random, may be fixed ONLY for testing purposes
DES.IV = ASCIIEncoding.ASCII.GetBytes(sKey);
ICryptoTransform desencrypt = DES.CreateEncryptor();
CryptoStream cryptostream = new CryptoStream(fsEncrypted, desencrypt, CryptoStreamMode.Write);
//byte[] bytearrayinput = new byte[fsInput.Length - 1]; // what do you need that big buffer for anyways?
//fsInput.Read(bytearrayinput, 0, bytearrayinput.Length);
//cryptostream.Write(bytearrayinput, 0, bytearrayinput.Length);
byte[] headerBuffer = new byte[54]; // buffer for our bmp header ... without any color tables or masks
//No need for lots of checks in a proof of concept
fsInput.Read(headerBuffer, 0, headerBuffer.Length);
var biCompression = BitConverter.ToInt32(headerBuffer, 30); //get biComp from header
if (biCompression != 0 && biCompression != 3)
{
throw new Exception("Compression is not in the correct format");
}
//The buffer is copied without any encryption
fsEncrypted.Write(headerBuffer, 0, headerBuffer.Length);
//copy the rest and encrypt it ... don't care about color tables and masks for now
//and let's just hope plaintext and ciphertext have the right size
fsInput.CopyTo(cryptostream);
cryptostream.Close();
fsInput.Close();
fsEncrypted.Close();
}
I know doubleDES is not used sine of Meet-in-the-middle Attack but i need to create a program that does that kind of encryption. I tried this but i think im stuck and just cannot figure out what am i missing..
DESCryptoServiceProvider DES = new DESCryptoServiceProvider();
DES.Mode = CipherMode.ECB;
DES.Padding = PaddingMode.Zeros;
// *****ENKRIPTIMI*****
DES.Key = utf8.GetBytes(textBox1.Text.Substring(0, 8));
StreamReader sr = new StreamReader(textBox2.Text);
string permbajtja = sr.ReadToEnd();
sr.Close();
FileStream fs1 = new FileStream(textBox2.Text, FileMode.Create, FileAccess.Write);
CryptoStream cs = new CryptoStream(fs1, DES.CreateEncryptor(), CryptoStreamMode.Write);
StreamWriter sw = new StreamWriter(cs);
sw.Write(permbajtja); sw.Flush();
sw.Close();
StreamReader stream = new StreamReader(textBox2.Text);
string msg = stream.ReadToEnd();
stream.Close();
MessageBox.Show(msg);
//*****DEKRIPTIMI*****
DES.Key = utf8.GetBytes(textBox1.Text.Substring(8, 8));
FileStream fs2 = new FileStream(textBox2.Text, FileMode.Open, FileAccess.Read);
CryptoStream cs1 = new CryptoStream(fs2, DES.CreateDecryptor(), CryptoStreamMode.Read);
StreamReader sr1 = new StreamReader(cs1);
string permbajtja1 = sr1.ReadToEnd();
// MessageBox.Show(permbajtja1);
sr1.Close();
fs2.Dispose();
fs2.Close();
StreamWriter sw1 = new StreamWriter(textBox2.Text);
sw1.Write(permbajtja1);
sw1.Flush();
sw1.Close();
**** THE PART ABOVE IS JUST FOR ENCRYPTING *****
The decryption part
DESCryptoServiceProvider DES = new DESCryptoServiceProvider();
DES.Mode = CipherMode.ECB;
DES.Padding = PaddingMode.Zeros;
// *****ENKRIPTIMI*****
DES.Key = utf8.GetBytes(textBox1.Text.Substring(8,8));
StreamReader sr = new StreamReader(textBox2.Text);
string permbajtja = sr.ReadToEnd();
sr.Close();
FileStream fs1 = new FileStream(textBox2.Text, FileMode.Create, FileAccess.Write);
CryptoStream cs = new CryptoStream(fs1, DES.CreateEncryptor(), CryptoStreamMode.Write);
StreamWriter sw = new StreamWriter(cs);
sw.Write(permbajtja); sw.Flush();
sw.Close();
StreamReader lexo = new StreamReader(textBox2.Text);
MessageBox.Show(lexo.ReadToEnd());
lexo.Close();
////*****DEKRIPTIMI*****
DES.Key = utf8.GetBytes(textBox1.Text.Substring(0, 8));
FileStream fs2 = new FileStream(textBox2.Text, FileMode.Open, FileAccess.Read);
CryptoStream cs1 = new CryptoStream(fs2, DES.CreateDecryptor(), CryptoStreamMode.Read);
StreamReader sr1 = new StreamReader(cs1);
string permbajtja1 = sr1.ReadToEnd();
MessageBox.Show(permbajtja1);
sr1.Close();
fs2.Dispose();
fs2.Close();
StreamWriter sw1 = new StreamWriter(textBox2.Text);
sw1.Write(permbajtja1);
sw1.Flush();
sw1.Close();
First of all you should write the encrypt and the decrypt method:
public static string Encrypt(string originalString, byte[] key)
{
DESCryptoServiceProvider cryptoServiceProvider = new DESCryptoServiceProvider();
MemoryStream memoryStream = new MemoryStream();
CryptoStream cryptoStream = new CryptoStream(memoryStream,
cryptoServiceProvider.CreateEncryptor(key, key),
CryptoStreamMode.Write);
using (StreamWriter streamWriter = new StreamWriter(cryptoStream))
{
streamWriter.Write(originalString);
streamWriter.Flush();
cryptoStream.FlushFinalBlock();
streamWriter.Flush();
return Convert.ToBase64String(memoryStream.GetBuffer(), 0, (int)memoryStream.Length);
}
}
public static string Decrypt(string cryptedString, byte[] key)
{
DESCryptoServiceProvider cryptoServiceProvider = new DESCryptoServiceProvider();
MemoryStream memoryStream = new MemoryStream(Convert.FromBase64String(cryptedString));
CryptoStream cryptoStream = new CryptoStream(memoryStream,
cryptoServiceProvider.CreateDecryptor(key, key),
CryptoStreamMode.Read);
using (StreamReader streamReader = new StreamReader(cryptoStream))
{
return streamReader.ReadToEnd();
}
}
Now you can apply twice the encryption method (and of course twice the decryption one) to your string:
byte[] key1 = ASCIIEncoding.ASCII.GetBytes("12345678");
byte[] key2 = ASCIIEncoding.ASCII.GetBytes("abcdefgh");
string originalString = "A secret string";
string cryptedString = Encrypt(Encrypt(originalString, key1), key2);
Console.WriteLine("Encrypt message: {0}", cryptedString);
Console.WriteLine("Decrypt message: {0}", Decrypt(Decrypt(cryptedString, key2), key1));
Take a look to my code, it may help you.