创建X509Certificate2时是否阻止文件创建?

Dou*_*ugN 7 c# ssl certificate x509certificate2 x509certificate

我们在ASP.NET应用程序中创建一个X509Certificate2对象,以定期传出连接.每次创建其中一个证书时,都会在以下位置创建一个新文件:

C:\ ProgramData \微软\加密\ RSA\MachineKeys的

该文件夹现在有400万个永远不会被清理的文件.我试过删除Persist标志

新的X509Certificate2(certBytes,p12Pwd,X509KeyStorageFlags.MachineKeySet);

//没有X509KeyStorageFlags.PersistKeySet

但这没有帮助 - 仍然在每次通话时获得2Kb文件.

当我看到这个答案时,我对此抱有希望,但这是一个2008 R2服务器,而临时文件不是0字节,所以它似乎是一个不同的情况.

如何在不填满磁盘的情况下使用X509Certificate2?

Nic*_*ate 6

使用 .NET 4.6:

X509Certificate2 从 .NET Framework 4.6 开始实现 IDisposable 接口;在之前版本的.NET Framework 中,X509Certificate2 类没有实现这个接口,因此不存在Dispose 方法。


pep*_*epo 5

为了重现您的问题,我创建了此示例代码。我的测试环境是Windows 8.1 64位,该应用程序是用.NET 4.5编写的。

using System.IO;
using System.Security.Cryptography.X509Certificates;

namespace ConsoleApplication2
{
    class Program
    {
        static void Main(string[] args)
        {
            var certBytes = File.ReadAllBytes(@"c:\cert.p12");
            var p12Pwd = "somepassword";

            for (var i = 0; i < 1000; i++)
            {
                var cert = new X509Certificate2(certBytes, p12Pwd, X509KeyStorageFlags.MachineKeySet);

                // this line helped keep filesize from growing   
                // cert.Reset(); 
            }
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

文件大小C:\ProgramData\Microsoft\Crypto\RSA\MachineKeys达到2MB ,令我感到震惊。然后,应用程序退出,文件大小下降到20K(可能是它的起始大小)。

然后,我添加了cert.Reset();(我在上面的代码中对其进行了注释)。当您不再需要X509Certificate2实例时,应调用此方法。之后,的文件大小C:\ProgramData\Microsoft\Crypto\RSA\MachineKeys在20K和22K之间波动。

因此,我的建议是cert.Reset();在您不再需要该X509Certificate2实例时致电。


小智 5

我在我们的服务器上有同样的问题。我现在找到的最好方法是从我的代码中删除文件。

using System;
using System.Security.Cryptography;
using System.Security.Permissions;
using System.IO;
using System.Security.Cryptography.X509Certificates;

namespace ConsoleApp1
{
    class Program
    {
        static void Main(string[] args)
        {
            Byte[] bytes = File.ReadAllBytes(@"D:\tmp\111111111111.p12");
            X509Certificate2 x509 = new X509Certificate2(bytes, "qwerty", X509KeyStorageFlags.MachineKeySet | X509KeyStorageFlags.PersistKeySet | X509KeyStorageFlags.Exportable);
            var privateKey = x509.PrivateKey as RSACryptoServiceProvider;
            string uniqueKeyContainerName = privateKey.CspKeyContainerInfo.UniqueKeyContainerName;
            x509.Reset();

            File.Delete(string.Format(@"C:\ProgramData\Microsoft\Crypto\RSA\MachineKeys\{0}", uniqueKeyContainerName));
        }
    }
}
Run Code Online (Sandbox Code Playgroud)