Reputation: 584
I am trying to encrypt and decrypt a stream (a PDF document at base), but I am having issues with this. When I try to open the document after decryption and download, I get the error Failed to load the PDF document.
Do you know why this might be happening?
Here is the code for encryption:
public EncryptResult EncryptStream(Stream dataStream, bool reuseIV = false)
{
RijndaelManaged crypto = new RijndaelManaged();
crypto.Key = _key;
if (!reuseIV || _iv == null)
{
// make a copy of the current IV
_iv = crypto.IV;
}
else
{
// reuse the previous IV
crypto.IV = _iv;
}
var result = new EncryptResult() { IV = crypto.IV };
using (var encryptor = crypto.CreateEncryptor())
{
using (MemoryStream msEncrypt = new MemoryStream())
{
using (CryptoStream csEncrypt = new CryptoStream(msEncrypt, encryptor, CryptoStreamMode.Write))
{
var byteArrayInput = new byte[dataStream.Length];
dataStream.Read(byteArrayInput, 0, byteArrayInput.Length);
csEncrypt.Write(byteArrayInput, 0, byteArrayInput.Length);
dataStream.Close();
result.Cipher = msEncrypt.ToArray();
msEncrypt.Flush();
msEncrypt.Position = 0;
return result;
}
}
}
}
and decryption:
public Stream DecryptStream(byte[] cipher, byte[] iv)
{
RijndaelManaged crypto = new RijndaelManaged();
crypto.Key = _key;
crypto.IV = iv;
crypto.Padding = PaddingMode.Zeros;
using (var decryptor = crypto.CreateDecryptor())
{
using (MemoryStream msDecrypt = new MemoryStream(cipher))
{
using (CryptoStream csDecrypt = new CryptoStream(msDecrypt, decryptor, CryptoStreamMode.Read))
{
var sOutputFilename = new MemoryStream();
var fsDecrypted = new StreamWriter(sOutputFilename);
fsDecrypted.Write(new StreamReader(csDecrypt).ReadToEnd());
sOutputFilename.Position = 0;
return sOutputFilename;
}
}
}
}
Thanks in advance.
Upvotes: 2
Views: 1734
Reputation: 3037
using (MemoryStream msEncrypt = new MemoryStream())
{
using (CryptoStream csEncrypt = new CryptoStream(msEncrypt, encryptor, CryptoStreamMode.Write))
{
//var byteArrayInput = new byte[dataStream.Length];
//dataStream.Read(byteArrayInput, 0, byteArrayInput.Length);
//csEncrypt.Write(byteArrayInput, 0, byteArrayInput.Length);
dataStream.CopyTo(csEncrypt);
dataStream.Close();
//result.Cipher = msEncrypt.ToArray(); // not here - not flushed yet
//msEncrypt.Flush(); // don't need this
//msEncrypt.Position = 0;
}
result.Cipher = msEncrypt.ToArray();
return result;
}
and in the decryptor, get rid of all the StreamReader/StreamWriter stuff. A PDF file is compressed, ie binary. But this is after the decryption so it can't be your error.
using (var decryptor = crypto.CreateDecryptor())
{
using (MemoryStream msDecrypt = new MemoryStream(cipher))
{
var outputStream = new MemoryStream();
using (CryptoStream csDecrypt = new CryptoStream(msDecrypt, decryptor, CryptoStreamMode.Read))
{
csDecrypt.CopyTo(outputStream );
}
outputStream .Position = 0;
return outputStream ;
}
}
Upvotes: 1
Reputation: 81493
One issue is, you are likely encrypting excess bytes at the end of your stream, you need to work out how many bytes are read or use
Reads the bytes from the current stream and writes them to another stream.
Upvotes: 0