"Возникла внутренняя ошибка." при загрузке файла pfx с X509Certificate2
Я пытаюсь использовать самоподписанный сертификат (C#):
X509Certificate2 cert = new X509Certificate2(
Server.MapPath("~/App_Data/myhost.pfx"), "pass");
на сервере общего веб-хостинга, и я получил ошибку:
System.Security.Cryptography.CryptographicException: An internal error occurred.
трассировка стека заканчивается
System.Security.Cryptography.CryptographicException.
ThrowCryptogaphicException(Int32 hr) +33
System.Security.Cryptography.X509Certificates.X509Utils.
_LoadCertFromFile(String fileName, IntPtr password, UInt32 dwFlags,
Boolean persistKeySet, SafeCertContextHandle& pCertCtx) +0
System.Security.Cryptography.X509Certificates.X509Certificate.
LoadCertificateFromFile(String fileName, Object password,
X509KeyStorageFlags keyStorageFlags) +237
System.Security.Cryptography.X509Certificates.X509Certificate2..ctor(
String fileName, String password) +131
На моей машине разработчика он загружается нормально. Причина, по которой я загружаю *.pfx, а не *.cer-файл, потому что мне нужен доступ с закрытым ключом (cer-файл загружается нормально). Я сделал pfx на моем dev mochine так:
makecert -r -n "CN=myhost.com, E=admin@myhost.com" -sky exchange -b 01/01/2009
-pe -sv myhost.pvk myhost.cer
<b>pvk2pfx</b> -pvk myhost.pvk -spc myhost.cer -pfx myhost.pfx -po pass</code>
Я использую версию v5.131.3790.0 от makecert
2 ответа
Используйте локальный компьютерный магазин для закрытого ключа:
X509Certificate2 cert = new X509Certificate2("myhost.pfx", "pass",
X509KeyStorageFlags.MachineKeySet);
MachineKeySet
описывается как "закрытые ключи хранятся в локальном хранилище компьютера, а не в хранилище текущего пользователя". По умолчанию без флагов - размещение в хранилище пользователя.
Даже если вы читаете сертификат с диска и сохраняете его в объекте, закрытые ключи все еще хранятся в базе данных ключей поставщика криптографических служб Microsoft Cryptographic. На хост-сервере процесс ASP.NET не имеет разрешения на доступ к хранилищу пользователей.
Другой подход (согласно некоторым комментариям ниже) заключается в изменении конфигурации IIS или удостоверения пула приложений, которые работают. Однако это предполагает, что имеется доступ к этим элементам конфигурации, что может не иметь места (например, в среде общего хостинга).
Я попробовал решение Рэнди изменить его на MachineKeySet, но затем получил сообщение об ошибке:
"ключ недействителен для использования в указанном состоянии"
Поэтому, немного погуглив, я нашел сообщение, в котором предлагалось изменить его на:
var certificate = new X509Certificate2(certKeyFilePath, passCode,
X509KeyStorageFlags.Exportable | X509KeyStorageFlags.MachineKeySet |
X509KeyStorageFlags.PersistKeySet );
и это решило мои проблемы.
Я еще не попробовал предложение изменить настройку пула приложений в конфигурации IIS. Для этого перейдите в Расширенные настройки для пула приложений вашего сайта, а затем установите для параметра "Загрузить профиль пользователя" значение true. Когда этот параметр имеет значение false, контейнеры ключей, по-видимому, недоступны.