【问题标题】:"1408F10B:SSL routines:SSL3_GET_RECORD:wrong version number call:" on Indy“1408F10B:SSL 例程:SSL3_GET_RECORD:错误的版本号调用:”在 Indy
【发布时间】:2015-06-20 02:26:02
【问题描述】:

我有一个网络应用程序对 Google Analytics API 进行频繁的 TIdHTTP 调用(每天大约 25,000-50,000 次)。每隔一段时间,对 API 的调用就会失败,并在主题行中显示错误消息(不经常 - 不到 1000 次中的 1 次)。我从来没有找到一种模式来实现它。并且重试失败的调用通常有效。所以它看起来完全是随机的。

我有最新版本的 openssl (1.0.2.1 - 03/20/2015)。以及最新版本的 Indy(源代码文件日期为 01/07/2015)。

以下是进行这些调用的基本源代码。

有人知道它可能是什么吗?

对 API 进行两次同时调用会影响事情吗(这发生在多线程 Web 应用程序中)?

IdSSLIOHandlerSocket1 := TIdSSLIOHandlerSocketOpenSSL.create(nil);
IdSSLIOHandlerSocket1.PassThrough := True;
IdHTTP := TIdHTTP.create(nil);
IdHTTP.reusesocket := rsTrue;
IdSSLIOHandlerSocket1.reusesocket := rsTrue;
idhttp.handleredirects := True;
with IdSSLIOHandlerSocket1 do begin
  SSLOptions.Method := sslvTLSv1_2;
  SSLOptions.SSLVersions := [sslvTLSv1_2];
  SSLOptions.VerifyMode := [];
  SSLOptions.VerifyDepth := 2;
end;
with IdHTTP do begin
  IOHandler := IdSSLIOHandlerSocket1;
  ProxyParams.BasicAuthentication := False;
  Request.UserAgent := 'EmbeddedAnalytics API Interface';
  Request.ContentType := 'text/html';
  request.connection := 'close';
  Request.Accept := 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8';
  Request.BasicAuthentication := False;
  Request.UserAgent := 'Mozilla/3.0 (compatible; Indy Library)';
  HTTPOptions := [hoForceEncodeParams];
  Request.AcceptEncoding := 'gzip,deflate';
  Request.CustomHeaders.Add('Accept-Language: en-us,en;q=0.5');
  idhttp.Request.CustomHeaders.Add('Authorization: Bearer '+FToken);
end;
idhttp.get(':https://www.googleapis.com/analytics/v3/data/realtime?ids=..........');

更新 1 将一些代码行更新为:

SSLOptions.Method := sslvSSLv3;
SSLOptions.SSLVersions := [sslvSSLv3];

它有效。我将监视并查看 SSL 错误是否消失。

解决方案 结果是对 sslVSSLv3 进行更改修复了它。我不再得到错误!看到大多数其他服务都采用 TLS,这有点令人惊讶。

【问题讨论】:

  • 与您的问题无关,但您应该 1)不要使用 ReuseSocket,2)不要在 Request.AcceptEncoding 中手动添加 deflategzip(设置 TIdHTTP.Compressor 属性代替),2)使用Request.AcceptLanguage而不是Request.CustomHeaders.Add(),以及4)删除您传递给Get()的URL前面的:。如果您发出如此多的请求,您可能会考虑使用Request.Connection := 'keep-alive' 而不是'close',这样您就可以为多个请求重用一个HTTP 连接。
  • 再次感谢@RemyLebeau 对 Indy 问题的主动监控。我会看看你的建议。我发现回到 sslvSSLv3 进行 Google API 调用可以解决这个问题。令人惊讶的是,由于 POODLE,许多其他服务正在远离这一点。对您来说,为什么 sslvTLSv1_2 大部分时间都有效,但经常无效?
  • @RemyLebeau - 谢谢。我已经实现了这些。我实际上有一个在closekeep-alive 之间切换的设置。当时它被设置为“关闭”。问题:如果在通话后我释放了 idhttp 对象,“keep-alive”会有效吗?另外,关于:,这是一个错字。
  • 默认情况下,没有。如果释放TIdHTTP 对象,它将关闭连接。如果您想为新的TIdHTTP 对象重复使用相同的连接,您必须 1) 保存最后一个 Host/PortIOHandler 属性值,2) 将 IOHandler 属性设置为 nil在不关闭连接的情况下,3) 将保存的IOHandler 对象分配给另一个TIdHTTP 对象,并分配保存的Host/Port 值,5) ​​将TIdHTTP.Response.KeepAlive 属性设置为true,将HTTP.Response.Connection 属性设置为到keep-alive。这将允许TIdHTTP 重新使用现有的连接。

标签: delphi google-analytics openssl indy


【解决方案1】:

通过改变这个问题解决了:

