通过 .NET 加密会产生格式错误的 ASN.1 header

Encrypting through .NET gives a Malformed ASN.1 header

我正在尝试加密一些文件以便通过 Internet 发送。数据应该经过 AES-256-CBC 加密,然后使用 public 密钥包裹在 SMIME 信封中。只有拥有私钥才能解密。非常标准的加密内容,真的。

我的 Encrypt() 方法如下所示:

internal static byte[] EncryptSMIME(byte[] content, X509Certificate2 cert, string encryptionAlgh, int keySize)
{ 
   var cInfo = new ContentInfo(content);

   var mimeEnvelope = new EnvelopedCms(cInfo, new AlghorithmIdentifier(Oid.FromFriendlyName(encryptionAlgh, OidGroup.EncryptionAlghorithm), keySize));

   var recipient = new CmsRecipient(cert);

   mimeEnvelope.Encrypt(recipient);
   return mimeEnvelope.Encode();
}

我们有一个负载生成器可以生成未加密的文件,通过这种方法提供它们并返回一个正确加密的文件。 运行 openssl asn1parse 工具返回正确的 header 数据。

但是,我们还有一个测试工具,应该能够以相同的方式从磁盘加密文件。因此,我构建了这个 WinForms 应用程序,它允许您 select 几个文件,然后通过相同的 Encrypt() 方法提供字节数组(直接来自 FileStream)。生成的文件是完全不同的,即使 运行 两个应用程序中的同一文件也是如此。首先,它要大得多(示例:350kb vs 548kb),而且它似乎有一个格式错误的 ASN.1 header。 openssl 工具返回:

Error in encoding

9268:error:0D07207B:asn1 encoding routines:ASN1_get_object:header too long:.\crypto\asn1\asn1_lib.c:157:

几天来我一直在努力解决这个问题,但我的实现没有发现任何问题。欢迎任何想法。

终于找到问题了!结果证明加密方法根本不是问题。

LoadTesting 工具使用 File.WriteAllBytes 编写实际的 post 加密文件。另一个使用的是 StreamWriter,它显然应用了完全不同的编码。

一旦我将 StreamWriter 替换为对 File.WriteAllBytes 的调用(使用与之前完全相同的字节数组),生成的文件就很好。