【问题标题】:Export X509Certificate2 to byte array with the Private key使用私钥将 X509Certificate2 导出到字节数组
【发布时间】:2012-04-06 08:12:12
【问题描述】:

我的商店中有一个 X509Certificate2 证书,我想使用 私钥导出到一个字节数组。证书字节数组必须是这样,当我稍后从字节数组导入证书时,私钥将具有私钥。

我尝试了很多方法,但没有成功导出带有私钥的证书。

X509Store store = new X509Store(StoreLocation.CurrentUser);      

store.Open(OpenFlags.ReadOnly);

X509Certificate2 cert = store.Certificates[1];

byte[] certBytes = cert.GetRawCertData(); // Obviously does not work!

是否可以成功将带有私钥的证书导出到字节数组中?

非常感谢您的帮助。

【问题讨论】:

    标签: c# x509 x509certificate2


    【解决方案1】:

    X509Certificate2 类的Export 函数允许您导出 带有字节数组私钥的证书。

    以下代码演示了使用私钥导出证书:

    X509Store store = new X509Store(StoreLocation.CurrentUser);
    
    store.Open(OpenFlags.ReadOnly);
    
    X509Certificate2 cert = store.Certificates[1];
    
    // Export the certificate including the private key.
    byte[] certBytes = cert.Export(X509ContentType.Pkcs12);
    

    要保护您导出的证书,请使用 Export 函数的以下重载:

    byte[] certBytes = cert.Export(X509ContentType.Pkcs12, "SecurePassword");
    

    开始编辑

    要导入证书,请使用以下代码:

    X509Certificate2 certToImport = new X509Certificate2(arr, "SecurePassword");
    
    // To mark it as exportable use the following constructor:
    X509Certificate2 certToImport = new X509Certificate2(arr, "SecurePassword", X509KeyStorageFlags.Exportable);
    // certToImport.HasPrivateKey must be true here!!
    
    X509Store store2 = new X509Store(StoreName.TrustedPublisher,
                                     StoreLocation.CurrentUser);
    store2.Open(OpenFlags.MaxAllowed);
    
    store2.Add(certToImport);
    store2.Close();
    

    结束编辑

    【讨论】:

    • 感谢您的回答,但我仍然遇到问题,当我运行您的代码并再次导入时,我得到 HasPrivateKey = false。可能是什么问题?
    • @ErikLarsson:我已经更新了我的答案。希望这可以帮助。 HasPrivateKey 属性在我的机器上为真。如果我打开 MMC 导出导入的证书,我也可以导出私钥。
    • 对于找到此线程的任何人,请注意,如果您想再次导出它,则需要在导入时将其设置为Exportable,请参阅下一个答案以及stackoverflow.com/questions/9358129/…
    • 这将为 .NET 4.6.2 控制台应用程序抛出 System.Security.Cryptography.CryptographicException: 'Key not valid for use in specified state.'
    • @EivindGussiåsLøkseth:你到底从哪里得到异常?
    【解决方案2】:

    未获得私钥的一个原因可能是它在最初添加到 CAPI 时已被标记为“不可导出”。在那种情况下,我认为这不是真正的解决办法。

    【讨论】:

    • 不,那只意味着你需要更强的技术。如果可以使用,可以导出。
    • @Joshua 不,当证书被标记为“不可导出”时,它只能用于通过操作系统对您的输入进行签名/解密,操作系统会返回结果。因此私钥可以使用,但受保护,不能导出。
    • @fjch1997:有时将调试器附加到 lsass。
    • @Joshua 当您从证书存储中获取证书时,处理私钥的不是托管代码
    • @fjch1997:嗯。当您使用内核调试器时,无论如何您都更喜欢本机代码。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2011-12-14
    • 1970-01-01
    • 1970-01-01
    • 2013-05-01
    • 2017-09-20
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多