Здравствуйте!
С недавнего времени перестал работать метод SignedXml.CheckSignature из библиотеки System.Security.dll
Вот код, который воспроизводит проблему:
Цитата:var content = File.ReadAllText("my.cer");
var rawCertData = Convert.FromBase64String(content);
var cert = new X509Certificate2(rawCertData);
var a = new SignedXml();
a.CheckSignature(cert, true);
Для любого ГОСТовского серта он завершается вот с такой ошибкой:
Цитата:Unhandled Exception: System.NotSupportedException: The certificate key algorithm
is not supported.
at System.Security.Cryptography.X509Certificates.X509CertificateExtensions.Ge
tAnyPublicKey(X509Certificate2 c)
at System.Security.Cryptography.Xml.SignedXml.CheckSignature(X509Certificate2
certificate, Boolean verifySignatureOnly)
at ConsoleApplication1.Program.Main(String[] args)
В случае, когда все хорошо, этот код выкинет другую ошибку: ArgumentNullException: Value is null (или что-то такое). Это нормально, потому что мы пытаемся проверить через пустую Xml. Однако исключение, которое я привел выше, не зависит от содержимого Xml, поэтому такой код для отладки данной проблемы корректный.
Мы провели небольшое исследование этой проблемы и выяснили, что она не зависит от версий криптопро CSP и криптопро .NET, не зависит от ОС.
Она появляется при установке .NET Framework 4.6.2 и уходит после ее удаления, и последующей установки любой другой версии.
Мы считаем, что это связано с тем, что в этом обновлении была переработана библиотека System.Security.dll, в частности именно этот метод.
Вероятно так же могли перестать работать и другие методы работы с сертификатом.
Вот декомпилированные исходники метода CheckSignature из двух библиотек System.Security.dll:
Версия библиотеки 4.6.1073.0, что соответствует .NET Framework 4.6.1:
http://pastebin.com/d6dpUgFnВерсия библиотеки 4.6.1590.0, что соответствует .NET Framework 4.6.2:
http://pastebin.com/8GQvECEiТ.к. развал происходит в методе GetAnyPublicKey, которого вообще не было в 4.6.1 и ранее, привожу и его исходники:
http://pastebin.com/9XyYmdy6Отсюда исключение и выбрасывается.
Стоит ли ждать поддержки 4.6.2?
Использовались криптопро .NET версии 1.0.5913.0, крипопро CSP версий 3.6, 3.9, 4.0 (разные билды, в т.ч. последний с вашего сайта).
Проверялось на операционных системах Windows server 2008 R2, 2012 R2, Windows 10.
P.S.: для тех, кто столкнется с похожей проблемой, удалить .net framework 4.6.2 можно вот так:
Windows 10: удалить обновление KB3151900
Windows server 2012 R2: удалить обновление KB3151864
Windows server 2008 R2: удалить .NET Framework 4.6.2 из "программы и компоненты".
Отредактировано пользователем 25 января 2017 г. 14:00:46(UTC)
| Причина: Не указана