【发布时间】:2016-07-28 15:21:23
【问题描述】:
我想以 .NET 中最有效的方式加密一个大文件(比如说 64 GB)。
我将如何实现:
- 创建
AesManaged的实例以加密文件流(读取64 GB) - 将此流保存到磁盘(因为它在内存中太大了)(写入 64 GB)
- 创建
HMACSHA512的实例以计算保存文件的哈希值(读取64 GB) - 使用 iv 将加密数据保存到磁盘(读写 64 GB)
简化的 C# 代码:
using (var aesManaged = new AesManaged())
{
using (var msEncrypt = File.OpenWrite(@"C:\Temp\bigfile.bin.tmp"))
{
using (var csEncrypt = new CryptoStream(msEncrypt, encryptor, CryptoStreamMode.Write))
{
File.OpenRead(@"C:\Temp\bigfile.bin").CopyTo(csEncrypt);
new MemoryStream(iv).CopyTo(csEncrypt);
}
}
}
using (var hmac = new HMACSHA512(hmacKey))
{
hmacHash = hmac.ComputeHash(File.OpenRead(@"C:\Temp\bigfile.bin.tmp"));
}
byte[] headerBytes;
using (var memoryStream = new MemoryStream())
{
var header = new Header
{
IV = iv,
HmacHash = hmacHash
};
Serializer.Serialize(memoryStream, header);
headerBytes = memoryStream.ToArray();
}
using (var newfile = File.OpenWrite(@"C:\Temp\bigfile.bin.enc"))
{
new MemoryStream(MagicBytes).CopyTo(newfile);
new MemoryStream(BitConverter.GetBytes(headerBytes.Length)).CopyTo(newfile);
new MemoryStream(headerBytes).CopyTo(newfile);
File.OpenRead(@"C:\Temp\bigfile.bin.tmp").CopyTo(newfile);
}
此实现的缺点是我创建了第二个文件并且我从磁盘读取了多次 64 GB。
有必要吗?如何最小化磁盘 IO 和内存分配?
【问题讨论】:
-
不,如果操作正确,则没有必要。此外,第 4 步很奇怪,因为应该在尝试加密之前创建 IV。在密文之前将IV写入文件是很常见的。
标签: c# encryption aes hmac