SSLOptions.Method := sslvTLSv1_2;
SSLOptions.SSLVersions := [sslvTLSv1_2];

到这里:

SSLOptions.Method := sslvSSLv3;
SSLOptions.SSLVersions := [sslvSSLv3];

您可能想尝试 TLS 1.0,以避免 SSLv3。

使用 Google 和 TLS 1.2 有两点需要注意。其中一些现在可能已经改变。 (此讨论非常具体,仅适用于 Google 服务器和 TLS 1.2)。

首先,如果使用 TLS 1.2 和 ECDSA,您必须禁用压缩。这个奇怪的事实出现在ECDHE-ECDSA Support 下的 OpenSSL 邮件列表的讨论中。这是它生成的相关支持票:Bug 3277: OpenSSL s_client doc missing option

其次,如果您不使用 ChaCha20/Poly1305 密码,那么您必须注意 TLS 1.2 的备用密码套件。我一直无法弄清楚这一点(特别是因为应该支持所有短暂的 DH 套件),但我知道它曾经在测试中就是这种情况。因此,请务必包含以下内容以供后备使用(运行 IIS 8(或可能 7)及更早版本的 Microsoft 服务器也需要这样做):

  • TLS_RSA_WITH_AES_256_CBC_SHA256
  • TLS_RSA_WITH_AES_256_CBC_SHA
  • TLS_RSA_WITH_AES_128_CBC_SHA256
  • TLS_RSA_WITH_AES_128_CBC_SHA

【讨论】:

  • 谢谢 - 我会切换回来并按照您的建议进行更改。并且会让你知道结果。 Remy Lebeau 指出不应设置压缩。
  • @MSchenke - 我认为 TLS 1.2 是一个不错的选择,因为它有 AES/GCM (AEAD) 或 ChaCah20/Poly1305 密码套件。你应该试着让它发挥作用。如果不能,则回退到“TLS 1.0 及更高版本”。如果可以协商,则需要1.2;否则它将采用它可以获得的最高 TLS。以下是如何在 C:How to block SSL protocols in favor of TLS? 中执行“TLS 1.0 及更高版本”。但我不知道如何使用 Delphi 或 Indy。
【解决方案2】:

通过改变这个问题解决了:

SSLOptions.Method := sslvTLSv1_2;
SSLOptions.SSLVersions := [sslvTLSv1_2];

到这里:

SSLOptions.Method := sslvSSLv3;
SSLOptions.SSLVersions := [sslvSSLv3];

令人惊讶的是,大多数服务都转而使用 TLS。

【讨论】:

  • 我在使用 TLS 1.2 Google 服务器时遇到了问题。请参阅下面的答案,它可能会解释您遇到的一些事情以及一些潜在的解决方法。
【解决方案3】:

我怀疑 Google 是否仍然允许使用 SSLv3 访问他们的服务器(请参阅Poodle 攻击)。

POODLE 攻击(代表“Padding Oracle On Downgraded Legacy Encryption") 是一种中间人漏洞利用 互联网和安全软件客户端回退到 SSL 的优势 3.0.

因此,如果您的客户端收到与 SSLv3 相关的错误消息,我会联系网络专家以检查此错误消息是否可能由中间人攻击引起。

这也可能是一个简单的网络问题,因为它不可重现。

对于更深入的诊断,Wireshark 记录会有所帮助(对于专家,而不是我)。

【讨论】:

  • 感谢您的评论。由于 POODLE 攻击的唯一原因,我不得不在一年内从 Indy 9 更新到 Indy 10。在这种情况下,它是让 PayPal 界面工作。我没有确切的版本,但我在 sslvTLSv1_2 之前使用过一些东西。升级到 Indy 10 并使用这个新版本解决了这个问题。您说您怀疑 Google 仍然允许使用 SSLv3 进行访问。如果是这种情况,他们会拒绝所有请求是否有意义?他们肯定不会让一些人通过,但不会让其他人通过?
  • “POODLE 攻击......是中间人......” - 它不是 MitM 攻击。如果这个人在中间,他将可以直接访问材料,并且不需要使用 padding oracle。我所看到的攻击更像是允许发出未经身份验证的请求的 MitB(浏览器中的人)。在浏览器中,它只是一个CSRF
  • @jww original source 说 SSLv3 makes it easier for man-in-the-middle attackers to obtain cleartext data via a padding-oracle attack, aka the "POODLE" issue
  • @mjn - 更多错误信息。没有主动攻击者正在拦截通道。可以在TLS Working Group: Rethink TLS 1.3 找到更好的讨论。
猜你喜欢
  • 2014-01-12
  • 2021-06-01
  • 2019-02-14
  • 2020-11-28
  • 1970-01-01
  • 2015-06-19
  • 2020-09-07
  • 1970-01-01
相关资源
最近更新 更多