Помилка автентифікації, оскільки віддалена сторона закрила транспортний потік


87

Я розробляю клієнт TCP для підключення сервера OpenSSL до автентифікації сертифіката. Я використовую файли .crt та .key, якими користується команда сервера. Ці сертифікати генеруються командами OpenSSL.

Я використовую SslStreamоб'єкт для автентифікації клієнта Tcp методом виклику SslStream.AuthenticateAsClient, передаючи сервер IP, SslProtocols.Ssl3і X509CertificateCollection.

Я отримую таку помилку:

Помилка автентифікації, оскільки віддалена сторона закрила транспортний потік


2
Це виглядає як проблема в пості-пудель днів: SslProtocols.Ssl3. Можливо, варто спробувати SslProtocols.Tls. У .Net 4.5 і вище ви також можете використовувати Tls11або Tls12. Див. Перелік SslProtocols . У вас можуть бути інші проблеми.
jww


Дякую. Моя проблема вирішується шляхом приєднання сертифіката з фізичного шляху сертифіката та пароля замість пошуку імені теми сертифіката з сховища сертифікатів Windows.
Оделу

Тепер я можу отримати результат з усіх протоколів SslProtocols (SSL3, Tls1 та Tls2). Дякую за відповідь
Оделу,

@Odelu, як ти вирішив проблему? На стороні клієнта або сервера?

Відповіді:


155

Я б радив не обмежувати SecurityProtocol TLS 1.1.

Рекомендоване рішення - використовувати

System.Net.ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12 | SecurityProtocolType.Tls11 | SecurityProtocolType.Tls

Інший варіант - додати такий ключ реєстру:

Key: HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\.NETFramework\v4.0.30319 
Value: SchUseStrongCrypto 

Варто зазначити, що .NET 4.6 за замовчуванням використовуватиме правильний протокол і не потребує жодного рішення.


6
вау, ти щойно розібрався з моєю проблемою - я намагався всілякі речі - а потім опинився тут, побачивши примітку на фреймворці. Просто переключив його на 4.6.1 (використовував 4.5), сподіваючись, що проблема полягає в тому, що фреймворк використовує неправильний протокол безпеки - і бінго, мої з'єднання не відмовляються, і я отримую свої дані!
Веверке

7
Важливо сказати, що це System.Net.ServicePointManager.SecurityProtocol = ...має бути виконано перед створенням запиту.
Тонаціо

2
це оновлення цільової фреймворкової версії до 4.6.1 врятувало мені життя :-)
Awais

Мій фреймворк встановлений на 4.6.2. Можливо, мені доведеться замість цього скористатися рішенням TLS
Світловий

Я використовую 4.7.2 Framework, а також сайт, на який я надсилаю запит, використовує TLS 1.2, але це схоже на 6 запитів з 10, я отримую цю помилку. будь-які ідеї?
Давіт Мікучадзе

16

Якщо ви хочете використовувати стару версію .net, створіть свій власний прапор і додайте його.

    //
    // Summary:
    //     Specifies the security protocols that are supported by the Schannel security
    //     package.
    [Flags]
    private enum MySecurityProtocolType
    {
        //
        // Summary:
        //     Specifies the Secure Socket Layer (SSL) 3.0 security protocol.
        Ssl3 = 48,
        //
        // Summary:
        //     Specifies the Transport Layer Security (TLS) 1.0 security protocol.
        Tls = 192,
        //
        // Summary:
        //     Specifies the Transport Layer Security (TLS) 1.1 security protocol.
        Tls11 = 768,
        //
        // Summary:
        //     Specifies the Transport Layer Security (TLS) 1.2 security protocol.
        Tls12 = 3072
    }
    public Session()
    {
        System.Net.ServicePointManager.SecurityProtocol = (SecurityProtocolType)(MySecurityProtocolType.Tls12 | MySecurityProtocolType.Tls11 | MySecurityProtocolType.Tls);
    }

1
Вам не потрібно використовувати свій власний клас, ви можете безпосередньо передавати цілі числа до SecurityProtocolTypeServicePointManager.SecurityProtocol = (SecurityProtocolType) 48 | (SecurityProtocolType) 192 | (SecurityProtocolType) 768 | (SecurityProtocolType) 3072;
Ян Ф.

13

Додавання наведеного нижче коду допомогло мені подолати проблему.

ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls11;

8
using (var client = new HttpClient(handler))
            {
                ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12 | SecurityProtocolType.Tls11 | SecurityProtocolType.Tls;
                var response = await client.SendAsync(new HttpRequestMessage(HttpMethod.Get, apiEndPoint)).ConfigureAwait(false);
                await response.Content.ReadAsStringAsync().ConfigureAwait(false);
            }

Це спрацювало для мене


1
Критичним бітом є такий рядок: ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12 | SecurityProtocolType.Tls11 | SecurityProtocolType.Tls; Ця відповідь чудова, хоча вона показує, де цей рядок повинен відповідати типовому випадку використання.
Нік Пейнтер,

5

Я наткнувся на те саме повідомлення про помилку під час використання ChargifyNET.dll для спілкування з API Chargify. Додавання chargify.ProtocolType = SecurityProtocolType.Tls12;до конфігурації вирішило проблему для мене.

Ось повний фрагмент коду:

public ChargifyConnect GetChargifyConnect()
{
    var chargify = new ChargifyConnect();
    chargify.apiKey = ConfigurationManager.AppSettings["Chargify.apiKey"];
    chargify.Password = ConfigurationManager.AppSettings["Chargify.apiPassword"];
    chargify.URL = ConfigurationManager.AppSettings["Chargify.url"];

    // Without this an error will be thrown.
    chargify.ProtocolType = SecurityProtocolType.Tls12;

    return chargify;
}

2

Для VB.NET перед веб-запитом ви можете розмістити наступне:

Const _Tls12 As SslProtocols = DirectCast(&HC00, SslProtocols)
Const Tls12 As SecurityProtocolType = DirectCast(_Tls12, SecurityProtocolType)
ServicePointManager.SecurityProtocol = Tls12

Це вирішило мою проблему безпеки в .NET 3.5.


0

Це трапилося зі мною, коли кінцеву точку веб-запиту було переключено на інший сервер, який приймав лише запити TLS1.2. Спробував так багато спроб, в основному таких, як Stackoverflow

  1. Ключі реєстру,
  2. Додано:
    System.Net.ServicePointManager.SecurityProtocol | = System.Net.SecurityProtocolType.Tls12; до Global.ASX OnStart,
  3. Додано в Web.config.
  4. Оновлений фреймворк .Net до версії 4.7.2, все ще отримуючи той самий виняток.

Отриманий виняток не виправдав фактичної проблеми, з якою я стикався, і не знайшов допомоги у оператора послуг.

Щоб вирішити цю проблему, я повинен додати новий набір шифрів TLS_DHE_RSA_WITH_AES_256_GCM_SHA384, я використав інструмент IIS Crypto 2.0 звідси, як показано нижче.

введіть тут опис зображення

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.