Экспорт закрытого ключа из объекта X509Certificate

Мы используем код C #, строим X509Certificate2 с файлом .p12, в конструктор вставляем путь к сертификату, пароль сертификата. Мы также отметили его как «Экспортируемый», как показано ниже:

X509Certificate2 x509Certificate2 = new X509Certificate2
("...\\MyCerificate.p12", "P@ssw0rd", X509KeyStorageFlags.Exportable);

мы получаем закрытый ключ в формате AsymmetricAlgorithm следующим образом:

x509Certificate2.PrivateKey

Теперь мы хотим получить закрытый ключ из сертификата в формате Base64, но мы понятия не имеем, как это сделать, и это так важно для нас.


person RRR    schedule 10.10.2011    source источник
comment
С чем вы пытаетесь использовать вывод Base64? Это строгая необходимость или предпочтение?   -  person Matt Kerr    schedule 12.05.2016


Ответы (4)


Важный вопрос: почему base64?

Если это для вашего собственного приложения, вы можете сохранить закрытый ключ в виде строки XML (намного проще :-).

string xml = x509Certificate2.PrivateKey.ToXmlString (true);

Если вам нужен base64 (опять же, только для вашего приложения), вы можете экспортировать ключ (параметры RSAP), затем объединить каждый byte[] и преобразовать объединенный вывод в строку base64.

Но если вы хотите взаимодействовать с другими приложениями, которым требуется закрытый ключ base64, вам необходимо знать формат (внутри строки base64). Например. во многих случаях закрытые ключи кодируются PEM (это base64 со специальным заголовком / нижний колонтитул, см. пример для X509Certificate).

Если это то, что вы ищете, вам необходимо закодировать закрытый ключ в Сначала структура PKCS # 8, затем превратитесь в base64 и добавьте верхний / нижний колонтитул. Для этого вы можете найти полезный код внутри Mono.Security.dll (лицензионный код MIT.X11 из проекта Mono).

person poupou    schedule 10.10.2011
comment
Я зависел от другого приложения, которое требует получения закрытого ключа base64. Я хочу разрешить пользователю вставлять X509Certificate2 и самостоятельно извлекать закрытый ключ в формате base 64 - знаете ли вы, предоставляет ли .Net framework какой-либо способ сделать это? - person RRR; 11.10.2011
comment
НЕТ, если бы это было (я действительно сомневаюсь в этом) или если бы я знал, я бы включил это в свой ответ. При этом ваша проблема остается, это не проблема base64, важно знать, что внутри для взаимодействия с другим вашим приложением. - person poupou; 11.10.2011
comment
Швы ссылок PKCS # 8 будут мертвы, я ожидал там статьи, но я получил только обзор проектов RSA Labs. - person Christian; 17.09.2018

Вы можете просто использовать свойство PrivateKey X509Certificate2. Фактическая реализация возвращаемого закрытого ключа зависит от алгоритма, используемого в сертификате - обычно это RSA:

rsaObj = (RSACryptoServiceProvider)myCertificate.PrivateKey; 

После этого вы сможете получить информацию о ключе RSA из его свойства ExportParameters.

person Robert    schedule 10.10.2011
comment
и когда мы знаем информацию о ключе (например, RSA-PKCS1-KeyEx), как мы можем преобразовать закрытый ключ в base64? - person RRR; 10.10.2011

Вы можете сделать это с помощью библиотеки OpenSSL для .NET:

using DidiSoft.OpenSsl;
...
X509Certificate2 x509Certificate2 = new X509Certificate2
("...\\MyCerificate.p12", "P@ssw0rd", X509KeyStorageFlags.Exportable);

PrivateKey privKey = PrivateKey.Load(x509Certificate2.PrivateKey);
bool withNewLines = true;
string base64PrivateKey = privKey.ToBase64String(withNewLines);
person Atanas Krachev    schedule 13.03.2019

Если ваша единственная проблема - закодировать закрытый ключ в кодировке Base64, вы можете просто сделать вот так:

var privateKey = x509Certificate2.PrivateKey;
var encoding = new System.Text.ASCIIEncoding();
var base64String = Convert.ToBase64String(encoding.GetBytes(privateKey.ToString()));
person fstender    schedule 10.10.2011
comment
privateKey.ToString () возвращает System.Security.Cryptography.RSACryptoserviceProvider ....., это не закрытый ключ ... - person RRR; 10.10.2011
comment
@RRR правильный. Вы обнаружите, что x509Certificate2.PublicKey.Key.ToString () вернет то же самое значение, делая это таким образом. Этого не может быть :) - person Matt Borja; 10.01.2014